【问题标题】:.map array by its objects keys then .map each key for values.map 数组通过其对象键然后 .map 每个键的值
【发布时间】:2021-06-16 03:09:48
【问题描述】:

如果我有一个对象数组,例如:

[{"name":"chair","type":"metal"},{"name":"chair","type":"wood"},{"name":"table","type":"plastic"},...]

如何映射它以使其返回:

<h3>chair</h3>
metal
wood

<h3>table</h3>
plastic

ecc.

我尝试的是:

return (
   <>
    {Object.values(myarray.reduce( (c, e) => {
        if (!c[e.name]) c[e.name] = e;
        return c;
    }, {})).map((title, index) => (
        <div key={index}>
            <h3>{title}</h3>
            {myarray.filter(one => one.name === title)
            .map((item, i) => (
                <div key={i}>{item.type}</div>
            ))}
        </div>
    ))}
</>
)

但它会抛出

错误:对象作为 React 子对象无效(找到:带键的对象 {名称,类型})。如果您打算渲染一组孩子,请使用 代替数组。

【问题讨论】:

  • 你为什么要把所有东西都作为一个对象返回?!那么,为什么您的 return 语句包含在 { } 中。似乎在

    中您应该使用 title.name 和在您的 div title.type 中。实际上您还应该将输入参数从标题重命名为对象或其他内容

  • 首先在reduce 方法中返回对象条目。这就是引发错误的原因。您需要将 Html 元素或字符串返回到您的数组中
  • @marks 我省略了它上面和下面不相关的 div。我添加了空外壳

标签: javascript reactjs reduce array.prototype.map


【解决方案1】:

下面是简单的分组逻辑

var data= [{"name":"chair","type":"metal"},{"name":"chair","type":"wood"},{"name":"table","type":"plastic"}]

var groupBy = (xs, f) => {
        return xs.reduce((r, v, i, a, k = f(v)) => ((r[k] || (r[k] = [])).push(v), r), {});
    };

var groupData = groupBy(data, (d) => d.name);
$.each(groupData,function(key,val){ 
  $('#pnlData').append("<h3>"+key+"</h3>")
  $.each(val,function(skey,sval){
  $('#pnlData').append("<span>"+sval.type+"</span> <br/>")
  })
}) 
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
<div id="pnlData"> </div>

【讨论】:

    【解决方案2】:

    这是一个示例代码

    const a = [{"name":"chair","type":"metal"},{"name":"chair","type":"wood"},{"name":"table","type":"plastic"}];
    
    const b = {};
    a.map(row => {
        b[row.name] = b[row.name] || []
        b[row.name].push(row.type) 
    })
    
    console.log(b) // you can check results here...
    
    // result: {"chair":["metal","wood"],"table":["plastic"]}
    

    【讨论】:

      【解决方案3】:

      Reduce是你需要的函数:

      const things = [{name: 'chair', type: 'metal'}, ...]
      
      things.reduce((a, _) => {
          a[_.name] = a[_.name] || [] // make array for this thing
          a[_.name].indexOf(_.type) < 0 && a[_.name].push(_.type) // add type if not already present
          return a
      }, {})
      

      【讨论】:

        【解决方案4】:

        您可以使用reduce 函数按名称对所有条目进行分组。然后您可以使用Object.keysObject.values 获取条目名称或类型。

        array.reduce((reducer, current) => {
            if (!reducer[current.name]) {
                reducer[current.name] = [];
            }
        
            reducer[current.name].push(current.type);
            return reducer;
        }, {})
        
        // result : { chair: ["wood", "metal"], table: ["plastic"] }
        

        【讨论】:

          【解决方案5】:

          如果可能,更改数据结构/数组对象。我认为如果它看起来像这样会更容易。你的新数组:

          const myArray = [
              {
                "name":"chair",
                "types":["metal", "wood"]
              },
              {
                "name":"table",
                "types":["plastic"]
              }
            ]
          
            //in your ui code would be 
            myArray.map(item => {
              return <div>
                  <h3>item.name</h3>
                  {item.types.map(type => <div>{type}</div>)}
              </div>
            })
          

          【讨论】:

            【解决方案6】:

            您可以将数据数组缩减为一个对象,然后使用该对象进行渲染。

             // reducer
            
               let data = [
                { name: "chair", type: "metal" },
                { name: "chair", type: "wood" },
                { name: "table", type: "plastic" }
              ];
            
              let data2 = data.reduce((xuu, val) => {
                xuu[val.name] = xuu[val.name] || [];
            
                xuu[val.name].push(val.type);
            
                return xuu;
              }, {});
            
             // render
            
              {Object.keys(data2).map((key, index1) => {
                return (
                  <div key={index1}>
                    <h3>{key}</h3>
                    {data2[key].map((val, index2) => {
                      return <div key={index2}>{val}</div>;
                    })}
                  </div>
                );
              })}
            

            你可以玩my sandbox

            【讨论】:

            • 谢谢它的工作。我不清楚的是为什么我必须在 .map 进程中使用 return 而 .mapping 数组不需要它?
            猜你喜欢
            • 2021-01-26
            • 2021-01-01
            • 1970-01-01
            • 2021-11-22
            • 1970-01-01
            • 1970-01-01
            • 1970-01-01
            • 1970-01-01
            • 1970-01-01
            相关资源
            最近更新 更多