【问题标题】:How to render a grouped list using react如何使用反应呈现分组列表
【发布时间】:2017-02-01 09:42:22
【问题描述】:

我正在尝试根据下面 sn-p 上的 const 元素根据按状态分组的对象数组来呈现列表。

我知道我可以在这里创建更小的组件,但我真的很想让我的 renderMethod 工作。

按照这个jsbin逻辑很好:

https://jsbin.com/cejiziyupa/edit?js,console

我不知道我对 react 和 JSX 做了什么。

有什么想法吗?

这是我在 codepen 上的代码 - http://codepen.io/vinicius5581/pen/rjJRvM?editors=0011

组件:

class MyComponent extends React.Component{

  constructor(props){
    super(props)
    renderMethod().bind(this);
  }

  renderMethod(){
    const elements = [
      { "id": 1, "label": "element1", "status": "status1"},
      { "id": 2, "label": "element2","status": "status2"},
      {"id": 3, "label": "element3", "status": "status6"},
      { "id": 4, "label": "element3", "status": "status10"}
    ]

    const groups = [
      { "name": "group1", "status" : ["status1", "status2", "status3", "status4"] },
      { "name": "group2", "status" : ["status5", "status6", "status7", "status8"] },
      { "name": "group3", "status" : ["status9", "status10"] }
    ]


    return (
      groups.map((group) => {
        return(
          console.log(group.name);
          <h1>{group.name}</h1>
          elements.filter((element) => group.status.includes(element.status)).map((element) =>{
            return(
              console.log(element.id);
              <div>
                <h1>{element.label}</h1>
                <p>{element.status}</p>
              </div>
            )
          })
        )
      })
    )

  }


  render(){
    return(
      {this.renderMethod()}
    )  
  } 
}

ReactDOM.render(<MyComponent />, document.getElementById('root'));

HTML:

<script src="https://cdnjs.cloudflare.com/ajax/libs/react/15.1.0/react.min.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/react/15.1.0/react-dom.min.js"></script>


<div id="root"></div>

【问题讨论】:

  • 首先,您的控制台日志导致语法错误,您不能在 JavaScript 中执行类似 return (a; b) 的操作。此外,您的代码笔没有将 JSX 转换为 React 函数,因此浏览器无法将 &lt;div&gt; 理解为 JavaScript 语法。

标签: javascript reactjs jsx


【解决方案1】:

从顶部。您的 codepen 没有转译 JSX,因此您的 javascript 中最终会出现 &lt;div&gt; 标签,这会导致语法错误。此外,您的 console.log 语句会导致语法错误,您不能在 Javascript 中执行 return(x; y)。

现在实际的react组件问题如下:

  • 在您的构造函数中,您尝试将renderMethod 函数绑定到this 的上下文。但要做到这一点,您需要使用 this.renderMethod 否则它会查找名为 renderMethod 的变量,该变量不存在。
  • 您是在函数的result 上调用绑定,而不是函数本身。因此,您正在立即执行该函数,返回一个反应对象并尝试绑定它。这可以通过删除括号来解决,调用函数 this.renderMethod().bind(this) 变为 this.renderMethod.bind(this)
  • 在您的渲染函数中,您将 renderMethod 调用包装在 JSX 样式的大括号中,我不确定这是否有效,它可能,但没有必要有那个或标准括号(并且可以说,甚至是单独的函数调用)。所以return ({this.renderMethod()})变成return this.renderMethod();
  • renderMethod的返回值是一个Array,当它需要是单个对象时。通常你可以用一个简单的div 来解决这个问题。请记住,您创建的是单个组件,而不是组件列表,永远没有理由返回数组。

现在由于开头所述的 JSX 问题,我无法让您的页面呈现,所以我在标准的 React 调用中重新制作了它。我添加了关键参数来消除警告。

class MyComponent extends React.Component{

  constructor (props) {
    super(props);
    this.renderMethod.bind(this);
  }

  renderMethod () {
    const elements = [
      { "id": 1, "label": "element1", "status": "status1" },
      { "id": 2, "label": "element2","status": "status2" },
      { "id": 3, "label": "element3", "status": "status6" },
      { "id": 4, "label": "element3", "status": "status10" }
    ];

    const groups = [
      { "name": "group1", "status" : ["status1", "status2", "status3", "status4"] },
      { "name": "group2", "status" : ["status5", "status6", "status7", "status8"] },
      { "name": "group3", "status" : ["status9", "status10"] }
    ];


    return React.createElement('div', {}, groups.map(
      group => elements.filter(element => group.status.includes(element.status)).map((element, index) => (
        React.createElement('div', { key: 'el_' + index }, [
          React.createElement('h1', { key: 'el_h1_' + index }, [element.label]),
          React.createElement('p', { key: 'el_p_' + index }, [element.status])
        ])
      ))
    ));
   }


   render () {
     return this.renderMethod();
   } 
 }

ReactDOM.render(React.createElement(MyComponent), document.getElementById('root'));

这相当于 JSX 中的类似内容

return (
  <div>
    {groups.map(
      group => elements.filter(element => group.status.includes(element.status)).map((element, index) => (
        <div key={'el_' + index}>
          <h1>{element.label}</h1>
          <p>{element.status}</p>
        </div>
      ))
    )}
  </div>
);

我也不打算详细介绍你在那里进行的所有 Array 迭代,但我只想说,你不应该在渲染调用中做那么多工作。

【讨论】:

    【解决方案2】:

    我发现你的代码中有很多不正确的地方:

    1. render 应该返回一个元素,但在您的代码中返回多个元素

    2. return 语句不应该有console.log。将其视为

    不正确:

    return (a + b; console.log(a););
    

    正确:

    console.log(a);
    return (a + b);
    
    1. map 应该返回单个根元素,但您返回的是多个元素。

    2. elements.filter应该在{},因为它是JS代码而不是JSX。

    更正的代码:

        class MyComponent extends React.Component{
    
          constructor(props){
            super(props);
            this.renderMethod = this.renderMethod.bind(this);
          }
    
          renderMethod() {
            const elements = [
              { "id": 1, "label": "element1", "status": "status1"},
              { "id": 2, "label": "element2","status": "status2"},
              {"id": 3, "label": "element3", "status": "status6"},
              { "id": 4, "label": "element3", "status": "status10"}
            ];
    
            const groups = [
              { "name": "group1", "status" : ["status1", "status2", "status3", "status4"] },
              { "name": "group2", "status" : ["status5", "status6", "status7", "status8"] },
              { "name": "group3", "status" : ["status9", "status10"] }
            ];
    
    
            return (
              <div>
                {groups.map(group => {
                  return(
                    <div>
                      <h1>{group.name}</h1>
                      {elements
                        .filter(element => group.status.includes(element.status))
                        .map(element => {
                          return(
                            <div>
                              <h1>{element.label}</h1>
                              <p>{element.status}</p>
                            </div>
                          )
                        })
                      }
                    </div>
                  )
                })}
              </div>
            );
          }
    
    
          render() {
            return (
              <div>{ this.renderMethod() }</div>
            )
          }
        }
    

    【讨论】:

      猜你喜欢
      • 2020-10-05
      • 2016-05-02
      • 1970-01-01
      • 2019-09-24
      • 2017-05-12
      • 2023-02-14
      • 1970-01-01
      • 1970-01-01
      • 2021-06-03
      相关资源
      最近更新 更多