前言
React 中的 Fragment 是一个类似于虚拟 DOM 节点的概念,它依靠于 React 16 以上的版本实现。Fragment 提供了一个强大而简洁的方法,用于组织不产生多余 DOM 节点的组件结构。在使用 React 进行前端开发时,理解并善用 Fragment 可以使你的代码更加高效和优雅。
import React, { Fragment } from 'react'; // 堆代码 duidaima.com function Example() { return ( <Fragment> <h1>标题</h1> <p>这是一段文本。</p > </Fragment> ); }简写形式:
function Example() { return ( <> <h1>标题</h1> <p>这是一段文本。</p > </> ); }两者效果相同,简写形式只是为了减少代码的冗余,特别是在 JSX 中涉及多个子元素时,它能使代码更简洁。
// 这是非法的 function Example() { return ( <h1>标题</h1> <p>这是一段文本。</p > ); }在这种情况下,如果没有 Fragment,我们通常会用一个额外的 DOM 元素来包裹它们,比如一个 <div>,但这就引入了额外的 DOM 元素,可能会影响页面布局、CSS 样式,甚至影响性能。使用 Fragment,我们可以避免不必要的 DOM 元素,并且保持结构清晰:
function Example() { return ( <> <h1>标题</h1> <p>这是一段文本。</p > </> ); }这样,React 渲染时只会在最终的 DOM 里看到 h1 和 p,而不会多出一个 <div> 或其他无关的标签。
const list = ['React', 'Vue', 'Angular']; function Example() { return ( <ul> {list.map(item => ( <Fragment key={item}> <li>{item}</li> <span>标签</span> </Fragment> ))} </ul> ); }在这个例子中,我们使用 Fragment 来避免为每个列表项创建额外的包裹元素。这在数据量较大时能够显著减少渲染的 DOM 元素数,提高性能。
function TableRow() { return ( <> <td>名称</td> <td>价格</td> <td>数量</td> </> ); }这里使用 Fragment 来避免为每个 td 元素添加一个额外的 div 包裹,保持表格结构的简洁。
function ConditionalRendering({ showDetails }) { return ( <> <h1>标题</h1> {showDetails && <p>这是详细内容。</p >} </> ); }这样,如果 showDetails 为 false,React 仅渲染 h1,否则同时渲染 h1 和 p,且不会引入额外的 DOM 结构。
function Example() { return ( <ul> {list.map((item) => ( <Fragment key={item}> <li>{item}</li> <span>标签</span> </Fragment> ))} </ul> ); }在这个例子中,我们给 Fragment 的直接添加了 key,帮助 React 在更新时高效地比较和重用元素。
const Example = () => { const ref = React.createRef(); return ( <Fragment> <div ref={ref}>内容</div> </Fragment> );在这个例子中,ref 直接绑定在了 div 元素上,而不是 Fragment 上。
function Example({ showDetails }) { return ( <> <h1>标题</h1> {showDetails ? <p>详细内容</p > : <span>没有详细内容</span>} </> ); }这样,Fragment 能有效避免多余的包裹元素,但在一些更复杂的条件渲染中,可能需要考虑其他方式来组织结构。