我有一個字符串列表:鴻溝列表中的元素
{"foo", "str1", "str2", ..., "bar", ..., "baz", ...}
我需要"foo"
,"bar"
和"baz"
之間獲得串子列表。
是否有可能與linq做到這一點?
編輯
我需要不看谷底列表兩次的方法。
我有一個字符串列表:鴻溝列表中的元素
{"foo", "str1", "str2", ..., "bar", ..., "baz", ...}
我需要"foo"
,"bar"
和"baz"
之間獲得串子列表。
是否有可能與linq做到這一點?
編輯
我需要不看谷底列表兩次的方法。
你可以做到這一點,以罰款的任何其他兩個元素之間的所有元素:
var strings = new[] { "foo", "str1", "str2", ... "bar", ... "baz" };
var between = strings.SkipWhile(s => s != "foo").Skip(1)
.TakeWhile(s => s != "bar"); // "str1", "str2", ...
如果你想獲得「foo」和「巴茲」之間的一切,除了「酒吧」,用這個(假設爲了「富」,「酒吧」,「巴茲」):
var strings = new[] { "foo", "str1", "str2", ... "bar", ... "baz" };
var between = strings.SkipWhile(s => s != "foo").Skip(1)
.TakeWhile(s => s != "baz")
.Where(s => s != "bar"); // "str1", "str2", ...
或者,如果你願意使用LINQ查詢有副作用,你可以做到這一點通過某些「停止」分割你的輸入列表字數:
var stops = new[] { "foo", "bar", "baz" };
var strings = new[] { "foo", "str1", "str2", "bar", "str3", "baz" };
var p = -1;
var partitions =
from s in strings
let i = Array.IndexOf(stops, s)
group s by p = i == -1 ? p : i into g
where g.Key == 0 || g.Key == 1
select g.Skip(1); // { "str1", "str2" }, { "str3" }
或略微更有效的(因爲它的第三站單詞後停止處理):
var partitions =
(from s in strings
let i = Array.IndexOf(stops, s)
group s by p = i == -1 ? p : i)
.SkipWhile(g => g.Key < 0)
.Take(2)
.Select(g => g.Skip(1)); // { "str1", "str2" }, { "str3" }
現在,這種方法是周圍的邊緣有點粗糙,它有點繁瑣,當涉及到「foo」之前或「baz」之後的項目,但如果因爲您只查找「foo」和「baz」之間的項目,它應該適合您。它具有額外的好處,即停用詞的順序不會影響結果。
var idxFoo = list.IndexOf("foo");
var idxBar = list.IndexOf("bar");
var idxBaz = list.IndexOf("baz");
var subList1 = list.Skip(idxFoo).Take(idxBar - idxFoo);
var subList2 = list.Skip(idxBar).Take(idxBaz - idxBar);
如果你想通過你的大量數據列表只有一次迭代,你可以這樣做:
List<string> longDataList = new List<string> { "foo", "str1", "str2", "str1", "str2", "str1", "str2", "bar", "str1", "str2", "str1", "str2", "str1", "str2", "baz", "str1", "str2", "str1", "str2", "str1", "str2" };
List<string> splitters = new List<string> { "foo", "bar", "baz" };
Dictionary<string, List<string>> resultDict = new Dictionary<string, List<string>>();
List<string> currentList = null;
longDataList.ForEach(s =>
{
if (splitters.Contains(s))
{
if (resultDict.ContainsKey(s))
currentList = resultDict[s];
else
{
currentList = new List<string>();
resultDict.Add(s, currentList);
}
}
else
currentList.Add(s);
});
透過大量的數據列表使用至少有一點LINQ,但不會把戲迭代只有一次。
我會說是的:)你已經嘗試過一些東西?如果是的話與我們分享。 – wonko79
那麼,我花了兩天的時間搜索並嘗試了不同的方法,但沒有找到任何方法,沒有在列表中查看兩次。 – dikyyn
看到我的答案只迭代一次。看起來不像其他解決方案那麼好,但也有訣竅。 – wonko79