相关值网络-如何仅重新计算一次?

| 我希望你们中的一个能弄清楚这一点。 我有一个包含很多对象的数组。数组中的每个对象都包含两件事: 可以更改的值。 数组中零个或多个其他对象的列表,如果它们的值更改,则此对象需要重新计算其值。这可以在对象之间多次层叠,但是没有依赖关系的循环。 我相信这称为网络(就像一棵树,但有多个父级)。具体来说,这是有向无环图。 我现在正在做的是这样:当我更改对象的值时,我检查数组中的每个对象以查看其是否取决于我刚刚更改的对象。如果是这样,那么我告诉该子对象重新计算。然后,孩子以相同的方式告诉孩子,依此类推。 此方法可以正常工作(值会正确更新),但是当进行更改时,它的速度会非常之慢(非常宽泛)。这是因为如果一个对象有许多更改的父对象,则它会为每个对象重新计算一次,并且还告诉它的孩子每次都重新计算,因此它们仅从一个父对象那里收到几条消息。这迅速滚雪球,直到许多对象重新计算数十次为止。 在所有对象的父母都重新计算之后,只重新计算每个对象一次的最佳方法是什么? 谢谢你的帮助。     
已邀请:
        听起来您想要有向无环图的拓扑排序。参见例如http://www.csse.monash.edu.au/~lloyd/tildeAlgDS/Graph/DAG/ 如果您的图形不是一直在变化,那么您应该可以对其进行一次简单排序,然后您就可以按照从左到右的顺序执行更新,知道在每一步中您将添加到列表中的节点集。被计算的都在当前位置的右边。有几种方法可以优化它,例如将它们存储在一个简单的堆中,每次选择最左边的值,重新计算它并添加回它引用的任何节点,或者按照其他人的建议(如果完整的依赖图是)足够小,只需按照需要对其进行计算的顺序将其存储在每个节点上(使用拓扑排序即可找到)。     
        每当
i
的变化需要re2ѭ的重新计算时(即
i
在对象
j
的列表中),创建一个非循环有向图,其顶点由数组中的节点给出,并且边为
i --> j
。该图是非循环的,前提是您的过程是有限的。 现在,当ѭ1改变时,先进行广度搜索以重新计算从属节点。在第一遍,收集所有节点
j
,使
i --> j
。重新计算那些
j
。在第二遍,取每个变化的
j
并得到其附属物
j --> k
。然后立即重新计算那些
k
。继续处理所有已更改的ѭ11的依存者,依此类推,直到只有叶子为止。 这要求您保留邻居列表,这是您所拥有信息的反面。因此,您需要进行一次通过才能获得有向边(填充数组,以使条目
i
具有所有
j
的数组,而
j
对应于数组
i --> j
)。     
        更新值时,创建其值仍需要重新计算的其他元素的列表。在重新计算此列表中元素的值之前,请确保该列表所依赖的其他元素均不在列表中。这将确保元素仅被重新计算一次。由于没有循环依存关系,因此在要重新计算的元素列表中始终至少有一个元素已经被重新计算了所有从属元素。 伪代码:
Create a set S 
Add initially updated element to S
while S is not empty
    remove an element X from S whose value does not depend on any other elements in E do not exist in S
    recalculate X\'s value and add any elements that depend on X\'s value to S
    

要回复问题请先登录注册