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

咨询AutoMapper Issue #3926中Nullable<T>参数异常的解决方案

问题描述

AutoMapper Issue #3962已被关闭并锁定,未给出任何解释或解决方案(实际上所有AutoMapper的Issue都被如此处理,维护者引导用户到社区求助)。

问题核心:IMemberConfigurationExpression.Condition接收的Func<TSrc, TDest, object, bool>委托,第三个参数为当前访问的源成员值。示例代码如下:

public static class IMappingExpressionExtensions
{
    public static void Coalesce<Src, Dst>(this IMappingExpression<Src, Dst> exp)
    {
        exp.ForAllMembers(cfg => cfg.Condition((src, dst, srcMember) => srcMember != null));
    }
}

当源成员为引用类型且值为null时,srcMember符合预期为null;但当源成员为无值的Nullable<T>类型时,srcMember意外返回default(T)而非null,导致条件判断失效。

可行解决方案

以下是两种可靠的解决思路:

1. 使用带上下文的Condition重载

AutoMapper提供了包含映射上下文的Condition重载,可通过上下文获取成员元数据,判断是否为Nullable<T>类型并检查实际值:

public static void Coalesce<Src, Dst>(this IMappingExpression<Src, Dst> exp)
{
    exp.ForAllMembers(cfg =>
    {
        cfg.Condition((src, dst, context) =>
        {
            var sourceMember = context.MemberMap.SourceMember;
            if (sourceMember == null) return true;
            
            // 检查成员是否为Nullable<T>类型
            var underlyingType = Nullable.GetUnderlyingType(sourceMember.PropertyType);
            if (underlyingType != null)
            {
                var value = sourceMember.GetValue(src);
                return value != null; // Nullable<T>无值时GetValue返回null
            }
            // 处理引用类型和普通值类型
            var srcMemberValue = context.MemberMap.GetSourceValue(src);
            return srcMemberValue != null;
        });
    });
}

2. 直接通过反射检查源成员值

如果不想依赖AutoMapper上下文,可直接通过反射获取源成员的实际值,区分Nullable<T>无值的情况:

public static void Coalesce<Src, Dst>(this IMappingExpression<Src, Dst> exp)
{
    exp.ForAllMembers(cfg =>
    {
        cfg.Condition((src, dst, srcMember) =>
        {
            var sourceMember = cfg.MemberMap.SourceMember;
            if (sourceMember == null) return true;
            
            var propertyType = sourceMember.PropertyType;
            // 判断是否为Nullable<T>类型
            if (Nullable.GetUnderlyingType(propertyType) != null)
            {
                var value = sourceMember.GetValue(src);
                return value != null;
            }
            // 其他情况沿用原判断逻辑
            return srcMember != null;
        });
    });
}

两种方法都能正确识别Nullable<T>无值的场景,避免将default(T)误判为非null值,实现原Coalesce方法的预期效果。

内容的提问来源于stack exchange,提问作者Kevin Krumwiede

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.08.22 10:33:47