目录文件大小计算 - 如何使其更快?

Jey*_*han 19 c# windows winapi filesystemobject winforms

使用C#,我找到了目录的总大小.逻辑是这样的:获取文件夹中的文件.总结总大小.查找是否有子目录.然后进行递归搜索.

我也尝试了另一种方法:使用FSO(obj.GetFolder(path).Size).这两种方法的时间差别不大.

现在的问题是,我在一个特定的文件夹中有成千上万的文件,它至少需要2分钟才能找到文件夹大小.此外,如果我再次运行程序,它会很快发生(5秒).我认为窗口正在缓存文件大小.

有什么方法可以减少我第一次运行程序时所花的时间吗?

spo*_*der 34

如果摆弄它一段时间,尝试并行化它,并且令人惊讶 - 它在我的机器上加速(在四核上最多3次),不知道它是否在所有情况下都有效,但试一试. ..

.NET4.0代码(或使用3.5与TaskParallelLibrary)

    private static long DirSize(string sourceDir, bool recurse)
    {
        long size = 0;
        string[] fileEntries = Directory.GetFiles(sourceDir);

        foreach (string fileName in fileEntries)
        {
            Interlocked.Add(ref size, (new FileInfo(fileName)).Length);
        }

        if (recurse)
        {
            string[] subdirEntries = Directory.GetDirectories(sourceDir);

            Parallel.For<long>(0, subdirEntries.Length, () => 0, (i, loop, subtotal) =>
            {
                if ((File.GetAttributes(subdirEntries[i]) & FileAttributes.ReparsePoint) != FileAttributes.ReparsePoint)
                {
                    subtotal += DirSize(subdirEntries[i], true);
                    return subtotal;
                }
                return 0;
            },
                (x) => Interlocked.Add(ref size, x)
            );
        }
        return size;
    }
Run Code Online (Sandbox Code Playgroud)

  • 你能解释为什么你检查了ReparsePoint吗?因为如果我评论线速度增加超过5倍. (3认同)
  • @AFgone因为在我的意见中,重新分析点不是真正的文件.MSDN:"该文件包含一个重新分析点,它是一个与文件或目录关联的用户定义数据块." 但一如既往,这取决于您的需求和要求. (2认同)

stu*_*uck 10

硬盘是一个有趣的野兽 - 顺序访问(例如读取一个大的连续文件)是超级活泼的,图80兆字节/秒.但是随机访问非常慢.这就是你要碰到的东西 - 递归到文件夹中不会读取太多(就数量而言)数据,但需要许多随机读取.你第二次看到zippy perf的原因是因为MFT仍然在RAM中(你在缓存思想上是正确的)

我见过的最好的机制是自己扫描MFT.我们的想法是,您可以在一个线性传递中阅读和解析MFT,从而构建您需要的信息.对于非常饱满的高清,最终结果将更接近15秒.

一些好的阅读:NTFSInfo.exe - http://technet.microsoft.com/en-us/sysinternals/bb897424.aspx Windows Internals - http://www.amazon.com/Windows%C2%AE-Internals-Including- Windows的PRO-开发商/ DP/0735625301/REF = sr_1_1?IE = UTF8&S =书籍和QID = 1277085832&SR = 8-1

FWIW:这个方法非常复杂,因为在Windows(或我所知道的任何操作系统)中确实没有很好的方法可以做到这一点 - 问题是确定需要哪些文件夹/文件的行为需要很多头磁盘上的移动.微软很难为你描述的问题建立一个通用的解决方案.


Eva*_*van 7

最简洁的答案是不.Windows可以使目录大小计算更快的方式是更新每个文件写入的目录大小和所有父目录大小.但是,这会使文件写入操作变慢.由于文件写入比读取目录大小更常见,因此这是一个合理的权衡.

我不确定究竟是什么问题正在解决,但如果是文件系统监控则可能值得一试:http://msdn.microsoft.com/en-us/library/system.io.filesystemwatcher.aspx