是否可以在以下代码段中不使用 for 循环?
const states = [
{ a: 1 },
{ b: 1 },
{ b: 2, c: 1 }
];
const defaultState = {
a: 0,
b: 0,
c: 0
};
const getRange = prop => {
const range = [];
for (let i = 0; i < states.length; i += 1) {
let prevState;
for (let j = i - 1; j >= 0; j -= 1) {
prevState = states[j] && states[j][prop];
if (prevState) break;
}
range[i] = states[i][prop] || (prevState || defaultState[prop]);
}
return range;
};
getRange('a') // [1, 1, 1]
getRange('b') // [0, 1, 2]
getRange('c') // [0, 0, 1]
它应该仅在 JavaScript 中而不依赖于任何其他库,我尝试使用 forEach() 和 some() 进行一些尝试,但无法复制当前行为。这是为了探索语言目的。
最佳答案
const states = [
{ a: 1 },
{ b: 1 },
{ b: 2, c: 1 }
];
const defaultState = {
a: 0,
b: 0,
c: 0
};
const getRange = prop => {
return states.reduce((res, o, i) => {
res.push( o[prop] || res[i - 1] || defaultState[prop] );
return res;
}, []);
};
console.log(getRange('a')); // [1, 1, 1]
console.log(getRange('b')); // [0, 1, 2]
console.log(getRange('c')); // [0, 0, 1]
res
是结果数组。对于我们推送的 states
数组中的每个对象 o
:
res.push( o[prop] || res[i - 1] || defaultState[prop] );
// or:
res[i] = o[prop] || res[i - 1] || defaultState[prop];
或者:
- 当前对象
o
状态, - the previous state recorded (stored in
res[i - 1]
)(前一个状态), - 或来自
defaultState
的默认状态。
在我的代码中,reduce
替换了你代码中的外部 for
,res[i - 1]
替换了内部的 for
(因为不需要循环直到第一个元素获得我们已经知道它只落后一步的前一个状态)。
编辑:
要将 0
视为 thuthy,请使用:
res.push( (o[prop] || o[prop] == 0)? o[prop]: // if o[prop] is truthy or equal to 0 then use it
(res[i - 1] || res[i - 1] == 0)? res[i - 1]: // otherwise (o[prop] is neither truthy nor equal to 0) then if res[i - 1] is truthy or equal to 0 then use res[i - 1]
defaultState[prop] ); // otherwise just use the default value no matter whether it is truthy or not (that's the point of default values anyway)
或:
res.push( !isNaN(o[prop])? o[prop]: // if o[prop] is a valid number use it
!isNaN(res[i - 1])? res[i - 1]: // otherwise, if res[i - 1] is a valid number then use it
defaultState[prop] ); // otherwise, use the default value
关于javascript - 从 for 循环转换为 forEach/map/some .. 等,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/44910334/