任务是从排序路径列表中创建一个树。每个节点都是一个文件系统对象(文件或文件夹) 目前我正在使用这个(伪代码):
foreach(string path in pathList)
{
INode currentNode = rootNode;
StringCollection pathTokens = path.split(pathSplitter);
foreach(pathToken in pathTokens)
{
if (currentNode.Children.contains(pathToken ))
{
currentNode = currentNode.Children.find(pathToken);
}
else
{
currentNode = currentNode.Children.Add(pathToken);
}
}
}
pathSplitter
获胜为\
,* nix为/
有没有更有效的方法来解决这个任务?
答案 0 :(得分:2)
输入数据的关键质量是路径列表排序。因此,您可以非常有效地使用当前节点和先前节点之间的公共前缀。你可以做的是从叶根文件夹节点的根目录中通过树数据结构保留最后的 trace 。然后对于当前路径,您只需遍历上一个跟踪(即处理相对于最后一个路径的当前路径),而不是一次又一次地在树中找到正确的位置。
比较最后和当前路径时,可能会发生以下三种情况:
\path\to\folder\file1.txt
\path\to\folder\file2.txt
跟踪仍然存在,file2.txt
的节点已添加。
\path\to\folder\file1.txt
\path\to\folder\subfolder\file2.txt
添加了subfolder
和file2.txt
的节点。
\path\to\folder\file1.txt
\path\to\another_folder\subfolder\file2.txt
首先,您需要回溯跟踪以表示\path\to\
。然后,添加another_path
,subfolder
和file2.txt
的节点。 (请注意,another_folder\subfolder\
部分可能完全丢失 - 我希望它很清楚。)
根据数据的整体特征和数量,此类算法可能会执行得更快。你可以玩一些正式的Big-O估计,但我认为测试它会更快。
答案 1 :(得分:1)
算法对我来说似乎是最优的;如果我没有弄错的话,路径的排序意味着节点将相对于它们所源自的树以深度优先顺序生成。这意味着图中不会执行不必要的回溯。此外,该算法在输入中的路径数量是线性的,并且每个路径在其长度上按时间线性处理,因此总体运行时间在输入的大小上是线性的。复杂性方面,这意味着算法是最优的,因为不可能读取运行时复杂度较低的所有路径。