在 javascript Map 中使用 JSON 对象作为记忆函数的查找

问题描述

我们使用一个 javascript Map 对象来存储计算成本高的样式函数,这些函数被调用以在 Openlayers 地图渲染中设置特征样式。

样式函数需要一个嵌套的 JSON 对象,该对象从要设置样式的每个特征中检索。

由于 proto 参数,

Map.has() 将无法识别 JSON 对象。我们可以使用 stringify 创建一个“Hashmap”键,该键可以在样式函数的后续调用中进行评估。

我们的理解是 JSON stringify 的计算成本很高,我们想询问是否有已知的替代方案来实现与此代码中所示相同的目标,但不使用 JSON stringify。

  let memoizedStyles = new Map()

  new ol.layer.VectorTile({
    source: new ol.source.VectorTile(source),style: feature => {

      const style = feature.get('style')

      const styleStr = JSON.stringify(style)

      if (memoizedStyles.has(styleStr)) return memoizedStyles.get(styleStr)
  
      const olStyle = new ol.style.Style({
        stroke: style.strokeColor && new ol.style.Stroke({
          color: style.strokeColor,width: parseFloat(style.strokeWidth) || 1
        }),fill: style.fillColor && new ol.style.Fill({
          color: style.fillColor
        })
      })
  
      memoizedStyles.set(styleStr,olStyle)
  
      return olStyle
    }
  })

解决方法

以下答案使用 sha1 散列。理论上存在哈希冲突的可能性,但实际上它不会发生,您不必担心。


我们经常使用记忆模式并使用散列而不是 JSON.stringify。我们确定了以下模式

// const objectHashStrict = require('object-hash-strict');
// const lruCacheExt = require('lru-cache-ext');

const cache = new lruCacheExt({ maxAge: 24 * 60 * 1000 });

const get = (input) => cache.memoizeSync(objectHashStrict(input.style),() => {
  // do stuff here as necessary
  return {
    name: input.name,...input.style,stroke: {
      color: '#ff0000',width: 1
    }
  };
});

console.log(get({ name: 'Alpha',style: { type: 'One' } }));
// => { name: 'Alpha',type: 'One',stroke: { color: '#ff0000',width: 1 } }
console.log(get({ name: 'Beta',width: 1 } }
console.log(get({ name: 'Zeta',style: { type: 'Two' } }));
// => { name: 'Zeta',type: 'Two',width: 1 } }
.as-console-wrapper {max-height: 100% !important; top: 0}
<script src="https://bundle.run/object-hash-strict@2.0.1"></script>
<script src="https://bundle.run/lru-cache-ext@1.2.4"></script>

免责声明:我是 lru-cache-extobject-hash-strict

的作者

相关问答

错误1:Request method ‘DELETE‘ not supported 错误还原:...
错误1:启动docker镜像时报错:Error response from daemon:...
错误1:private field ‘xxx‘ is never assigned 按Alt...
报错如下,通过源不能下载,最后警告pip需升级版本 Requirem...