使用 LINQ 根据字符串将包含的已知子字符串对字符串列表进行分组

Ben*_*lla 2 c# linq group-by

我有一个已知的字符串列表,如下所示:

List<string> groupNames = new List<string>(){"Group1","Group2","Group3"};
Run Code Online (Sandbox Code Playgroud)

我还有一个事先未知的字符串列表,如下所示:

List<string> dataList = new List<string>()
{
   "Group1.SomeOtherText",
   "Group1.SomeOtherText2",
   "Group3.MoreText",
   "Group2.EvenMoreText"
};
Run Code Online (Sandbox Code Playgroud)

我想做一个 LINQ 语句,它将获取 dataList 并将其转换为匿名对象或字典,该对象具有组名称的键和包含该组中字符串列表的值。目的是循环组和内部循环组列表,并根据字符串所在的组对字符串执行不同的操作。

我想要一个看起来像这样的数据结构:

var grouped = new
{
   new
   {
       Key="Group1",
       DataList=new List<string>()
            {
               "Group1.SomeOtherText",
               "Group1.SomeOtherText2"
            }
    },
    new 
    {
       Key="Group2",
       DataList=new List<string>()
            {
               "Group2.EvenMoreText"
            }
    }
    ...
};
Run Code Online (Sandbox Code Playgroud)

我知道我可以循环遍历 dataList,然后检查每个字符串是否包含组名称,然后将它们添加到单独的列表中,但我正在尝试学习执行此类任务的 LINQ 方式。

提前致谢。

编辑:

只是有另一个想法...如果我的组名在枚举中怎么办?

public enum Groups
{
    Group1,
    Group2,
    Group3
}
Run Code Online (Sandbox Code Playgroud)

我如何将其放入字典>?

这就是我正在尝试的,但我不确定如何形成 ToDictionary 部分

Dictionary<Groups,List<string>> groupedDictionary =   (from groupName in Enum.GetNames(typeof(Groups))
                                                      from data in dataList 
                                                      where data.Contains(groupName)
                                                      group data by groupName).ToDictionary<Groups,List<string>>(...NOT SURE WHAT TO PUT HERE....);
Run Code Online (Sandbox Code Playgroud)

编辑2:

找到了枚举问题的解决方案:

var enumType = typeof(Groups);
Dictionary<Groups,List<string>> query = (from groupName in Enum.GetValues(enumType).Cast<Groups>()
             from data in dataList
             where data.Contains(Enum.GetName(enumType, groupName))
             group data by groupName).ToDictionary(x => x.Key, x=> x.ToList());
Run Code Online (Sandbox Code Playgroud)

Jon*_*eet 5

看起来像:

var query = from groupName in groupNames
            from data in dataList
            where data.StartsWith(groupName)
            group data by groupName;
Run Code Online (Sandbox Code Playgroud)

请注意,这不是联接,因为可能存在重叠的组名称“G”和“Gr”,因此一个项目可以匹配多个组名称。如果您可以从每个项目中提取组名称(例如,通过获取第一个点之前的所有内容),那么您可以使用“join ... into”来获得组连接。反正...

然后:

foreach (var result in query)
{
    Console.WriteLine("Key: {0}", result.Key);
    foreach (var item in result)
    {
        Console.WriteLine("  " + item);
    }
}
Run Code Online (Sandbox Code Playgroud)

如果你确实需要匿名类型,你可以这样做......

var query = from groupName in groupNames
            from data in dataList
            where data.StartsWith(groupName)
            group data by groupName into g
            select new { g.Key, DataList = g.ToList() };
Run Code Online (Sandbox Code Playgroud)