这个问题更多的是关于一个有效的算法而不是实现,所以我不会发布代码。 (不会真的帮助你理解这个问题)
向您介绍以下问题: 我正在开发一个程序来计算automovilistics崩溃报告。它为您提供了一系列" 方程式" ( Eq 从现在开始,Eqs为复数形式),您可以在其中输入数据并获得n个结果。
例如:你选择空间覆盖(x),其中和输入时间(t),aceleration(a)和初始速度(v),然后x =(a * t)+((a * t ^ 2)/ 2)。 事情就是这个Eqs在一个对象里面,它包含了很多东西而不是变量本身,我们称之为 Bo (我正在谈论的busssines对象。< / p>
所以BO非常大(并且需要),除了其他东西之外,1 Bo可以有N个Eqs,并且不止一个结果,每个Eq都可以将值范围作为输入,这会让你得到好吧...(假设你只能使用2个变量的范围,实际上这不受限制)所以你将得到每个结果的结果表(一些Bos有4个不同的结果)。范围的Te步骤上限为20个第一范围,10秒范围。 (在Bo中有4个结果,可以映射800个结果为1 Bo)。
顺便说一下,我必须存储(保存在文件中)这个Bos及其各自的结果,并且Var imputs每次都不能在运行时计算它们(我可以保存ecuations,并且var imputs and calculate每次我需要它们的结果),因为Bos可以改变效果,并且用户需要保持优势结果,不要问......
此外,您可以将Bo的一个结果导入另一个Bo的Eq输入。 所以在前面的例子中(让我们称之为Bo1),aceleration可能来自另一个计算它的Bo(Bo2),并且需要其他参数来计算它,如果你改变了Bo2的输入,结果会改变,所以至少1 bo1的变量将改变,使得Bo1的结果发生变化。这可以级联(B2从B3导入,依此类推)。并且一个Bo可以从其他N个Bos中导入所有N个变量。
我不能使用指针或引用类型(也许可以使用引用类型,无论如何,这将是很多工作,必须使用来自不同用户的先前保存的数据,并且对象缺少引用等)。 / p>
我决定只使用一组数组,在每个数组中存储,{Id_of_Bo_Exporting,Id_Bo_importing,Id_Variable_of_Bo_Importing,...(用于映射特定结果导出的ohters id)}数组为int(前2个长)
我不是很喜欢它,但代码工作得很好。 (感谢阅读)问题是我的继承人的儿子。
问题是,我必须检查圆周进口,如果B3从B2进口B2和B2进口,我不允许从B3(或B2)进口Bo1。这将导致无限循环,(我可以停止循环但不是数学视图中的逻辑以允许导入)。
和导入列表,最终可能很长,
我想要一个ArrayList&lt;的ArrayList&LT;长&GT;&GT;所以每次我添加一个导入我都会在这个东西上添加ID#34;我不喜欢。 (arraylist的araylist)
每个数组的长数将在第一个位置上有#34; Bo id标题&#34;,每次Bo导入时,新的Id在其列表中添加,AND每个其他Bo导入Bo(一个makin the import)。
因此,如果我的用户试图从B1制作B9,该方法将检测到,B1将被添加到自己的列表中并且不允许。
实施起来非常简单。 (让我们使用java,不,我使用.net,自己没有启动这个项目)
示例 {{}}
从B2进口B1: {的 {B1,B2} }
B1从B6进口: {{B1,B2,的 B6 }}
B2从B4进口: {{B1,B2,B6,的 B4 }, {B2,B4} }
B4从B9进口: {{B1,B2,B3,B4,的 B9 },{B2,B4,的 B9 }, {B4,B9 }}
从B10进口B3: {{B1,B2,B3,B4,B9,的 B10 },{B2,B4,B9},{B4,B9}的 {B3,B10} } < / p>
每个数组的长数将在第一个位置上有#34; Bo id标题&#34;,每次Bo导入时,新的Id在其列表中添加,AND每个其他Bo导入Bo(一个makin the import)。
因此,如果我的用户试图从B1制作B9,该方法将检测到,B1将被添加到自己的列表中并且不允许。
实施起来非常简单。 (让我们使用java,不,我使用.net,自己没有启动这个项目)
private boolean checkCircularity(long ida,long idb){
//ida importing, idb exporting
// asume List is public and called iL
// Clone il to restore it in case}
for (int i = 0 ; i < iL.size() ;i++)
// Each arraylist of long in the big array iL
{
// I would use some kind of SetUniqueList, dont know in c#
// but i could check it if needed and add it if it doesnt exist
if (iL.get(i).contains(ida))
{
if (((iL.get(i)).get(0)) == idb)
{// Circiut, breaks for's restore the original list and returns false
}
else{
if (!iL.get(i).contains(idb)) {iL.get(i).add(idb);}
}
}
} return true; }
现在问题(使用ListSet或其他任何东西)你能想到一个更有效的方法吗? 两个列表(导入和iL可以非常快地取决于用户)。 标题是速度。
答案 0 :(得分:0)
如果我正确理解了这个问题,那么检查'循环'实际上是图表中循环检测的一个例子。换句话说,如果每个“导入”都被建模为有向图边,那么您就是在尝试检测一个循环。
如果这是正确的,那么这是一个很好理解的问题。我建议将导入建模为直接节点参考,然后使用其中一种标准算法来检测周期,请参阅Cycle Detection。