我已经阅读了大量有关() => {}
语法的使用,构造函数中的绑定,道具等中的绑定等等的文章。但据我所知,绑定this
代价高昂性能方面,并且使用箭头函数进行自动绑定非常昂贵,因为它每次都会创建一个新的匿名函数。
那么性能最佳,反应方式是什么?'处理这个问题?
构造函数中的绑定似乎适用于不需要传递参数的函数,如下所示:
constructor(props) {
super(props)
this.handleClick = this.handleClick.bind(this)
}
但是我们如何处理传递params的绑定函数,而不是在prop中绑定它,如下所示:
<li onClick={this.handleClick.bind(this, item.id)} />{item.name}</li>
在构造函数中绑定this
然后在prop中绑定null
或undefined
会导致只绑定一次的绑定函数吗?
如果有任何误解,请随时纠正我。看起来这个问题的解决方案应该更为人所知并且更具普遍性......就好像我还没有生活在一块石头下一样!
修改
即使使用抽象,点击处理程序也不会与每个项呈现绑定?
在文章here中,他们将此示例提供给避免绑定点击处理程序,但是因为React.createClass会对方法进行自动绑定,所以我不知道这是怎么回事实际上并没有绑定每个项目渲染?
var List = React.createClass({
render() {
let { handleClick } = this.props;
// handleClick still expects an id, but we don't need to worry
// about that here. Just pass the function itself and ListItem
// will call it with the id.
return (
<ul>
{this.props.items.map(item =>
<ListItem key={item.id} item={item} onItemClick={handleClick} />
)}
</ul>
);
}
});
var ListItem = React.createClass({
render() {
// Don't need a bind here, since it's just calling
// our own click handler
return (
<li onClick={this.handleClick}>
{this.props.item.name}
</li>
);
},
handleClick() {
// Our click handler knows the item's id, so it
// can just pass it along.
this.props.onItemClick(this.props.item.id);
}
});
有人可以解释一下吗? 这不就是它避免绑定每个ListItem渲染,但是由于在React.createClass中自动绑定,它仍然存在吗?
我使用class List extends Component
语法而不是createClass尝试了此示例,并且this.handleClick
未定义,因为handleClick方法未绑定到类。
在一天结束时,似乎这只是清理冗长,并且通过减少方法绑定实际上并没有提高性能...
答案 0 :(得分:8)
适用于您的<li onClick={this.handleClick.bind(this, item.id)} />{item.name}</li>
这通常意味着你需要另一层抽象IE一个新的反应组件返回相同的元素,但你可以将onClick作为prop传递,并将item id传递给prop。然后在该组件中,您可以调用this.props.onClick(this.props.id)
或者格式化数据。
本文阐述了绑定实例方法的每种方式之间的所有差异,以及每种方式如何影响性能https://medium.com/@housecor/react-binding-patterns-5-approaches-for-handling-this-92c651b5af56#。
答案 1 :(得分:5)
如果传递参数,则必须在render
函数中绑定,而不是在构造函数中绑定。这可以使用bind或arrow函数来完成。
<li onClick={this.handleClick.bind(this, item.id)} />{item.name}</li>
或
<li onClick={() => this.handleClick(item.id)} />{item.name}</li>
答案 2 :(得分:0)
这有用吗? (使用TypeScript)
<Input type="password" onChange={this.onPasswordInputChange('primary')} />;
<Input type="password" onChange={this.onPasswordInputChange('secondary')} />;
interface IOnPasswordInputChange {
(value: string): void;
}
private onPasswordInputChange = (type: string): IOnPasswordInputChange => {
return (value: string) => {
this.setState({ [type]: value });
};
}
答案 3 :(得分:0)
onDelete(e) {
const id = e.target.dataset.id;
}
<DropdownItem data-id={item.id} onClick={this.onDelete}><i className="fa fa-trash" /> Remove</DropdownItem>
答案 4 :(得分:0)
从语法上讲,我更喜欢使用箭头函数来进行绑定(特别是因为只有箭头函数才能将额外的参数传递给事件处理程序)。了解与箭头函数相关的性能损失后,我创建了一个实用程序函数,该函数接受箭头函数定义,这些定义将在组件的整个生命周期内进行缓存:
utils.js
export function createLambdaCache() {
const result = {};
return (key, lambda) => {
if (!(key in result)) {
result[key] = lambda;
}
return result[key];
};
}
component.js
class MyComponent extends React.Component {
render() {
return (
...
// below 'btnEvent' string is used as a key to cache the event reference for subsequent renders
<button onClick={this.bindWithArgs('btnEvent', evt => this.clickHander(id, evt))} />
...
);
}
clickHandler(id, evt) {
console.log(id, evt);
}
bindWithArgs = createLambdaCache();
}
createLambdaCache
以上的打字稿版本:
type evtHandler<E> = (evt: E) => void;
export function createLambdaCache<T = any>() {
const result: {[key in keyof T]: evtHandler<any>} = {} as any;
return <E>(key: keyof T, lambda: evtHandler<E>) => {
if (!(key in result)) {
result[key] = lambda;
}
return <evtHandler<E>>result[key];
};
}