React - 谓词功能组件

Posted

技术标签:

【中文标题】React - 谓词功能组件【英文标题】:React - Predicate functional component 【发布时间】:2020-10-02 11:47:49 【问题描述】:

我创建了一个 react 功能组件来基于谓词包装代码段(而不是在 JSX 中使用三元)。

所以,组件看起来像这样:

const PredicateWrapper = ( children, iff, otherwise ) => (
    iff ? children : (otherwise || null)
);

并且可以这样使用:

<PredicateWrapper iff=students>
   students.map(student => <Student />)
</PredicateWrapper>

问题在于,如果students 为空,则会引发错误“无法读取空属性映射”。如果我用一些文本替换students.map,则文本不会呈现,证明包装器正在工作,但是,包装器的重点是处理students 为空的情况,我希望它不会“在包装器中输入”。

如果iff 是假的,我怎样才能实现这样的东西,允许内部代码不评估并抛出运行时错误?

【问题讨论】:

【参考方案1】:

非常有趣的问题!

我在这里可能大错特错,但我认为这是因为students.map(student =&gt; &lt;Student /&gt; 仍然是您父组件渲染树的一部分。因此,当 React 尝试构建父组件的树时,它会尝试执行引发错误的那一行。

PredicateWrapper 在子组件被递归时被挂载和解析,这是iff 将启动的时候——但那是在第二次迭代中。

例如,如果我这样做,我不会得到错误

const Child = ( students ) => 
  return students.map(student => <Student />);
;


<PredicateWrapper iff=students>
  <Child students=students />
</PredicateWrapper>

【讨论】:

【参考方案2】:

让我们看看如何将 JSX 编译成带有 online Babel compiler 的 javascript

const PredicateWrapper = ( children, iff, otherwise ) =>
  iff ? children : otherwise || null;

const students = null;

const App = () =>
  React.createElement(
    PredicateWrapper,
    
      iff: students,
    ,
    students.map((student) => React.createElement(Student, null))
  );

现在您可以看到students.map 将被执行并导致错误“Cannot read property map of null”

实现目标的一种可能实现是使用渲染道具

术语“render prop”是指一种在 使用值为函数的 prop 对组件进行反应。

const PredicateWrapper = ( render, iff, otherwise = () => null ) =>
  iff ? render() : otherwise();

const StudentA = () => <span>?</span>;
const StudentB = () => <span>?</span>;

const students = [StudentA, StudentB];
//const students = null;

function App() 
  return (
    <PredicateWrapper
      iff=students
      render=() => students.map(Student => <Student />)
    />
  );

【讨论】:

感谢您的解释。不过,我不确定我是否喜欢建议的解决方案,因为渲染内容可能非常大。如果我已经用大括号括起来了,我可以改用三元

以上是关于React - 谓词功能组件的主要内容,如果未能解决你的问题,请参考以下文章

理解React的组件

单元测试 React 功能组件的功能

React - 在功能组件中测试外部功能

从 React 组件调用功能组件中的函数

将数据从子功能组件传递到父组件 - React/Typescript

React:从基于类的组件转变为基于功能的组件