12

編集:コードが期待どおりに機能するため、これを例に変更しました。

ファイルをコピーし、MD5ハッシュを取得してから、コピーを削除しようとしています。これは、別のアプリが書き込む元のファイルのプロセスロックを回避するために行っています。ただし、コピーしたファイルがロックされています。

File.Copy(pathSrc, pathDest, true);

String md5Result;
StringBuilder sb = new StringBuilder();
MD5 md5Hasher = MD5.Create();

using (FileStream fs = File.OpenRead(pathDest))
{
    foreach(Byte b in md5Hasher.ComputeHash(fs))
        sb.Append(b.ToString("x2").ToLower());
}

md5Result = sb.ToString();

File.Delete(pathDest);

次に、「プロセスがファイルにアクセスできません」という例外が発生しますFile.Delete()

このusingステートメントを使用すると、ファイルストリームが適切に閉じられると思います。また、ファイルストリームを個別に宣言し、削除し、using読み取り後に配置してみました。fs.Close()fs.Dispose()

この後、実際にmd5の計算をコメントアウトすると、ファイルが削除されてコードが実行されるため、と関係があるように見えますComputeHash(fs)

4

6 に答える 6

20

名前空間をインポートする

using System.Security.Cryptography;

これは、md5 ハッシュ コードを返す関数です。文字列をパラメーターとして渡す必要があります。

public static string GetMd5Hash(string input)
{
        MD5 md5Hash = MD5.Create();
        // Convert the input string to a byte array and compute the hash.
        byte[] data = md5Hash.ComputeHash(Encoding.UTF8.GetBytes(input));

        // Create a new Stringbuilder to collect the bytes
        // and create a string.
        StringBuilder sBuilder = new StringBuilder();

        // Loop through each byte of the hashed data 
        // and format each one as a hexadecimal string.
        for (int i = 0; i < data.Length; i++)
        {
            sBuilder.Append(data[i].ToString("x2"));
        }

        // Return the hexadecimal string.
        return sBuilder.ToString();
}
于 2012-12-10T17:39:55.143 に答える
15

あなたのコードをコンソールアプリに入れ、エラーなしで実行し、ハッシュを取得し、テストファイルは実行の最後に削除されましたか? テストアプリの .pdb をファイルとして使用しました。

実行している .NET のバージョンは何ですか?

ここで動作するコードを入れています。これを VS2008 .NET 3.5 sp1 のコンソール アプリに入れると、(少なくとも私にとっては) エラーなしで実行されます。

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Security.Cryptography;
using System.IO;

namespace lockTest
{
    class Program
    {
        static void Main(string[] args)
        {
            string hash = GetHash("lockTest.pdb");

            Console.WriteLine("Hash: {0}", hash);

            Console.ReadKey();
        }

        public static string GetHash(string pathSrc)
        {
            string pathDest = "copy_" + pathSrc;

            File.Copy(pathSrc, pathDest, true);

            String md5Result;
            StringBuilder sb = new StringBuilder();
            MD5 md5Hasher = MD5.Create();

            using (FileStream fs = File.OpenRead(pathDest))
            {
                foreach (Byte b in md5Hasher.ComputeHash(fs))
                    sb.Append(b.ToString("x2").ToLower());
            }

            md5Result = sb.ToString();

            File.Delete(pathDest);

            return md5Result;
        }
    }
}
于 2009-05-06T01:54:22.433 に答える
1

MD5オブジェクトをusing()でラップしてみましたか?ドキュメントから、MD5は使い捨てです。それはそれがファイルを手放すかもしれません。

于 2009-05-06T00:28:28.443 に答える
0

ループの後にmd5hasher.Clear()を使用すると、うまくいく可能性があります。

于 2009-05-06T01:38:52.110 に答える
-1

ファイルを削除する前にmd5Hasherをnullに設定してみましたか?おそらく、FileStreamにまだハンドルが接続されています(メモリリークが発生している可能性があります)。

于 2009-05-06T00:31:13.897 に答える
-1

FileShare.ReadWrite でファイルを開かないのはなぜですか?

于 2009-05-06T01:06:00.800 に答える