Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/javascript/421.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181

Warning: file_get_contents(/data/phpspider/zhask/data//catemap/3/reactjs/23.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Javascript React中重复代码的简化_Javascript_Reactjs_Design Patterns - Fatal编程技术网

Javascript React中重复代码的简化

Javascript React中重复代码的简化,javascript,reactjs,design-patterns,Javascript,Reactjs,Design Patterns,在React中,有没有最佳实践来简化以下内容 getInitialState: function () { return { checkbox1: false, checkbox2: false, checkbox3: false, ... }; }, selectCheckbox1: function () { this.setState({ checkbox1: !this.state.checkbox1 }); }, select

在React中,有没有最佳实践来简化以下内容

getInitialState: function () {
  return {
    checkbox1: false,
    checkbox2: false,
    checkbox3: false,
    ...
  };
},

selectCheckbox1: function () {
  this.setState({
    checkbox1: !this.state.checkbox1
  });
},

selectCheckbox2: function () {
  this.setState({
    checkbox2: !this.state.checkbox2
  });
},

selectCheckbox3: function () {
  this.setState({
    checkbox3: !this.state.checkbox3
  });
},

...

render: function () {
  return (
    <div>
      <input type="checkbox" checked={this.state.checkbox1} onChange={this.selectCheckbox1} />
      <input type="checkbox" checked={this.state.checkbox2} onChange={this.selectCheckbox2} />
      <input type="checkbox" checked={this.state.checkbox3} onChange={this.selectCheckbox3} />
      ...
    </div>
  );
}
getInitialState:函数(){
返回{
复选框1:false,
复选框2:错误,
复选框3:错误,
...
};
},
选择复选框1:功能(){
这是我的国家({
checkbox1:!this.state.checkbox1
});
},
选择复选框2:功能(){
这是我的国家({
checkbox2:!this.state.checkbox2
});
},
选择复选框3:功能(){
这是我的国家({
checkbox3:!this.state.checkbox3
});
},
...
渲染:函数(){
返回(
...
);
}
例如,我可以对状态使用数组而不是单个字段,并创建一个通用函数,该函数使用索引参数来区分要更新的复选框:

const Checkboxes = React.createClass({
  getInitialState: function () {
    return {
      checkboxes: [false, false, false, ...]
    };
  },

  selectCheckbox: function (index) {
    let checkboxes = this.state.checkboxes.slice();
    checkboxes[index] = !checkboxes[index];
    this.setState({
      checkboxes: checkboxes
    });
  },

  render: function () {
    return (
      <div>
        <input type="checkbox" checked={this.state.checkboxes[0]} onChange={() => this.selectCheckbox(0)} />
        <input type="checkbox" checked={this.state.checkboxes[1]} onChange={() => this.selectCheckbox(1)} />
        <input type="checkbox" checked={this.state.checkboxes[2]} onChange={() => this.selectCheckbox(2)} />
        ...
      </div>
    );
  }
});
const复选框=React.createClass({
getInitialState:函数(){
返回{
复选框:[假,假,假,…]
};
},
selectCheckbox:函数(索引){
让checkboxes=this.state.checkboxes.slice();
复选框[索引]=!复选框[索引];
这是我的国家({
复选框:复选框
});
},
渲染:函数(){
返回(
此选项。选择复选框(0)}/>
此选项。选择复选框(1)}/>
此选项。选择复选框(2)}/>
...
);
}
});

我对React和JavaScript是新手,所以我不知道这里幕后到底发生了什么。第二个比第一个好吗?首选哪种方法?为什么?

第二种方法肯定比第一种方法更好。你可以放心

除此之外,还可以通过使用阵列贴图渲染复选框,而无需每次在渲染函数中重复它们

render: function () {
    return (
      <div>
        {this.state.checkboxes.map((c, i) => {
             return (
              <input key={i} type="checkbox" checked={c} onChange={() => this.selectCheckbox(i)} />
           );
         })}
      </div>
    );
  }
render:function(){
返回(
{this.state.checkbox.map((c,i)=>{
返回(
此选项。选择复选框(i)}/>
);
})}
);
}

我会这样做:

class App extends Component {
  constructor(props) {
    super(props);
    this.state = {
      checkboxes: {
        cheese: false,
        lettuce: false,
        tomatoe: false
      }
    };
  }

  handleChange = e => {
    const checkboxId = e.target.id;
    this.setState({
      checkboxes: {
        ...this.state.checkboxes,
        [checkboxId]: !this.state.checkboxes[checkboxId]
      }
    });
  };

  render() {
    return (
      <div>
        {Object.entries(this.state.checkboxes).map(([key, val]) => {
          return (
            <div key={key}>
              <input
                type="checkbox"
                checked={val}
                id={key}
                onChange={this.handleChange}
              />
              <label>
                {key}
              </label>
            </div>
          );
        })}
      </div>
    );
  }
}
类应用程序扩展组件{
建造师(道具){
超级(道具);
此.state={
复选框:{
奶酪:错,
莴苣:错,
托马托:错
}
};
}
handleChange=e=>{
const checkboxId=e.target.id;
这是我的国家({
复选框:{
…此.state.checkbox,
[checkboxId]:!this.state.checkbox[checkboxId]
}
});
};
render(){
返回(
{Object.entries(this.state.checkbox).map([key,val])=>{
返回(
{key}
);
})}
);
}
}

这使得事情更加明确,更容易理解,并且还有一个额外的好处,就是每次渲染时不创建新的匿名函数。

我更喜欢命名复选框(在对象中,而不是数组中),就像第一个示例中一样。但这可能因用例而异。如前所述,让它们像数组一样未命名,可以提供映射到它们的好处

我将这样做以减少回调函数声明的重复(无需将复选框值存储在数组中):

const复选框=React.createClass({
getInitialState:函数(){
返回{
复选框1:false,
复选框2:错误,
复选框3:错误
};
},
选择复选框:功能(复选框NR){
//返回带有checkboxNr集的回调
return()=>{
这是我的国家({
[checkboxNr]:!this.state[checkboxNr]
});
}
},
渲染:函数(){
const{checkboxes1,checkboxes2,checkboxes3}=this.state;
返回(
);
}
});

在每个渲染上创建新的匿名函数有哪些缺点?什么时候进行垃圾收集?@JoshBroadhurst允许底层组件在
shouldComponentUpdate
中比较道具是最佳做法。匿名函数总是不同的,明白了吗。谢谢在map调用中仍然有一个匿名函数(
([key,val])=>{…}
),但它不是作为道具传递的。这个匿名函数是如何影响渲染周期的?它被称为每个渲染周期,这就是为什么要使用
handleChange=e=>{
而不是
handleChange:function(e){
你能解释一下这个语法:
const{checkbox1,checkbox2,checkbox3}=this.state;
从onChange prop的命名函数返回匿名函数是否与直接在onChange prop中使用匿名函数具有相同的垃圾收集性能问题?@JoshBroadhurst。当然,也许我应该提到这一点。在本例中,是对象。
this.state
是包含所有属性。根据您引用的行,我们挑选出与名称checkbox1、checkbox2和checkbox3匹配的属性。然后它们在范围中作为变量提供。这相当于编写
const checkbox1=this.state.checkbox1;const checkbox2=this.state.checkbox2
等@JoshBroadhurst关于垃圾收集我不知道,但我猜他们也有类似的行为。但我也猜,在大多数情况下,垃圾收集也不会是一个问题。(虽然这是从Veery有限的经验讲的。)这个问题仍然没有解决。是吗?
const Checkboxes = React.createClass({
  getInitialState: function () {
    return {
      checkbox1: false,
      checkbox2: false,
      checkbox3: false
    };
  },

  selectCheckbox: function (checkboxNr) {
    // return a callback with the checkboxNr set
    return () => {
        this.setState({
         [checkboxNr]: !this.state[checkboxNr]
        });
    }
  },

  render: function () {
    const {checkboxes1, checkboxes2, checkboxes3} = this.state;
    return (
      <div>
        <input type="checkbox" checked={checkboxes1} onChange={ this.selectCheckbox("checkbox1") } />
        <input type="checkbox" checked={checkboxes2} onChange={ this.selectCheckbox("checkbox2") } />
        <input type="checkbox" checked={checkboxes3} onChange={ this.selectCheckbox("checkbox3") } />
      </div>
    );
  }
});