【问题标题】:immutablejs mergeIn OrderedMap returns Map if no key exists不可变的 js 合并在有序映射中如果不存在键则返回映射
【发布时间】:2016-05-20 01:23:43
【问题描述】:

我正在尝试创建一个对象,如果需要,该对象中的键在创建时创建为 OrderedMaps。

即。

OrderedMap().setIn(['users','subusers'], OrderedMap())

我想要什么

OrderedMap->users->OrderedMap()->subusers->OrderedMap()

我实际上得到了什么

OrderedMap->users->Map()->subusers->OrderedMap()

有没有什么简单的方法可以得到一个只包含 OrderedMaps 的 OrderedMap?

【问题讨论】:

  • 将是一个很棒的功能!为此,您应该在 GitHub 上针对 Immutable.js 创建一个问题。
  • 我观察到OrderedMap.updateIn( keyPath, updater)OrderedMap.mergeIn( keyPath, ...iterables) 的行为相同,并且会有相同的要求:如何让这些方法创建OrderedMap 结构,而不是Map,在任何键那个不存在的keyPath? ——这样结构的每个部分都保持秩序。

标签: immutable.js


【解决方案1】:

不幸的是,所有whateverIn 函数都以updateIn 结尾,它使用emptyMap() 作为其notSetValue。我猜想添加一个类似于 Immutable 的 fromJS 的 reviver 函数会是一个好主意,并且可能会被接受为 Issue/Pull Request。

请注意,当您从头开始构建完整的树时,您可能只想将 fromJS 与自定义 reviver 一起使用。这是 ImmutableJS 文档中示例的副本:

const { fromJS, isKeyed } = require('immutable@4.0.0-rc.9')
fromJS({ a: {b: [10, 20, 30]}, c: 40}, function (key, value, path) {
  console.log(key, value, path)
  return isKeyed(value) ? value.toOrderedMap() : value.toList()
})

下面是一个使用 OrderedMap 代替的更新函数。

let map = Immutable.OrderedMap({key0:Immutable.OrderedMap()}).setIn(['key0','key1', 'key2', 'key3'], 'banana');

function check(what, name) {
  console.log('verify map using', name);
  let entry = what.entrySeq().first();

  while(entry) {
    if (Immutable.isImmutable(entry[1])) {
      console.log(`${entry[0]} is ${Immutable.isOrdered(entry[1]) ? '' : 'un'}ordered`);
      entry = entry[1].entrySeq().first();
    } else {
      console.log(`${entry[0]} = ${entry[1]}` );
      entry = null;
    }
  }
}

check(map, 'setIn');


function orderedUpdateIn(what, path, value) {
  if (what.has(path)) {
    return what.setIn(path, value);
  }
  
  let missingPath = [], existingPath = [];
  let pathMap = what;
  
  // figure out what part is missing
  for (let i = 0;i < path.length; i++) {
    pathMap = pathMap.get(path[i]);
    if (!pathMap) {
      missingPath = path.slice(i);
      existingPath = path.slice(0,i);
      break;
    }
  }
  
  // build missing part
  let valueToSet = Immutable.OrderedMap({ 
    [missingPath[missingPath.length - 1]]: value
  });
  
  for (let i = missingPath.length - 1;i >= 0; i--) {
    valueToSet = Immutable.OrderedMap({
      [missingPath[i]]: valueToSet
    });
  }

  return map.setIn(existingPath, valueToSet);
}

map = orderedUpdateIn(Immutable.OrderedMap({key0:Immutable.OrderedMap()}), ['key0','key1', 'key2', 'key3'], 'banana');
check(map, 'updateIn');
&lt;script src="https://cdnjs.cloudflare.com/ajax/libs/immutable/4.0.0-rc.12/immutable.js"&gt;&lt;/script&gt;

【讨论】:

    猜你喜欢
    • 2014-06-19
    • 2013-08-26
    • 2017-12-17
    • 1970-01-01
    • 2018-08-23
    • 2018-03-21
    • 2018-07-28
    • 2017-03-21
    • 2022-12-05
    相关资源
    最近更新 更多