You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何在C#中基于值将对象数组合并为单个对象?

C# 高效合并SecuritySettings的实现方案

核心需求

输入为SecurityResponse类型数组,每个元素包含colorSettings、speedSettings等多组设置集合;每组集合的项包含唯一settingKey和权限值securitySettingValue(W=写入、R=读取、H=隐藏)。需按W > R > H的宽松优先级合并相同settingKey的项,取最宽松权限,同时避免多层嵌套循环。

实现思路:利用LINQ内置方法简化逻辑

LINQ的SelectMany、GroupBy、Max等内置方法可以完全替代手动嵌套循环,且内部经过性能优化,代码更简洁易维护。

第一步:定义基础类型(明确结构)

先把相关类型定义清楚(如果已有类型,可跳过此步):

// 用枚举表示权限,按严格到宽松排序,枚举值越大权限越高
public enum SecurityPermission { H, R, W }

public class SecuritySetting
{
    public string SettingKey { get; set; }
    public SecurityPermission SecuritySettingValue { get; set; }
}

public class SecurityResponse
{
    public IEnumerable<SecuritySetting> ColorSettings { get; set; }
    public IEnumerable<SecuritySetting> SpeedSettings { get; set; }
    // 其他设置集合(如SoundSettings等)可按需添加
}

第二步:全局合并所有设置(返回字典)

如果需要将所有类型的设置合并为一个按settingKey索引的字典,可直接用以下实现:

public Dictionary<string, SecurityPermission> MergeAllSecuritySettings(SecurityResponse[] responses)
{
    // 定义所有需要提取的设置集合
    var settingExtractors = new Func<SecurityResponse, IEnumerable<SecuritySetting>>[]
    {
        response => response.ColorSettings,
        response => response.SpeedSettings
        // 追加其他设置集合的提取逻辑...
    };

    return responses
        // 扁平化所有设置集合,避免嵌套循环
        .SelectMany(response => settingExtractors.SelectMany(extractor => extractor(response)))
        // 按settingKey分组
        .GroupBy(setting => setting.SettingKey)
        // 每组取权限最高的项,转为字典
        .ToDictionary(
            group => group.Key,
            group => group.Max(setting => setting.SecuritySettingValue)
        );
}

第三步:按原设置类型分组合并

如果需要保留原有的ColorSettings、SpeedSettings分组结构,可拆分出通用的单类型合并方法:

// 合并后的结果类型,与SecurityResponse结构一致
public class MergedSecuritySettings
{
    public IEnumerable<SecuritySetting> ColorSettings { get; set; }
    public IEnumerable<SecuritySetting> SpeedSettings { get; set; }
    // 对应原类型的其他设置集合...
}

public MergedSecuritySettings MergeSecuritySettingsByType(SecurityResponse[] responses)
{
    return new MergedSecuritySettings
    {
        ColorSettings = MergeSingleSettingGroup(responses, r => r.ColorSettings),
        SpeedSettings = MergeSingleSettingGroup(responses, r => r.SpeedSettings)
        // 其他设置类型的合并调用...
    };
}

// 通用的单类型设置合并方法
private IEnumerable<SecuritySetting> MergeSingleSettingGroup(
    SecurityResponse[] responses, 
    Func<SecurityResponse, IEnumerable<SecuritySetting>> settingExtractor)
{
    return responses
        .SelectMany(settingExtractor)
        .GroupBy(s => s.SettingKey)
        .Select(group => new SecuritySetting
        {
            SettingKey = group.Key,
            SecuritySettingValue = group.Max(s => s.SecuritySettingValue)
        });
}

兼容字符串类型权限的处理

如果原securitySettingValue是字符串(而非枚举),可先定义权限优先级转换函数,再用于比较:

// 转换字符串权限为优先级数值,数值越大权限越宽松
private static int GetPermissionPriority(string permission) => permission switch
{
    "W" => 2,
    "R" => 1,
    "H" => 0,
    _ => throw new ArgumentOutOfRangeException(nameof(permission), "无效的权限值")
};

在合并时替换Max逻辑:

// 示例:单类型合并中替换为字符串权限处理
.Select(group => new SecuritySetting
{
    SettingKey = group.Key,
    SecuritySettingValue = group.OrderByDescending(s => GetPermissionPriority(s.SecuritySettingValue))
                               .First()
                               .SecuritySettingValue
});

优势说明

  • 完全避免手动多层嵌套循环,代码可读性更强
  • LINQ内置方法经过微软优化,性能优于手动实现的遍历逻辑
  • 枚举/优先级函数的使用,避免了字符串比较的潜在错误,逻辑更严谨

内容的提问来源于stack exchange,提问作者Franco Aguilera

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.06.27 07:03:27