MST

星途 面试题库

面试题:React 列表组件复用中的跨应用场景适配与设计模式

现在需要将封装好的 React 列表组件在多个不同业务的 React 应用中复用,不同应用可能有不同的样式、交互逻辑以及数据获取方式。请阐述你会如何设计这个列表组件,使其具有高度的可适配性,并结合设计模式(如策略模式、装饰器模式等)给出具体的架构设计思路。
45.0万 热度难度
前端开发React

知识考点

AI 面试

面试题答案

一键面试

设计思路

  1. 样式方面
    • 使用 CSS 模块或 styled - components 来处理样式。通过传递样式相关的 props 来实现不同应用的样式定制。例如,对于列表项的背景颜色、字体大小等,组件接收 itemBackgroundColoritemFontSize 等 props。这样可以在不同应用中轻松覆盖默认样式。
    • 采用装饰器模式,将样式逻辑分离出来。可以创建一个样式装饰器函数,该函数接收一个 React 组件作为参数,并返回一个新的带有特定样式的组件。比如:
    import React from'react';
    const withListItemStyle = (WrappedComponent) => {
      return (props) => {
        return (
          <div style={{ backgroundColor: 'lightgray', padding: '10px' }}>
            <WrappedComponent {...props} />
          </div>
        );
      };
    };
    export default withListItemStyle;
    
    在列表组件中,可以使用这个装饰器来添加基础样式,不同应用如果有特殊样式需求,可以再次使用装饰器或者通过 props 传递样式覆盖。
  2. 交互逻辑方面
    • 采用策略模式,将不同的交互逻辑抽象成策略函数。例如,点击列表项的逻辑,不同应用可能有不同处理,一个应用可能是跳转到详情页,另一个应用可能是显示一个弹窗。
    • 在列表组件中,定义一个 onItemClick 的 prop,接收一个函数作为参数。不同应用在使用该列表组件时,传递符合自身业务的点击处理函数。如下示例:
    const ListComponent = ({ items, onItemClick }) => {
      return (
        <ul>
          {items.map((item, index) => (
            <li key={index} onClick={() => onItemClick(item)}>
              {item.text}
            </li>
          ))}
        </ul>
      );
    };
    
  3. 数据获取方式方面
    • 列表组件不直接负责数据获取,而是通过 props 接收数据。这样不同应用可以根据自身的数据获取逻辑(如通过 API 调用、本地存储读取等)获取数据后传递给列表组件。
    • 可以提供一个 fetchData 的 prop,接收一个异步函数。该函数负责获取数据并返回 Promise。在列表组件的 componentDidMount(类组件)或 useEffect(函数组件)中调用这个 fetchData 函数来获取数据。例如:
    import React, { useEffect, useState } from'react';
    const ListComponent = ({ fetchData }) => {
      const [items, setItems] = useState([]);
      useEffect(() => {
        const fetch = async () => {
          const data = await fetchData();
          setItems(data);
        };
        fetch();
      }, [fetchData]);
      return (
        <ul>
          {items.map((item, index) => (
            <li key={index}>{item.text}</li>
          ))}
        </ul>
      );
    };
    export default ListComponent;
    

整体架构设计

  1. 组件结构
    • 创建一个基础的 ListBase 组件,负责处理列表的基本渲染逻辑,如循环渲染列表项等。
    • 通过装饰器模式,对 ListBase 组件进行样式装饰,生成带有默认样式的 StyledList 组件。
    • 在不同应用中,根据需求进一步通过 props 定制 StyledList 组件的样式、交互逻辑和数据获取方式。
  2. 代码示例
    • ListBase.js
    import React from'react';
    const ListBase = ({ items }) => {
      return (
        <ul>
          {items.map((item, index) => (
            <li key={index}>{item.text}</li>
          ))}
        </ul>
      );
    };
    export default ListBase;
    
    • styles.js(样式装饰器)
    import React from'react';
    const withListItemStyle = (WrappedComponent) => {
      return (props) => {
        return (
          <div style={{ backgroundColor: 'lightgray', padding: '10px' }}>
            <WrappedComponent {...props} />
          </div>
        );
      };
    };
    export default withListItemStyle;
    
    • StyledList.js
    import ListBase from './ListBase';
    import withListItemStyle from './styles';
    const StyledList = withListItemStyle(ListBase);
    export default StyledList;
    
    • 在应用中使用
    import React, { useEffect, useState } from'react';
    import StyledList from './StyledList';
    const fetchData = async () => {
      // 模拟数据获取
      return [
        { text: 'Item 1' },
        { text: 'Item 2' }
      ];
    };
    const onItemClick = (item) => {
      console.log(`Clicked on ${item.text}`);
    };
    const App = () => {
      return (
        <StyledList fetchData={fetchData} onItemClick={onItemClick} />
      );
    };
    export default App;
    

通过以上设计,列表组件可以在不同业务的 React 应用中高度适配,满足不同的样式、交互逻辑和数据获取需求。