无状态功能组件只是一个接收props
并返回React元素的函数:
const Foo = props => <Bar />;
这样,可以省略父组件中的<Foo {...props} />
(即React.createElement(Foo, props)
),而直接调用Foo
Foo(props)
,这样React.createElement
的开销很小被淘汰,但这不是必需的。
使用props
参数直接调用功能组件是否被视为错误的做法,为什么?这样做可能有什么含义?这会否对性能产生负面影响?
我的具体情况是,有一些组件是DOM元素的浅层包装,因为第三方认为这是个好主意:
function ThirdPartyThemedInput({style, ...props}) {
return <input style={{color: 'red', ...style}} {...props} />;
}
这是一个显示这种情况的demo。
这是一种被广泛接受的做法,但问题在于无法从无状态函数中获取ref
的包装的DOM元素,因此该组件使用React.forwardRef
:
function withRef(SFC) {
return React.forwardRef((props, ref) => SFC({ref, ...props}));
// this won't work
// React.forwardRef((props, ref) => <SFC ref={ref} {...props } />);
}
const ThemedInput = withRef(ThirdPartyThemedInput);
这种方式可以用作:
<ThemedInput ref={inputRef} />
...
inputRef.current.focus();
我知道的明显缺点是withRef
要求开发人员知道包装组件的实现,这不是HOC的通常要求。
在上述情况下,它是否被视为正确的方法?
答案 0 :(得分:1)
我认为直接调用无状态功能组件没有任何问题。正如您所说,这甚至消除了很小的开销。关于可能的影响,大胆地说没有影响,将来也没有影响,因为这是使用证监会的一种罕见方法。但是,所有内容都得出结论,不应有任何含义(仅需少调用一个函数)。
无论如何,下面我想提出一种使用findDOMNode
代替引用的替代方法:
我已经创建了Focus
组件,该组件确实非常易于使用,但是需要首先进行初始化(因为我们需要一种在props之外触发焦点的方法,因为组件可能会使用相同的props进行渲染)。>
// focus.js
import React from "react";
import { findDOMNode } from "react-dom";
export default function createFocus() {
class Focus extends React.Component {
componentDidMount() {
Focus.now = () => {
findDOMNode(this).focus();
}
}
render() {
return this.props.children;
}
}
return Focus;
}
// index.js
import React, { Component } from 'react';
import { render } from 'react-dom';
import createFocus from './focus';
const Focus = createFocus();
import { ThirdPartyThemedInput } from './third-party-lib';
function App() {
return (
<div>
<button onClick={() => Focus.now()}>Proceed with form</button>
<Focus>
<ThirdPartyThemedInput placeholder="Fill me" />
</Focus>
</div>
);
}
render(<App />, document.getElementById('root'));
答案 1 :(得分:0)
当您不需要使用任何生命周期方法或不需要更新组件状态时,功能组件非常有用。就您不需要它们而言,您很好,但最好还是使用无状态组件。
这不会影响性能问题,但会获得有关性能的利润,因为我们只是使用函数来渲染组件,而无需关心其更新,安装,接收道具等。但是仍然没有100%的增长使用无状态组件,因为在内部反应是使用类来呈现它们。
此post还将指导在有状态组件和无状态组件之间进行选择。
此外,您不仅可以接收道具,还可以接收裁判:
const stateless = (props, ref) => <ReturnComponent {...props} ref={ref} />
好的,让我完善我的陈述。大多数博客甚至文档都指出无状态组件没有引用。以下是有关此问题的一些问答:
我是否仅需使用statefull组件即可使用ref?
不。我已经提到过,如果必须使用组件状态或使用某些生命周期方法,则必须使用基于类的组件。
如何在无状态组件中创建引用?
const stateless = () => {
// we can't do this.myRef = React.createRef()
// so, let's create an object
const RefObj = {}
// now, create ref in {RefObj}
RefObj.myRef = React.createRef()
return <input type="text" ref={myRef} />
}