簡體   English   中英

查找文件中最后一次出現的字符串

[英]Find the last occurrence of a string in a file

我需要從 C# 中的特定字符串中獲取最后一次出現的日志跟蹤,例如:

lines = File.ReadLines(logPath)
        .SkipWhile(line => !line.Contains("param"))
        .Take(20);

該代碼有效,但它從日志中第一次出現“param”返回 20 行,而我需要最后一個。

您可以創建一個(擴展)方法,該方法向后遍歷源序列,直到找到與某個謂詞匹配的項目。 當您搜索匹配項時,請保留您查看過的項目的堆棧,如果找到匹配項,則返回它們:

public static IEnumerable<T> SkipUntilLast<T>(
    this IEnumerable<T> source, Func<T, bool> predicate)
{
    var stack = new Stack<T>();

    foreach(var item in source.Reverse())
    {
        if (predicate(item))
            return stack;

        stack.Push(item);
    }

    return Enumerable.Empty<T>();
}

用法:

lines = File.ReadLines(logPath).
        .SkipUntilLast(line => line.Contains("param"))
        .Take(20);

請注意, Reverse會將源序列放入緩沖區,然后堆棧會做類似的事情(取決於最后一個匹配是更接近尾端還是靠近源頭)。 您可以使用所需大小的隊列來保留您檢查過的項目,因此在您的情況下它不會超過 20 個項目。 您還可以通過在謂詞檢查之前移動stack.Push來決定是否應將匹配項包含在輸出中。


示例文件

something
param foo
this
is
not
included
param bar
here
we
go
again

跳到包含“param”的最后一行,然后取三行:

File.ReadLines("samplefile").SkipUntilLast(line => line.Contains("param")).Take(3);

結果:

[ "here", "we", "go" ]

您可以在將行轉換為 List 或 Array 后使用 Last。 如下圖:

lines = File.ReadLines(logPath)
        .SkipWhile(line => !line.Contains("param"))
        .ToList()
        .Last();

要查找與提供的謂詞匹配的字符串的最后一次出現,我建議使用LastOrDefault

File.ReadLines(logPath)       
    .LastOrDefault(line => !line.Contains("param"));

否則,如果您需要提到的20的最后一個,則使用SkipFirstOrDefault

File.ReadLines(logPath)
    .SkipWhile(line => !line.Contains("param"))
    .Skip(19)
    .FirstOrDefault();

也可以這樣做:

File.ReadLines(logPath)
    .SkipWhile(line => !line.Contains("param"))
    .Take(20)
    .LastOrDefault();

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM