【问题标题】:Are React Functional Components Regular Functions or Constructor Functions?React 函数式组件是常规函数还是构造函数?
【发布时间】:2021-06-12 06:49:35
【问题描述】:

在过去(换句话说,几年前)React 组件是具有render 方法的类。

class MyComponents extends React.Component {
    render() {
        return <div>...</div>
    }
}

最近,React 引入了函数式组件。

function MyComponent() {
    return <div>...</div>
}

以上任何一个都可以让你在 JSX 的另一部分中使用你的组件——类似这样的

<Navigation>
    <MyComponent/>
</Navigation>    

我想知道,在幕后,React 是使用这些功能组件函数作为对象构造函数,还是只是将组件函数作为常规函数调用。

也就是说——你可以调用一个javascript函数

function someFunction() {
    //...
}

const result = someFunction()

或者,您可以使用 javascript 函数创建一个新对象

function SomeFunction() {
    //...
}

const object = new SomeFunction()        

在普通的 javascript 中,约定通常是 Capitalized 的函数是构造函数,而不是的函数是常规函数。然而,我读过的很多关于组件的浅薄博客文章都表明(但从未直接说明)这些组件函数被用作常规函数,而被用作对象构造函数。

这里有没有人知道函数式组件是对象构造器、常规函数,还是 React 在幕后做了第三件奇怪的事情。如果你能指出 React 内部代码中执行此操作的特定位,则可以加分。

【问题讨论】:

  • 有趣的问题。我还没有找到正确的行,但是 createElement 调用 ReactElement 有一个注释 "Factory 方法来创建一个新的 React 元素。这不再符合类模式,所以不要使用 new调用它。另外,instanceof 检查将不起作用。”
  • React 不调用函数组件作为构造函数。你可以这么说,因为箭头函数作为函数组件是完全合法的,但它们作为构造函数是不合法的。
  • 谢谢@NicholasTower——当你说“箭头函数作为函数组件是完全合法的”——是记录在任何地方,还是只是一种常见的做法(我不怀疑你是正确,我只是对 React 的这一部分不熟悉,并尝试尽可能多地学习)
  • 谢谢@LindaPaiste - 这些是开始探索的有用代码点。 “这不再符合类模式,所以不要使用 new 来调用它。”是令人信服的,如果有间接证据的话。
  • @AlanStorm 是的,它没有直接回答你的问题,但它证明 React 使用大写名称来表示不是类且不是 new-able 的事物。

标签: javascript reactjs object


【解决方案1】:

好的,我想我已经最终找到了这个。功能组件作为构造函数调用——它们只是作为常规函数调用。

首先——如果我给一个组件添加一些调试

    function MyComponent() {
        /* ... */
        console.log(this)
        /* ... */
    }

this 的值未定义。这与将MyComponent 作为函数调用的代码一致。如果代码调用new MyComponentthis 将是MyComponent 对象的一个​​实例。

其次,如果我没有正确阅读源代码,看起来this conditional 是 React 具有处理基于类和基于函数的组件的分支逻辑的地方。

基于类的组件gets the new treatment,但a function based component 没有。

    if (isClass) {
      inst = new Component(element.props, publicContext, updater);
      /*...*/
    } else {
      /* ... */
      inst = Component(element.props, publicContext, updater);
      /* ... */
    }       

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2012-06-02
    • 2013-06-12
    • 2016-04-02
    • 1970-01-01
    • 1970-01-01
    • 2012-12-13
    • 1970-01-01
    • 2020-02-19
    相关资源
    最近更新 更多