如何管理原始对象之间的数据依赖关系



考虑以下情况:

items = [
  {
    id: 1
    attributes: [
      { key: a, value: 2 }
      { key: b, value: 3 }
    ],
    requirements: null
  }
  {
    id: 2
    attributes: [
      { key: b, value: 2 }
    ],
    requirements: a > 2
  }
  {
    id: 3
    attributes: [
      { key: a, value: 1 }
      { key: c, value: 1 }
    ],
    requirements: a > 1 and b > 2
  }
  {
    id: 4
    attributes: [
      { key: a, value: 2 }
      { key: d, value: 7 }
    ],
    requirements: b > 5 and h < 10
  }
]

将各种attributes加在一起(求和)的预期结果是:

result = [
  { key: a, value: 3 }
  { key: b, value: 5 }
  { key: c, value: 1 }
]

正如您所观察到的,列表中的对象之间存在依赖关系(requirements)。特别地,具有id: 4的对象(序列的最后一个)从计算中被丢弃,因为从未检查条件b > 5 and h < 10。相反,具有id: 2的对象最初被丢弃,然后作为具有id: 3的对象的结果落在计算中(通过将属性a加1,使得条件a > 2成立)。

需要什么算法才能获得具有N个对象的所需结果

免责声明:拟议结构只是一个例子。你可以提出任何你认为可以实现结果的改变。我正在使用JavaScript(CoffeeScript)编程语言,但其他任何语言都可以

让我们从可以使用的格式获取数据开始。我们需要能够随意测试需求,而不是只在数据对象实例化时测试:

  {
    id: 4
    attributes: [
      { key: a, value: 2 }
      { key: d, value: 7 }
    ],
    requirements: (sum) -> sum.b > 5 and sum.h < 10
  }

当我们在做这件事的时候,让我们让属性处于一个更有用的状态(注意,这不是绝对必要的,但会让一切变得更简单):

  {
    id: 4
    attributes: {
      a: 2
      d: 7
    },
    requirements: (sum) -> sum.b > 5 and sum.h < 10
  }

现在,我将介绍天真的算法,它是最简单的,应该适合您的需求。从本质上讲,我们将继续在数据集上循环,测试每个尚未使用的数据集,如果通过,则将其添加到总和中。

changed = true
sum = {}
init(sum, items)
while changed
    changed = false
    for item in items
        if !item.used && item.requirements(sum)
            add(sum, item.attributes)
            changed = true
            item.used = true

我将让您填写addinit函数。add应该是简单的;它将第二参数中的每个元素添加到第一参数中的每一个元素。CCD_ 12需要设置CCD_ 13中可以用于(测试或添加到)CCD_ 14的每个元素。

最新更新