用过Linux操作系统的人,都知道有du这么一个命令,可以很方便的列出当前文件夹内子目录及子文件的大小。
然而在Windows系统,则无类似工具,若需查看某文件夹下哪个子文件夹最大,包含文件最多,着实是一件头疼的事。不借助工具恐怕只能右击一个个的子文件夹查看其属性后,再做比较。
我在学习《Java编程思想》 io章节的时候学习到用递归法计算出某文件夹的大小,在原代码基础上进行修改,开发出一个非常实用的小工具,可以方便的列出某文件夹下所有子文件夹及文件的大小及其数量,不仅如此,稍加扩展还能得到您想要的其他信息,我只在此抛砖引玉。附上运行结果图:
说明:
1. df实际对应df.bat,将其加入path后在cmd窗口可以直接输入,df.bat内容如下:
@echo off
java -cp ".;xxx" comm.df %1
2. df后不加参数,则是列出当前目录的文件信息;若加路径参数,在列出目标路径下文件的信息。
是不是很方便呢 ^_^。
闲言少叙,最后贴上代码:
df.java
package comm;
import java.io.File;
import java.util.ArrayList;
import java.util.Formatter;
import java.util.Iterator;
import java.util.List;
public class df {
static Formatter f = new Formatter(System.out);
static String strF = "%-10s%7s %11s %10s %-20s\n";
static class Node{
String fileName;
String permission;
TreeInfo treeInfo;
private Node(String fileName, String permission, TreeInfo treeInfo) {
this.fileName = fileName;
this.permission = permission;
this.treeInfo = treeInfo;
}
}
private static class TreeInfo implements Iterable<File>{
public List<File> files = new ArrayList<File>();
public List<File> dirs = new ArrayList<File>();
public List<File> unReachables = new ArrayList<File>();
public long size = 0;
@Override
public Iterator<File> iterator() {
return files.iterator();
}
void addAll(TreeInfo other){
files.addAll(other.files);
dirs.addAll(other.dirs);
unReachables.addAll(other.unReachables);
size += other.size;
}
}
public static TreeInfo recurseDirs(File startDir, String regex){
TreeInfo result = new TreeInfo();
if(startDir.isDirectory()){
File[] files = startDir.listFiles();
if(files != null){
for(File item : files){
if(!item.canRead()) {
result.unReachables.add(item);
continue;
}
if(item.isDirectory()){
result.dirs.add(item);
result.addAll(recurseDirs(item, regex));
}else{
if(!item.canRead()) {
result.unReachables.add(item);
continue;
}
if(item.getName().matches(regex)){
result.files.add(item);
result.size += item.length();
}
}
}
}else{
result.unReachables.add(startDir);
}
}else{
if(startDir.canRead()){
if(startDir.getName().matches(regex)){
result.files.add(startDir);
result.size += startDir.length();
}
}else{
result.unReachables.add(startDir);
}
}
return result;
}
public static TreeInfo walk(String start){
return recurseDirs(new File(start), ".*");
}
public static TreeInfo walk(File start){
return recurseDirs(start, ".*");
}
public static String getPermission(File file){
String d = file.isDirectory() ? "d" : "-";
String r = file.canRead() ? "r" : "-";
String w = file.canWrite() ? "w" : "-";
String x = file.canExecute() ? "x" : "-";
return d + r + w + x;
}
public static void printTitle(){
f.format(strF, "Permission", "Size", "FileCount", "DirCount", "FileName");
f.format("--------------------------------------------------------------\n");
}
public static void printSingleLine(Node node){
f.format(strF, node.permission, showSize(node.treeInfo.size), node.treeInfo.files.size(), node.treeInfo.dirs.size(), node.fileName);
}
private static void printTail() {
f.format("--------------------------------------------------------------\n");
}
public static String showSize(long size){
String result = "";
if(size / 1024 >= 1){
if(size / 1024 / 1024 < 1){
result = String.format("%.2fK", 1.0 * size / 1024);
}else if(size / 1024 /1024 >= 1 && size / 1024 / 1024 / 1024 < 1){
result = String.format("%.2fM", 1.0 * size / 1024 / 1024);
}else{
result = String.format("%.2fG", 1.0 * size / 1024 / 1024 / 1024);
}
}else{
result = String.format("%dB", size);
}
return result;
}
public static void main(String[] args) {
long start = System.currentTimeMillis();
String dir = ".";
if(args.length == 1){
dir = args[0];
}
int fileCnt = 0, dirCnt = 0;
long totalSize = 0;
File topFile = new File(dir);
printTitle();
for(File file : topFile.listFiles()){
Node node = new Node(file.getName(), getPermission(file), walk(file));
printSingleLine(node);
fileCnt += node.treeInfo.files.size();
dirCnt += node.treeInfo.dirs.size();
if(node.permission.startsWith("d"))dirCnt += 1;
totalSize += node.treeInfo.size;
}
printTail();
long end = System.currentTimeMillis();
System.out.println(String.format("%s has %d dirs, %d files, total %s.\n"
+ "Takes %.2f seconds.", topFile.getAbsoluteFile(), dirCnt, fileCnt, showSize(totalSize),
(end - start)/1000.0));
}
}