欢迎您访问程序员文章站本站旨在为大家提供分享程序员计算机编程知识!
您现在的位置是: 首页  >  IT编程

C#获取文件夹及文件的大小与占用空间的方法

程序员文章站 2024-02-21 13:11:46
本文详细介绍了利用c#实现根据路径,计算这个路径所占用的磁盘空间的方法 。 网上有很多资料都是获取文件夹/文件的大小的。对于占用空间的很少有完整的代码。这里介绍实现这一功...

本文详细介绍了利用c#实现根据路径,计算这个路径所占用的磁盘空间的方法 。

网上有很多资料都是获取文件夹/文件的大小的。对于占用空间的很少有完整的代码。这里介绍实现这一功能的完整代码,供大家参考一下。

首先说下文件夹/文件大小与占用空间的区别。

这个是硬盘分区格式有关 大小是文件的实际大小,而占用空间是占硬盘的实际空间 以fat32格式为例,硬盘的基本存储单位是簇,在fat32中一簇是4kb 那么,也就是说即使文件只有1个字节,在硬盘上也要占到4kb的空间 如果文件是4kb零1个字节,那就要占用8kb的空间,以此类推

结论: 大小是文件的实际大小,而占用空间是占硬盘的实际空间

那么问题来了。怎样获取本机的簇有多少字节呢?

首先可以通过windows api获取磁盘的相关信息。

//调用windows api获取磁盘空闲空间
//导入库
[dllimport("kernel32.dll", charset = charset.auto)]
static extern bool getdiskfreespace([marshalas(unmanagedtype.lptstr)]string rootpathname,
ref int sectorspercluster, ref int bytespersector, ref int numberoffreeclusters, ref int totalnumbeofclusters);

下面是具体代码:

/// <summary>
/// 获取指定路径的大小
/// </summary>
/// <param name="dirpath">路径</param>
/// <returns></returns>
public static long getdirectorylength(string dirpath)
{
long len = 0;
//判断该路径是否存在(是否为文件夹)
if (!directory.exists(dirpath))
{
//查询文件的大小
len = filesize(dirpath);
}
else
{
//定义一个directoryinfo对象
directoryinfo di = new directoryinfo(dirpath);

//通过getfiles方法,获取di目录中的所有文件的大小
foreach (fileinfo fi in di.getfiles())
{
len += fi.length;
}
//获取di中所有的文件夹,并存到一个新的对象数组中,以进行递归
directoryinfo[] dis = di.getdirectories();
if (dis.length > 0)
{
for (int i = 0; i < dis.length; i++)
{
len += getdirectorylength(dis[i].fullname);
}
}
}
return len;
}

/// <summary>
/// 获取指定路径的占用空间
/// </summary>
/// <param name="dirpath">路径</param>
/// <returns></returns>
public static long getdirectoryspace(string dirpath)
{
//返回值
long len = 0;
//判断该路径是否存在(是否为文件夹)
if (!directory.exists(dirpath))
{
//如果是文件,则调用
len = filespace(dirpath);
}
else
{
//定义一个directoryinfo对象
directoryinfo di = new directoryinfo(dirpath);
//本机的簇值
long clustersize = getclustersize(di);
//遍历目录下的文件,获取总占用空间
foreach (fileinfo fi in di.getfiles())
{
//文件大小除以簇,余若不为0
if (fi.length % clustersize != 0)
{
decimal res = fi.length / clustersize;
//文件大小除以簇,取整数加1。为该文件占用簇的值
int clu = convert.toint32(math.ceiling(res)) + 1;
long result = clustersize * clu;
len += result;
}
else
{
//余若为0,则占用空间等于文件大小
len += fi.length;
}
}
//获取di中所有的文件夹,并存到一个新的对象数组中,以进行递归
directoryinfo[] dis = di.getdirectories();
if (dis.length > 0)
{
for (int i = 0; i < dis.length; i++)
{
len += getdirectoryspace(dis[i].fullname);
}
}
}
return len;
}

//所给路径中所对应的文件大小
public static long filesize(string filepath)
{
//定义一个fileinfo对象,是指与filepath所指向的文件相关联,以获取其大小
fileinfo fileinfo = new fileinfo(filepath);
return fileinfo.length;
}

//所给路径中所对应的文件占用空间
public static long filespace(string filepath)
{
long temp = 0;
//定义一个fileinfo对象,是指与filepath所指向的文件相关联,以获取其大小
fileinfo fileinfo = new fileinfo(filepath);
long clustersize = getclustersize(fileinfo);
if (fileinfo.length % clustersize != 0)
{
decimal res = fileinfo.length / clustersize;
int clu = convert.toint32(math.ceiling(res)) + 1;
temp = clustersize * clu;
}
else
{
return fileinfo.length;
}
return temp;
}

public static diskinfo getdiskinfo(string rootpathname)
{
diskinfo diskinfo = new diskinfo();
int sectorspercluster = 0, bytespersector = 0, numberoffreeclusters = 0, totalnumberofclusters = 0;
getdiskfreespace(rootpathname, ref sectorspercluster, ref bytespersector, ref numberoffreeclusters, ref totalnumberofclusters);

//每簇的扇区数
diskinfo.sectorspercluster = sectorspercluster;
//每扇区字节
diskinfo.bytespersector = bytespersector;

return diskinfo;
}

//// <summary>
/// 结构。硬盘信息
/// </summary>
public struct diskinfo
{
public string rootpathname;
//每簇的扇区数
public int sectorspercluster;
//每扇区字节
public int bytespersector;
public int numberoffreeclusters;
public int totalnumberofclusters;
}
/// <summary>
/// 获取每簇的字节
/// </summary>
/// <param name="file">指定文件</param>
/// <returns></returns>
public static long getclustersize(fileinfo file)
{
long clustersize = 0;
diskinfo diskinfo = new diskinfo();
diskinfo = getdiskinfo(file.directory.root.fullname);
clustersize = (diskinfo.bytespersector * diskinfo.sectorspercluster);
return clustersize;
}

/// <summary>
/// 获取每簇的字节
/// </summary>
/// <param name="dir">指定目录</param>
/// <returns></returns>
public static long getclustersize(directoryinfo dir)
{
long clustersize = 0;
diskinfo diskinfo = new diskinfo();
diskinfo = getdiskinfo(dir.root.fullname);
clustersize = (diskinfo.bytespersector * diskinfo.sectorspercluster);
return clustersize;
}