JS生成嵌套数组

 $scope.testArray = [ {bedNum: 1, bedMsg: test1}, {bedNum: 2, bedMsg: test2}, {bedNum: 3, bedMsg: test3}, {bedNum: 4, bedMsg: test4}, {bedNum: 5, bedMsg: test5}, {bedNum: 6, bedMsg: test6}, {bedNum: 7, bedMsg: test7}, {bedNum: 8, bedMsg: test8}, {bedNum: 9, bedMsg: test9}, {bedNum: 10, bedMsg: test10}, {bedNum: 11, bedMsg: test11}, {bedNum: 12, bedMsg: test12} ]; $scope._inArray = []; $scope._outArray=[]; var i = 0; angular.forEach$scope.testArray, function data, index { if i < $scope.colsNum { i++; $scope._inArray.pushdata; if $scope.testArray.length == index + 1 { $scope._outArray.push$scope._inArray; } } else { $scope._outArray.push$scope._inArray; $scope._inArray = []; $scope._inArray.pushdata; i = 1; } }

<!—————分割线—————>

比如$scope.colsNum=3,生成一个$scope._outArray=[[5],[5],[2]]这样的数组。

这里是想把$scope.testArray生成一个嵌套的数组,这样也能实现,但觉得自己写的太啰嗦了,希望给一个更好的写法。

用 lodash

如果用 lodash,很简单,一个函数就搞定

const _ = require"lodash";
const result = _.chunkdata, colsNum;
console.logresult;

lodash 的 _.chunk 源码

回答完这个问题之后我突然好奇 lodash 是怎么实现的,所以我去翻了下它的源码,其中最关键的一段是

 while index < length { result[resIndex++] = baseSlicearray, index, index += size; }

可以看出来,它采用的是 slice 的思想,每次取一段出来放在新数组中。 slice 它调用的 baseSlice_baseSlice.js 中,对应 _.slice 方法,,实现的功能和 Array.prototype.slice 一致。

这就有意思了,如果采用这种方式,就有办法使用函数式与法了——见自己写函数的第三个方法。

自己写函数

reduce

当然自己写也可以,之前回答某个问题的时候写过,再写一次,用 reduce 再稍加处理。

主要是保持两个数组,一个是结果数组,一个是当前组数组,不需要 i 变量,因为当前组数组的 length 就能取到数量信息。

function groupByColsdata, cols { const r = data.reducer, t => { r.current.pusht; if r.current.length === cols { r.list.pushr.current; r.current = []; } return r; }, { list: [], current: [] }; if r.current.length { r.list.pushr.current; } return r.list;
}
const result = groupByColsdata, colsNum;
console.logresult;

forEach

其实 reduce 用在这里优势不明显,因为有最后一步处理,不能直接返回结果。所以用和你的方法类似的 forEach 改写

function groupByCols2data, cols { const list = []; let current = []; data.forEacht => { current.pusht; if current.length === cols { list.pushcurrent; current = []; } }; if current.length { list.pushcurrent; } return list;
}

slice + map 实现

为了函数式写法,可能有些计算不太好理解,先看代码

const result = Array.applynull, { length: Math.ceildata.length / cols
}.mapx, i => { return data.slicei * cols, i * cols + cols;
};

Array.apply 是为了生成一个长度为 Math.ceildata.length / cols 的数组,这就是循环次数(Math.ceil 用于保证有余数则进1)。

然后在循环次数内通过 slice 分段取出来。

用 RxJs

RxJs 用于异步处理数据还是挺方便的,用它的 bufferCount 解决这种问题

const Rx = require"rxjs";
const out = Rx.Observable.fromdata .bufferCountcolsNum .toArray .doconsole.log .subscribe;

这种方法适合异步或者 callback 处理(上面 console.log 那里传入的你的数据处理函数。

发表评论

电子邮件地址不会被公开。 必填项已用*标注