Andrey Green
Andrey Green

Reputation: 25

Code optimization. One function instead of several duplicate lines of code

I want to create one function instead of several duplicate lines of code. I have this module. It`s works, but I want to optimize this code.

import React from 'react';

const form = (props) => {
    //start
    let arr = props.data.nodes.map((element) => element.vendor);
    let unique = arr.filter(function(elem, index, self) {
        return index === self.indexOf(elem);
    });
    let arr2 = props.data.nodes.map((element) => element.location);
    let unique2 = arr2.filter(function(elem, index, self) {
        return index === self.indexOf(elem);
    });
    let arr3 = props.data.nodes.map((element) => element.service);
    let unique3 = arr3.filter(function(elem, index, self) {
        return index === self.indexOf(elem);
    });
    let arr4 = props.data.nodes.map((element) => element.type);
    let unique4 = arr4.filter(function(elem, index, self) {
        return index === self.indexOf(elem);
    });
  //end
    return(
        <div className='wrapper'>
            <form>
                <label>
                    <p className="nameOfInput">Vendor</p>
                    <select onChange={props.filterOurData} >
                        <option>Choose vendor</option>
                        {unique.map((element) => <option  key={element.toString()}>{element}</option>)}
                    </select>
                </label>
                <label>
                    <p className="nameOfInput">Location</p>
                    <select onChange={props.filterOurLocation} >
                        <option>Choose location</option>
                        {unique2.map((element) => <option key={element.toString()}>{element}</option>)}
                    </select>
                </label>
                <label>
                    <p className="nameOfInput">Service</p>
                    <select onChange={props.filterOurService} >
                        <option>Choose service</option>
                        {unique3.map((element) => <option key={element.toString()}>{element}</option>)}
                    </select>
                </label>
                <label>
                    <p className="nameOfInput">Device Type</p>
                    <select onChange={props.filterOurDeviceType} >
                        <option>Choose device type</option>
                        {unique4.map((element) => <option key={element.toString()}>{element}</option>)}
                    </select>
                </label>
            </form>
        </div>
    );
}

export default form;

I want to optimize code from the "start" to the "end", but I can't figure out how.

Link to the my small app: https://github.com/DrGreenNow/Relate-data

Upvotes: 1

Views: 50

Answers (2)

Mayank Shukla
Mayank Shukla

Reputation: 104499

I will suggest you to create a separate component for Select and pass all the relevant info to that component. That component will be responsible of filtering the data and rendering the ui elements.

Data that you need to pass to Select Component will be:

data: to render the options

filterKey: to filter out the data

label: default label for the select field

change: function to handle change

Like this:

const form = (props) => {
    return(
        <div className='wrapper'>
            <form>
                <Select label="Vendor" onChange={props.filterOurData} filterKey="vendor" data={props.data.nodes} />
                <Select label="Location" onChange={props.filterOurLocation} filterKey="location" data={props.data.nodes} />
                <Select label="Service" onChange={props.filterOurService} filterKey="service" data={props.data.nodes} />
                <Select label="Device Type" onChange={props.filterOurDeviceType} filterKey="type" data={props.data.nodes} />
            </form>
        </div>
    );
}


const Select = (props) => {
    let arr = props.data.map((element) => element[props.filterKey]);
    let unique = arr.filter((elem, index, self) => index === self.indexOf(elem));

    return (
        <label>
            <p className="nameOfInput">{props.label}</p>
            <select onChange={props.onChange} >
                <option>Choose {props.label}</option>
                {unique.map((element) => <option  key={element.toString()}>{element}</option>)}
            </select>
        </label>
    )
}

Upvotes: 2

Niall Moore
Niall Moore

Reputation: 138

I've attempted to simplify it a bit

    
    // setup dummy data
    let props = {
      data: {
      nodes: []
      }
    };
    for (let i = 0; i<10; i++) {
        let node = {
        vendor: "vendor"+ i,
        location: "location" + i,
        service: "service" + i,
        type: "type" + i
      }
    props.data.nodes.push(node)
    }
    
    //start
    let unique = []
    let unique2 = []
    let unique3 = []
    let unique4 = []
    
    props.data.nodes.map((element) => {
      unique.push(element.vendor)
      unique2.push(element.location)
      unique3.push(element.service)
      unique4.push(element.type)
    })
    //end
    
    console.log(unique)
    console.log(unique2)
    console.log(unique3)
    console.log(unique4)
    console.log(props.data.nodes)
    

One map -> 4 arrays of data

Upvotes: 1

Related Questions