1. 程式人生 > >C# txt文字讀取最後X行

C# txt文字讀取最後X行

using System.IO;

/// <summary>
/// 讀取文字檔案最後的內容
/// </summary>
/// <param name="AFileName">檔名</param>
/// <param name="ALineCount">行數</param>
/// <param name="AEncoding">字元編碼</param>
/// <returns>返回讀取的內容</returns>
public string ReadLastLine(string AFileName, int ALineCount, Encoding AEncoding)
{
    if (ALineCount <= 0) return string.Empty;
    if (!File.Exists(AFileName)) return string.Empty; // 檔案不存在
    if (AEncoding == null) AEncoding = Encoding.Default;
    using (FileStream vFileStream = new FileStream(AFileName,
        FileMode.Open, FileAccess.Read, FileShare.Read))
    {

        if (vFileStream.Length <= 0) return string.Empty; // 空檔案
        byte[] vBuffer = new byte[0x1000]; // 緩衝區
        int vReadLength; // 讀取到的大小
        int vLineCount = 0; // 讀取的行數
        int vReadCount = 0; // 讀取的次數
        int vScanCount = 0; // 掃描過的字元數
        long vOffset = 0; // 向後讀取的位置
        do
        {
            vOffset = vBuffer.Length * ++vReadCount;
            int vSpace = 0; // 偏移超出的空間
            if (vOffset >= vFileStream.Length) // 超出範圍
            {
                vSpace = (int)(vOffset - vFileStream.Length);
                vOffset = vFileStream.Length;
            }
            vFileStream.Seek(-vOffset, SeekOrigin.End); //“SeekOrigin.End”反方向偏移讀取位置

            vReadLength = vFileStream.Read(vBuffer, 0, vBuffer.Length - vSpace);
            #region 所讀的緩衝裡有多少行
            for (int i = vReadLength - 1; i >= 0; i--)
            {
                if (vBuffer[i] == 10)
                {
                    if (vScanCount > 0) vLineCount++; // #13#10為回車換行
                    if (vLineCount >= ALineCount) break;
                }
                vScanCount++;
            }
            #endregion 所讀的緩衝裡有多少行
        } while (vReadLength >= vBuffer.Length && vOffset < vFileStream.Length && 
            vLineCount < ALineCount);

        if (vReadCount > 1) // 讀的次數超過一次,則需重分配緩衝區
        {
            vBuffer = new byte[vScanCount];
            vFileStream.Seek(-vScanCount, SeekOrigin.End);
            vReadLength = vFileStream.Read(vBuffer, 0, vBuffer.Length);
        }
        return AEncoding.GetString(vBuffer, vReadLength - vScanCount, vScanCount);
    }
}

private void button1_Click(object sender, EventArgs e)
{
    textBox1.Text = ReadLastLine(@"c:\temp\WindowsUpdate.log", 7, Encoding.Default);
}
以上程式碼轉載於http://bbs.csdn.net/topics/230002962,31樓