1、加载文件后,删除文件时提示如下
文件“..jpg”正由另一进程使用,因此该进程无法访问此文件。
背景
C# 中使用Image.FromFile(string path) 并使用 System.IO.File.Delete(string path) 后提示该文件正在被另一进程使用XXX的问题,是因为对应的文件在一直使用中 ,其生成的 Image 对象被 Disponse() 前都不会被解除锁定,这就造成了此问题,就是在这个图形被解锁前无法对图像进行操作(比如删除,修改等操作)。
解决方案
方法1:如果 Image 对象不需要保存在程序内存中,可以在进行删除、修改等操作之前将 Image 对象销毁
System.Drawing.Image image = System.Drawing.Image.FromFile(filePath);
System.Drawing.Bitmap bmp = new System.Drawing.Bitmap(image);
image.Dispose();
方法2:如果 Image 对象需要保存在程序内存中,将从文件加载的 Image 绘制到程序内存中的 Image 上,然后将 从文件加载的 Image 对象销毁。
System.Drawing.Image img = System.Drawing.Image.FromFile(filepath);
System.Drawing.Image bmp = new System.Drawing.Bitmap(img.Width, img.Height, img.PixelFormat);
System.Drawing.Graphics g = System.Drawing.Graphics.FromImage(bmp);
g.DrawImage(img, 0, 0);
g.Flush();
g.Dispose();
img.Dispose();
方法3:以文件流的形式加载文件,加载完后关闭文件,然后将文件流转换成 Image 对象
System.IO.FileStream fs = new System.IO.FileStream(filePath, FileMode.Open, FileAccess.Read);
int byteLength = (int)fs.Length;
byte[] fileBytes = new byte[byteLength];
fs.Read(fileBytes, 0, byteLength);
//文件流关閉,文件解除锁定
fs.Close();
MemoryStream mStream = new MemoryStream(fileBytes);
Image image = Image.FromStream(mStream);
因为 FromStream 方法参数应用的流必须一直保持打开,故而代码中有一个文件流是向MemeoryStream流的转换,从而可以关闭文件流,保持 MemoryStream 流的打开状态。在不用 mStream 时关闭。
mStream.Close();
2、文件被占用强制删除类
public void WipeFile(string filename, int timesToWrite)
{
try
{
if (System.IO. File.Exists(filename))
{
//设置文件的属性为正常,这是为了防止文件是只读
System.IO.File.SetAttributes(filename, System.IO.FileAttributes.Normal);
//计算扇区数目
double sectors = Math.Ceiling(new System.IO.FileInfo(filename).Length / 512.0);
// 创建一个同样大小的虚拟缓存
byte[] dummyBuffer = new byte[512];
// 创建一个加密随机数目生成器
System.Security.Cryptography.RNGCryptoServiceProvider rng = new System.Security.Cryptography.RNGCryptoServiceProvider();
// 打开这个文件的FileStream
System.IO.FileStream inputStream = new System.IO.FileStream(filename, System.IO.FileMode.Open, System.IO.FileAccess.Write, System.IO.FileShare.ReadWrite);
for (int currentPass = 0; currentPass < timesToWrite; currentPass++)
{
// 文件流位置
inputStream.Position = 0;
//循环所有的扇区
for (int sectorsWritten = 0; sectorsWritten < sectors; sectorsWritten++)
{
//把垃圾数据填充到流中
rng.GetBytes(dummyBuffer);
// 写入文件流中
inputStream.Write(dummyBuffer, 0, dummyBuffer.Length);
}
}
// 清空文件
inputStream.SetLength(0);
// 关闭文件流
inputStream.Close();
// 清空原始日期需要
DateTime dt = new DateTime(2037, 1, 1, 0, 0, 0);
System.IO.File.SetCreationTime(filename, dt);
System.IO.File.SetLastAccessTime(filename, dt);
System.IO.File.SetLastWriteTime(filename, dt);
// 删除文件
System.IO.File.Delete(filename);
}
}
catch (Exception)
{
}
}
3、文件被另一进程占用
Download Handle (418 KB)
string fileName = @"c:\aaa.doc";//要检查被那个进程占用的文件
Process tool = new Process();
tool.StartInfo.FileName = "handle.exe";//占用文件的进程
tool.StartInfo.Arguments = fileName+" /accepteula";
tool.StartInfo.UseShellExecute = false;
tool.StartInfo.RedirectStandardOutput = true;
tool.Start();
tool.WaitForExit();
string outputTool = tool.StandardOutput.ReadToEnd();
string matchPattern = @"(?<=\s+pid:\s+)\b(\d+)\b(?=\s+)";
foreach(Match match in Regex.Matches(outputTool, matchPattern))
{
Process.GetProcessById(int.Parse(match.Value)).Kill();
}