假设我有一个父组件。
Parent.js
class Parent extends React.Component {
someMethod () {
LoadDataforChild();
}
render() {
return (
<div>
<Child someMethod={this.someMethod}/>
</div>
);
}
}
export default Parent;
Child.js(儿童是纯粹的组成部分)
class Child extends React.Component {
componentWillMount() {
this.props.someMethod();
}
render() {
return (
<div>
Hello child
</div>
);
}
}
我完全没有意识到反应中的反模式。我在Child(纯组件)中调用了父方法。这是反模式吗?什么是父母和儿童组成部分的反模式究竟是什么?
答案 0 :(得分:1)
一般来说反模式并不多,因为在父母中有数据获取的确定用例 - 想想多个孩子等等。但通常这是通过回调来完成的,例如当用户点击按钮时比在山上。
在您的示例中,将数据作为prop直接传递给子级并处理父级mount事件中的数据加载会更有意义。
注意,您应该避免使用componentWillMount()
,因为这是一种反模式。请改用componentDidMount()
。 Read here
答案 1 :(得分:1)
将您的问题扩展到reactjs中的反模式,我想广泛回答,因为我可以基于off.docs,文章和我自己的经验:
//REDUX REDUCER
const initialState = {
isHOCOpened: false,
child: null
}
export default reducer = (state = initialState, {type, content}) => {
switch (type) {
case ('openHOC'): {
const updatedState = {...state};
updatedState.isHOCOpened = true;
updatedState.child = content;
return {
...state, ...updatedState
}
...
}
//PARENT COMPONENT
...some other imports;
import ChildElement from './ChildElement';
export default class ParentElement extends Component {
...some code...
render() {
const { openHOC, HOCcontent } = this.props;
return (
<div onClick={()=>this.openHOC(<ChildElements/>)}>
<HOCElement/>
</div>
}
//HIGHER ORDER COMPONENT
export default const HOC = ({isHOCOpened, child}) => {
...some code...
return (
<div>
{isOpened && {children}}
</div>
)
}
推荐的方式是
...some other imports;
import ChildElement from './ChildElement';
export default class ParentElement extends Component {
state = {
isHOCOpened: false,
}
openHOC = () => this.setState({openHOC: true});
render() {
return (
<div onClick={this.openHOC}>
{isOpened && <HOCElement/><ChildElement/></HOCElement>}
</div>
}
}
...
export default const HOC = ({children}) => {
...some stuff...
return (
<div>{children}</div>
)
整理应用逻辑,避免在状态/存储中存储组件;
onClick={() => {
//some code
this.setState({isOpened: true})
}
更好地利用事件,并将其仅存储为之前的示例:
openHOC = () => {
//some code
return this.setState({openHOC: true})
};
render() {
return (
<div onClick={this.openHOC}>
{isOpened && <HOCElement/><ChildElement/></HOCElement>}
</div>
}
它会影响性能,因为它每次都会创建函数,但这仅对ReactJS产生了对JS的全面理解。请查看该文章,以更深入地讨论this。
class App extends Component {
constructor(props) {
super(props);
this.state = {
name: ''
};
}
updateValue(evt) {
this.setState({
name: evt.target.value
});
}
render() {
return (
<form>
<input onChange={this.updateValue.bind(this)} value={this.state.name} />
</form>
)
}
}
而是在构造函数中绑定所有变量:
class App extends Component {
constructor(props) {
super(props);
this.state = {
name: ''
};
this.updateValue = this.updateValue.bind(this);
}
<ul>
{liArray.map( (e,i) => <li key={i}>{e.text}</li>}
</ul>
这不是完全反模式,而是简单的错误代码和意外结果。由于在off docs中已经写了很多次,因此React使用Keys来跟踪DOM树中的更改并重绘它,因此尽管索引是对其数组位置的更改,但Keys必须是唯一的;
将独特的道具作为ID或其他{liArray.map(e => <li key={e.id}>{e.text}</li>}
setState({value: this.state.counter + passedValue})
在调用setState之前执行以下操作: updateValue(passedValue) {
const result = this.state.counter + passedValue;
setState({value: result})
}
updateValue(value) {
this.setState({counter: value});
this.addToCounter(1)
}
因为setState是异步的check it 将其作为setState中的第二个参数传递,以使其在组件为新状态时运行:
updateValue(value) {
this.setState(
{counter: value},
()=>this.addToCounter(1)
)
}
<mycomponent>content</mycomponent>
,但这可以解决问题<Mycomponent>content</MyComponent>
。 Button 和 button ;