Computer >> บทช่วยสอนคอมพิวเตอร์ >  >> การเขียนโปรแกรม >> C#

วิธีอ่านไฟล์ใน C# - Text และ Binary Files

C# มีหลายวิธีอ่านไฟล์ ขึ้นอยู่กับประเภทไฟล์ (Text/Binary) และขนาดไฟล์

1. อ่าน Text File แบบบรรทัดต่อบรรทัด (StreamReader) - แนะนำสำหรับไฟล์ใหญ่

using System;
using System.IO;

public class Program
{
    public static void Main()
    {
        string path = @"D:\data.txt";

        try
        {
            using (StreamReader sr = new StreamReader(path))
            {
                string line;
                while ((line = sr.ReadLine()) != null)
                {
                    Console.WriteLine(line);
                }
            }
        }
        catch (FileNotFoundException)
        {
            Console.WriteLine("File not found");
        }
        catch (IOException ex)
        {
            Console.WriteLine($"IO Error: {ex.Message}");
        }
    }
}

2. อ่าน Text File ทั้งหมดทีเดียว (File.ReadAllText/Lines) - ใส่ใจได้เฉพาะไฟล์เล็ก


// อ่านทั้งไฟล์เป็น String เดียว
string content = File.ReadAllText(path);

// อ่านเป็น Array ของบรรทัด
string[] lines = File.ReadAllLines(path);

// อ่านแบบ Lazy (Streaming) - .NET Core 2.1+
foreach (string line in File.ReadLines(path))
{
    Console.WriteLine(line);
}

3. อ่าน Binary File (BinaryReader)

using System.IO;

public class BinaryReadExample
{
    public static void Main()
    {
        string path = "mydata.bin";

        // เขียนก่อน (สำหรับทดสอบ)
        WriteBinaryFile(path);

        // อ่าน
        try
        {
            using (BinaryReader br = new BinaryReader(File.Open(path, FileMode.Open)))
            {
                int i = br.ReadInt32();
                double d = br.ReadDouble();
                bool b = br.ReadBoolean();
                string s = br.ReadString();

                Console.WriteLine($"Int: {i}");
                Console.WriteLine($"Double: {d}");
                Console.WriteLine($"Bool: {b}");
                Console.WriteLine($"String: {s}");
            }
        }
        catch (EndOfStreamException)
        {
            Console.WriteLine("File truncated or corrupt");
        }
    }

    static void WriteBinaryFile(string path)
    {
        using (BinaryWriter bw = new BinaryWriter(File.Create(path)))
        {
            bw.Write(25);
            bw.Write(3.14157);
            bw.Write(true);
            bw.Write("I am happy");
        }
    }
}

4. อ่าน Binary เป็น Byte Array


// ไฟล์เล็ก
byte[] data = File.ReadAllBytes(path);

// ไฟล์ใหญ่ - Streaming
using (FileStream fs = File.OpenRead(path))
{
    byte[] buffer = new byte[8192];
    int bytesRead;
    while ((bytesRead = fs.Read(buffer, 0, buffer.Length)) > 0)
    {
        ProcessBuffer(buffer, bytesRead);
    }
}

// .NET 5+ - ReadExactly / ReadAtLeast
byte[] buffer = new byte[100];
int read = await fs.ReadExactlyAsync(buffer); // Throw ถ้าอ่านไม่ครบ

5. Encoding ปัญหาภาษาไทย


// ระบุ Encoding ชัดเจน
using (StreamReader sr = new StreamReader(path, Encoding.UTF8))
{
    // หรือ TIS-620 สำหรับไฟล์เก่า
    // using (StreamReader sr = new StreamReader(path, Encoding.GetEncoding("TIS-620")))
}

// File.ReadAllText กำหนด Encoding
string content = File.ReadAllText(path, Encoding.UTF8);

// Detect Encoding (Heuristic)
Encoding detected = DetectEncoding(path); // ใช้ Library: Ude.NetStandard

ตารางเปรียบเทียบเมธอด

เมธอดMemorySpeedเหมาะสำหรับ
File.ReadAllTextHigh (All in Memory)Fast (Small Files)Config, Small Text Files
File.ReadAllLinesHighFastLine-by-line Processing
File.ReadLinesLow (Streaming)GoodLarge Files, LINQ
StreamReaderLow (Streaming)GoodLarge Files, Custom Parsing
BinaryReaderLowFastStructured Binary Data
FileStream + BufferLow (Controlled)FastestHigh Performance, Custom Format

Error Handling Best Practices


public static async Task SafeReadAllTextAsync(string path)
{
    try
    {
        return await File.ReadAllTextAsync(path);
    }
    catch (FileNotFoundException)
    {
        throw new FileNotFoundException($"Config file not found: {path}");
    }
    catch (UnauthorizedAccessException)
    {
        throw new UnauthorizedAccessException($"No permission to read: {path}");
    }
    catch (IOException ex) when (ex.HResult == -2147024864) // ERROR_FILE_IN_USE
    {
        throw new IOException($"File is locked: {path}", ex);
    }
}