はじめに なぜ「ファイルサイズ取得」が業務で重要なのか
業務システムでは、「受信したファイルが想定サイズ以上かチェックする」「空ファイル(サイズ 0)をエラーとして弾く」「バックアップやログの容量を集計してディスク使用量を監視する」など、ファイルサイズを扱う場面がとても多いです。
サイズを見ずに処理すると、「中身が入っていないファイルをそのまま取り込んでしまう」「巨大ファイルを読み込んでメモリを圧迫する」といったトラブルにつながります。
C# では、System.IO.FileInfo クラスを使うことで、ファイルサイズを簡単かつ安全に取得できます。
ここでは、プログラミング初心者向けに、基本の使い方から、業務で使えるユーティリティ化、サイズの単位変換や合計サイズの計算まで、かみ砕いて解説していきます。
基本のメソッド FileInfo.Length でファイルサイズを取得する
最もシンプルなファイルサイズ取得
まずは、「特定のファイルのサイズをバイト単位で取得する」一番シンプルな例から見てみましょう。
using System;
using System.IO;
class Program
{
static void Main()
{
string path = @"C:\data\report.csv";
FileInfo info = new FileInfo(path);
long size = info.Length;
Console.WriteLine($"ファイルサイズ: {size} バイト");
}
}
C#ここで重要なのは、サイズの型が long であることです。
ファイルサイズはかなり大きくなる可能性があるため、int ではなく 64 ビット整数の long で扱います。FileInfo.Length は「ファイルのサイズ(バイト数)」をそのまま返してくれるプロパティです。
また、FileInfo を使うためには、using System.IO; を書いておく必要があります。
ファイル・ディレクトリ操作をするときは、まず using System.IO; と書く、というのをセットで覚えておくと楽です。
ファイルが存在しない場合の扱い
存在しないパスで new FileInfo(path) をしても、その時点では例外は出ません。
しかし、info.Length にアクセスしたタイミングで、ファイルが存在しないと FileNotFoundException が発生します。
業務コードでは、「存在チェック」と「サイズ取得」をセットで行うことが多いです。
using System;
using System.IO;
class Program
{
static void Main()
{
string path = @"C:\data\report.csv";
if (!File.Exists(path))
{
Console.WriteLine("ファイルが存在しません。");
return;
}
FileInfo info = new FileInfo(path);
long size = info.Length;
Console.WriteLine($"ファイルサイズ: {size} バイト");
}
}
C#このようにしておくと、「そもそもファイルがない」というケースを、サイズ取得とは別に扱えます。
実務で使えるユーティリティ化 単体ファイルのサイズ取得
安全にサイズを取得するユーティリティメソッド
毎回 File.Exists と new FileInfo を書くのは面倒なので、「安全にサイズを取得する」ユーティリティメソッドを用意しておくと便利です。
using System;
using System.IO;
public static class FileSizeUtil
{
public static long GetFileSize(string filePath)
{
if (!File.Exists(filePath))
{
throw new FileNotFoundException($"ファイルが見つかりません: {filePath}", filePath);
}
FileInfo info = new FileInfo(filePath);
return info.Length;
}
}
C#使い方の例は次の通りです。
class Program
{
static void Main()
{
string path = @"C:\data\report.csv";
try
{
long size = FileSizeUtil.GetFileSize(path);
Console.WriteLine($"ファイルサイズ: {size} バイト");
}
catch (FileNotFoundException ex)
{
Console.WriteLine("エラー: " + ex.Message);
}
}
}
C#ここでのポイントは、「存在しない場合は 0 を返す」のではなく、「例外として扱う」設計にしていることです。
業務によっては、「ファイルがないのは異常」とみなすことが多く、その場合は例外で止めたほうがバグに気づきやすくなります。
「存在しないなら 0」を返すバージョン
一方で、「存在しなければサイズ 0 として扱いたい」というケースもあります。
その場合は、戻り値で表現するユーティリティを用意します。
public static class FileSizeUtil
{
public static long GetFileSizeOrZero(string filePath)
{
if (!File.Exists(filePath))
{
return 0;
}
FileInfo info = new FileInfo(filePath);
return info.Length;
}
}
C#このように、「例外で止めるか」「0 で返すか」をメソッドごとに分けておくと、呼び出し側の意図が明確になります。
サイズの単位変換 バイトから KB・MB・GB へ
バイトのままだと人間には分かりにくい
FileInfo.Length はバイト単位ですが、人間が見るには「何 MB くらいか」のほうが直感的です。
そこで、バイト数を KB・MB・GB に変換するユーティリティを用意しておくと便利です。
一般的には、次のような換算を使います。
1 KB = 1024 バイト
1 MB = 1024 KB = 1024 × 1024 バイト
1 GB = 1024 MB = 1024 × 1024 × 1024 バイト
シンプルな変換メソッド
まずは、「バイト数から MB を求める」シンプルな例です。
public static class FileSizeUtil
{
public static double ToMegaBytes(long bytes)
{
return bytes / 1024.0 / 1024.0;
}
}
C#使い方の例は次の通りです。
class Program
{
static void Main()
{
string path = @"C:\data\bigfile.bin";
long size = FileSizeUtil.GetFileSize(path);
double mb = FileSizeUtil.ToMegaBytes(size);
Console.WriteLine($"ファイルサイズ: {size} バイト ({mb:F2} MB)");
}
}
C#ここでのポイントは、「整数同士で割ると小数点以下が切り捨てられてしまう」ので、1024.0 のように double で割っていることです。{mb:F2} は「小数点以下 2 桁まで表示」という意味です。
自動で単位を選んで文字列にする
もう少し実務寄りにするなら、「サイズに応じて B / KB / MB / GB を自動で選んで文字列にする」メソッドもよく使われます。
public static class FileSizeUtil
{
public static string FormatSize(long bytes)
{
const double KB = 1024.0;
const double MB = KB * 1024.0;
const double GB = MB * 1024.0;
if (bytes < KB)
{
return $"{bytes} B";
}
else if (bytes < MB)
{
double value = bytes / KB;
return $"{value:F2} KB";
}
else if (bytes < GB)
{
double value = bytes / MB;
return $"{value:F2} MB";
}
else
{
double value = bytes / GB;
return $"{value:F2} GB";
}
}
}
C#使い方の例は次の通りです。
class Program
{
static void Main()
{
string path = @"C:\data\archive.zip";
long size = FileSizeUtil.GetFileSize(path);
string formatted = FileSizeUtil.FormatSize(size);
Console.WriteLine($"ファイルサイズ: {formatted}");
}
}
C#このようにしておくと、ログや画面表示で「人間にとって読みやすいサイズ」を簡単に出せます。
フォルダ内のファイルサイズ合計を求める
指定フォルダ直下の合計サイズ
業務では、「このフォルダがどれくらいディスクを使っているか」を知りたいことがよくあります。
その場合は、フォルダ内のファイルサイズを合計します。
using System;
using System.IO;
public static class DirectorySizeUtil
{
public static long GetDirectorySize(string directoryPath)
{
if (!Directory.Exists(directoryPath))
{
throw new DirectoryNotFoundException($"ディレクトリが見つかりません: {directoryPath}");
}
long total = 0;
string[] files = Directory.GetFiles(directoryPath);
foreach (string filePath in files)
{
FileInfo info = new FileInfo(filePath);
total += info.Length;
}
return total;
}
}
C#使い方の例は次の通りです。
class Program
{
static void Main()
{
string dir = @"C:\logs\app";
long totalBytes = DirectorySizeUtil.GetDirectorySize(dir);
string formatted = FileSizeUtil.FormatSize(totalBytes);
Console.WriteLine($"ディレクトリの合計サイズ: {formatted}");
}
}
C#ここでのポイントは、「合計サイズも long で持つ」ことです。
多数のファイルを足し合わせると、すぐに大きな値になるためです。
サブフォルダも含めた再帰的な合計サイズ
さらに、「サブフォルダも含めてフォルダ全体のサイズを知りたい」場合は、再帰的にディレクトリをたどります。
public static class DirectorySizeUtil
{
public static long GetDirectorySizeRecursive(string directoryPath)
{
if (!Directory.Exists(directoryPath))
{
throw new DirectoryNotFoundException($"ディレクトリが見つかりません: {directoryPath}");
}
long total = 0;
AddDirectorySize(directoryPath, ref total);
return total;
}
private static void AddDirectorySize(string directoryPath, ref long total)
{
foreach (string filePath in Directory.GetFiles(directoryPath))
{
FileInfo info = new FileInfo(filePath);
total += info.Length;
}
foreach (string subDir in Directory.GetDirectories(directoryPath))
{
AddDirectorySize(subDir, ref total);
}
}
}
C#このようにしておくと、「ログフォルダ全体で何 GB 使っているか」「バックアップフォルダがディスクを圧迫していないか」といった監視に使えます。
実務での典型パターンと注意点
「サイズ 0 のファイルをエラー扱いする」チェック
よくある業務要件として、「空ファイルはエラーとして扱う」というものがあります。
たとえば、外部システムから受信した CSV がサイズ 0 だった場合、「データが来ていない」と判断したいケースです。
その場合のコードイメージは次の通りです。
using System;
using System.IO;
class Program
{
static void Main()
{
string path = @"C:\import\sales.csv";
long size = FileSizeUtil.GetFileSize(path);
if (size == 0)
{
Console.WriteLine("エラー: ファイルサイズが 0 です。");
return;
}
Console.WriteLine("ファイルサイズは正常です。処理を続行します。");
}
}
C#このように、「サイズチェックを最初に行う」ことで、無駄なパース処理や後続エラーを防げます。
「想定以上に大きいファイルを拒否する」ガード
逆に、「あまりに大きいファイルは処理しない」というガードも重要です。
たとえば、「10 MB を超える CSV は受け付けない」といったルールです。
using System;
using System.IO;
class Program
{
static void Main()
{
string path = @"C:\import\large.csv";
long size = FileSizeUtil.GetFileSize(path);
double mb = FileSizeUtil.ToMegaBytes(size);
if (mb > 10.0)
{
Console.WriteLine($"エラー: ファイルが大きすぎます ({mb:F2} MB)。");
return;
}
Console.WriteLine("サイズは許容範囲内です。処理を続行します。");
}
}
C#こうしたガードを入れておくことで、「想定外の巨大ファイルでメモリや処理時間が爆発する」事故を防げます。
例外とエラー処理を意識したファイルサイズ取得
どんな例外が起こり得るか
ファイルサイズ取得では、次のような理由で例外が発生する可能性があります。
ファイルが存在しない、権限がなくてアクセスできない、別プロセスがロックしている、パスが不正または長すぎる、などです。
呼び出し側での例外処理の例を見てみます。
using System;
using System.IO;
class Program
{
static void Main()
{
string path = @"C:\data\report.csv";
try
{
long size = FileSizeUtil.GetFileSize(path);
string formatted = FileSizeUtil.FormatSize(size);
Console.WriteLine($"ファイルサイズ: {formatted}");
}
catch (FileNotFoundException ex)
{
Console.WriteLine("ファイルが見つかりません: " + ex.Message);
}
catch (UnauthorizedAccessException ex)
{
Console.WriteLine("権限エラーが発生しました: " + ex.Message);
}
catch (IOException ex)
{
Console.WriteLine("入出力エラーが発生しました: " + ex.Message);
}
catch (Exception ex)
{
Console.WriteLine("想定外のエラーが発生しました: " + ex.Message);
}
}
}
C#実務では、これらのメッセージをログに残しておくことで、「どのファイルのサイズ取得に、どんな理由で失敗したか」を後から追跡できます。
まとめ 実務で使えるファイルサイズ取得ユーティリティの考え方
ファイルサイズ取得は、一見シンプルですが、「空ファイルの検知」「巨大ファイルのガード」「ディスク使用量の監視」など、業務システムの安定運用を支える重要な要素です。
だからこそ、「ただ Length を読む」だけで終わらせず、ユーティリティとして整理しておく価値があります。
FileInfo.Length を使って、サイズを long で正しく扱うこと。
存在チェックを含めたユーティリティ(例外を投げる版と、0 を返す版)を用意し、用途に応じて使い分けること。
バイトから KB・MB・GB への変換や、人間向けのフォーマット表示をユーティリティ化しておき、ログや画面で読みやすくすること。
フォルダ単位の合計サイズ取得や、再帰的なディレクトリサイズ計算を用意して、ログ・バックアップ・一時領域の容量管理に活かすこと。
サイズ 0 のファイルや、想定以上に大きいファイルを検知して、処理前に弾くガードを入れておくこと。
ここまで押さえておけば、「サイズを見ずに処理してしまったせいで起きるトラブル」をかなり減らせます。
