【问题标题】:set every element value to false except one value in javascript object将每个元素值设置为 false,除了 javascript 对象中的一个值
【发布时间】:2018-03-13 12:30:47
【问题描述】:

我有一个这样的对象:

layers = {a: false, b: false, c: false, d: false, e: false};
setLayer = (val) => {
   // set val to true and every other to false
}

我将在 onClick 事件上调用 setLayer 函数。像这样:

<a onClick={this.setLayer('c')}>hello</a>
// this will set layers like this: {a: false, b: false, c: true, d: 
false, e: false}
<a onClick={this.setLayer('b')}>hello world</a>
// this will set layers like this: {a: false, b: true, c: false, d: 
false, e: false}

我不想使用 for 循环并检查 obj 中的每个键。因为 obj 在我的代码中添加了越来越多的对象。

【问题讨论】:

  • 您必须使用某种循环。无论是forfor in,还是下面答案中已经提到的任何一个。如果你不想要一个循环,那么你应该只保留一个变量,如 layerSet = 'b',它会在点击时更新为正确的值,然后在你的逻辑中稍后检查这个变量。

标签: javascript reactjs object


【解决方案1】:

取一个变量

var lastUpdatedKey;

setLayer = (val) => {
    lastUpdatedKey && (layers[lastUpdatedKey] = false);
    layers[val] = true;
    lastUpdatedKey = val;
}

【讨论】:

  • @sourabh 有帮助
【解决方案2】:

我会建议这样的事情:

const initrnalValues = {a: false, b: false, c: false, d: false, e: false}
const layers = {a: false, b: false, c: false, d: false, e: false};

const setLayer = var => {
 Object.assign(layers, initrnalValues, {
    [val]: true
}
}

就是这样,没有任何类型的循环

【讨论】:

  • 因为 assign 正在合并对象,我假设内部 JS 编译器将循环(使用您的代码两次:它需要将 2 个对象合并到第一个对象中)
  • 你对感觉背后发生的事情是正确的,但很可能他不希望代码设计有任何循环(我也不喜欢循环),感觉背后发生的事情很好to be loop(我们使用的大部分函数最后都是循环的..)
【解决方案3】:

如果您不想使用循环,则必须使用不同的实现。

一个非常优雅的解决方案是使用Proxy 代替您的layers 对象:

const layers = new Proxy({}, {
  get: function(obj, prop) {
    return prop === obj.__active__;
  },
  set: function(obj, prop, value) {
    if (!Object.getOwnPropertyDescriptor(obj, '__active__')) {
      Object.defineProperty(obj, '__active__', {
        value: null,
        writable: true,
        configurable: false,
        enumerable: false,
      });
    }

    obj[prop] = false;
    if (value === true) {
      obj.__active__ = prop;
    }
  }
});

layers.a = true;
layers.b = false;
layers.c = false;
console.log(layers);

layers.b = true;
console.log(layers);

layers.c = true;
console.log(layers);

【讨论】:

    【解决方案4】:

    使用 Object.keys 迭代图层对象中的键。如果 key 与 'val' 匹配,则将其设置为 true

    layers = {a: false, b: false, c: false, d: false, e: false};
    setLayer = (val) => {
     Object.keys(layers).forEach(item => {
       item == val ? layers[item] = true: ''
     })
    }
    

    【讨论】:

    • 那仍然是一个循环(虽然不是 for 循环)
    【解决方案5】:
    Object.keys(object).forEach(key => object[key] = false)
    object[oneKeyNeedToBeTrue] = true;
    

    【讨论】:

    • 虽然这段代码可能会解决问题,包括解释如何以及为什么解决问题将真正有助于提高您的帖子质量,并可能导致更多的赞成票。请记住,您正在为将来的读者回答问题,而不仅仅是现在提出问题的人。请编辑您的答案以添加解释并说明适用的限制和假设
    猜你喜欢
    • 2015-03-17
    • 2021-01-16
    • 2022-12-10
    • 1970-01-01
    • 2015-02-16
    • 1970-01-01
    • 1970-01-01
    • 2021-04-12
    • 2014-12-23
    相关资源
    最近更新 更多