2つのファイルの内容が同じかチェックする

C#で内容を含めて2つのファイルの内容が同じかどうかをチェックする方法です。

処理の流れは、2つのファイルをファイルサイズで比較した後、内容を1バイトずつ比較しています。

FileStreamで1バイトづつ比較しているのでメモリ使用量が少なく比較的高速に動作します。逆に一度ファイルの中身を全部 string で読みだして比較するとかするとメモリは大量に使用するは動作は低速だで大きいファイルの内容を比較するにはこの方法が一番よさそうです。

確認環境

この記事は以下の環境で動作確認を行っています。

  • ViauslStudio 2019(16.10.4)
  • .NET Core 5 + C# 9.0

実装コード

さっそく実装コードの紹介です。

FileUtilクラス

FileUtil クラス内に static メソッドとして IsSameContents を定義しています。

using System;
using System.IO;

public static class FileUtil
{
    /// <summary>
    /// 指定した2つのファイルの内容が同じかを確認します。
    /// </summary>
    public static bool ContentsEqual(string path1, string path2)
    {
        if (path1 == path2)
        {
            return true;
        }

        FileStream fs1 = null;
        FileStream fs2 = null;
        try
        {
            fs1 = new FileStream(path1, FileMode.Open, FileAccess.Read, FileShare.ReadWrite);
            fs2 = new FileStream(path2, FileMode.Open, FileAccess.Read, FileShare.ReadWrite);

            if (fs1.Length != fs2.Length)
            {
                return false;
            }

            int file1byte;
            int file2byte;
            do
            {
                file1byte = fs1.ReadByte();
                file2byte = fs2.ReadByte();
            }
            while ((file1byte == file2byte) && (file1byte != -1));
            return (file1byte - file2byte) == 0;
        }
        finally
        {
            using (fs1)
            { }
            using (fs2)
            { }
        }
    }
}

使い方

上記の処理の使い方です。

特に難しい事はないです。メソッドに 2 つのファイルのファイルパスを引数に指定して結果を bool 値で確認します。

static void Main(string[] args)
{
    string file1 = "foo.txt";
    string file2 = "bat.txt";

    bool result = FileUtil.IsSameContents(file1, file2);
    // true: 同じ内容 / false: 異なる内容
}

参考

stackoverflow.com