为什么这不能正确计算文件夹的总大小?

时间:2015-01-31 22:15:11

标签: java

以下是两个java类:

package je3.io;

import java.io.File;
import java.util.ArrayList;
import java.util.List;

/**
 * Created by IDEA on 31/01/15.
 */
public class DirWalker {
    private List<File> recursiveList = new ArrayList<File>();

    public void walkDir(String pathname) {
        File d = new File(pathname);
        recursiveList.add(d);
        if(d.isDirectory()) {
            for(String f : d.list()) {
                walkDir(f);
            }
        }
    }

    public void reset() {
        recursiveList.clear();
    }

    public List<File> getRecursiveList() {
        return recursiveList;
    }

    public static void main(String[] args) {
        DirWalker dirWalker = new DirWalker();
        dirWalker.walkDir("/tmp");
        dirWalker.getRecursiveList().forEach(System.out::println);
    }
}

package je3.io;

import java.io.File;

/**
 * Created by IDEA on 31/01/15.
 */
public class DirSummariser {
    private DirWalker dirWalker = new DirWalker();
    private long dirSize = 0;

    public DirSummariser(String pathname) {
        dirWalker.reset();
        dirWalker.walkDir(pathname);
    }

    public DirSummariser(File file) {
        this(file.getAbsolutePath());
    }

    public long calculateDirSize() {
        for(File f : dirWalker.getRecursiveList()) {
            dirSize += f.length();
        }
        return dirSize;
    }

    public static void main(String[] args) {
        DirSummariser dirSummariser = new DirSummariser("/Users/hualin/Downloads/pdf");
        System.out.println(dirSummariser.calculateDirSize());
    }
}

在第二节课的主要方法中,我试图计算pdf文件夹的总大小,大小应该在30MB左右。 java程序编译时没有错误,但是说文件夹的大小只有1600字节。

2 个答案:

答案 0 :(得分:3)

问题出在DirWalker

public void walkDir(String pathname) {
    File d = new File(pathname);
    recursiveList.add(d);
    if(d.isDirectory()) {
        for(String f : d.list()) {  // <-- here
            walkDir(f);             // <--
        }
    }
}

d.list()返回的字符串只是文件名,没有附加路径。例如,如果您找到文件some_directory/foo.txt,则您将从列表中删除的字符串为foo.txt,并且由于foo.txt不在当前工作目录中,因此{{你从它构造的对象将是无效的(或描述不同的文件)。

你必须设置你试图检查部分递归的路径才能使其正常工作,例如:

File

或者,正如@Adam在评论中提到的那样,通过将描述父目录的 walkDir(pathname + File.separator + f); 对象传递到递归并使用File构造函数,如

File(parent, child)

注意:这个答案,我认为应该提到,是针对OP的练习用例而量身定做的,所以我主要试图解释为什么他的代码不起作用并提出方法让它起作用。如果您将来成为一名流浪访问者并寻找通过Java浏览目录的方法,请查看@ fge的答案以获得更好的方法。

答案 1 :(得分:2)

使用java.nio.file API,它可以做得更好。

以下是一个示例,也使用throwing-lambdas,以递归方式计算目录中所有文件的总大小:

final Path theDirectory = Paths.get("path/to/your/directory");

final long totalSize = Files.walk(theDirectory)
    .filter(Files::isRegularFile)
    .mapToLong(Functions.rethrow(Files::size))
    .sum();

如果您没有Java 8,请使用Files.walkFileTree()