代码之家  ›  专栏  ›  技术社区  ›  Ryan Cogswell

是否可以使用唯一、稳定的函数(如组件)而不是字符串作为反应键?

  •  -1
  • Ryan Cogswell  · 技术社区  · 6 年前

    当回答 this question 我最终使用索引作为以下代码中的键:

    const menuItems = [
      { Page: ActiveDeals, Icon: Home },
      { Page: UpcomingDates, Icon: CalendarToday },
      { Page: DealsPipeline, Icon: FilterList }
    ];
    const mappedMenuItems = menuItems.map((menuItem, index) => (
      <DashboardListItem
        key={index}
        {...menuItem}
        ShownPage={this.state.shownPage}
        setShownPage={this.setShownPage}
      />
    ));
    

    在这种情况下,这是很好的,因为顺序不是易变的,但理想情况下,我会使用特定于数据的特定内容来获取唯一键。在本例中,数据中没有(或不需要)任何字符串标识符。这个数组中每个条目的主要独特之处是通过 Page 属性到每个 menuItem .此功能对于每个菜单项都是唯一的,并且会随着时间的推移而稳定(不会随着重新渲染而改变),因此它符合 key 属性,但文档将字符串指示为首选键类型。

    所以我想,“用一个函数作为键可以吗?”

    我在发布问题的同时给出了我自己的答案,但是如果你有什么需要补充的,也可以自由回答——特别是如果你知道为什么反应团队推荐字符串作为键的具体原因。

    2 回复  |  直到 6 年前
        1
  •  0
  •   Ryan Cogswell    6 年前

    为了回答这个问题,我首先查阅了文档,其中明确地建议键是字符串。

    https://reactjs.org/docs/lists-and-keys.html#basic-list-component

    _键_是一种特殊的 一串 需要包括的属性 创建元素列表。

    而且在 https://reactjs.org/docs/lists-and-keys.html#keys

    选择键的最佳方法是使用唯一标识 它的同级中的列表项。当您没有稳定的ID时, 呈现的项,您可以使用项索引作为最后的手段。

    到目前为止,文档提到了字符串和整数(例如索引),但我仍然想知道使用其他东西是否有什么坏处。所以接下来要看的是源代码。

    为了找到正确的源代码,我省略了一个我应该拥有的键,然后使用结果消息(“列表中的每个子元素都应该有一个唯一的…”)来搜索Github存储库。这让我 ReactChildFiber.js . 然后我发现以下与我的问题相关的功能:

      function mapRemainingChildren(
        returnFiber: Fiber,
        currentFirstChild: Fiber,
      ): Map<string | number, Fiber> {
        // Add the remaining children to a temporary map so that we can find them by
        // keys quickly. Implicit (null) keys get added to this set with their index
        // instead.
        const existingChildren: Map<string | number, Fiber> = new Map();
    
        let existingChild = currentFirstChild;
        while (existingChild !== null) {
          if (existingChild.key !== null) {
            existingChildren.set(existingChild.key, existingChild);
          } else {
            existingChildren.set(existingChild.index, existingChild);
          }
          existingChild = existingChild.sibling;
        }
        return existingChildren;
      }
    

    所以这里 existingChildren 是一个 Map 钥匙是用在里面的。 Map 可以支持作为键的函数,我尝试使用 menuItem.Page 就像我的钥匙一样,它看起来工作得很好,但是代码中的类型清楚地表明 string | number 作为键的类型。

    现在我的结论是除了 弦乐数 应该避免这样做,因为消息源声明这是一个限制,并且可能有一些我不知道的原因(可能是关于未来计划),可能使这个限制比当前看起来更重要,但是我仍然好奇是否有更强有力的理由来限制用于密钥的类型。

        2
  •  -3
  •   ShriP    6 年前

    它应该是唯一的字符串。你可以从这里得到帮助 https://reactjs.org/docs/lists-and-keys.html#basic-list-component

    键有助于确定哪些项已更改、添加或删除。应该为数组中的元素提供键,以使元素具有稳定的标识。