Linq Join 多键键的一侧键为 null

Linq Join multi key one side of key is null

提问人:spiral 提问时间:1/26/2023 更新时间:1/26/2023 访问量:76

问:

尝试联接两个表,其中一侧的部分键可为 null。得到“无法从用法中推断出类型参数”,我认为这与键中的不匹配类型有关。

TableA.GroupJoin(TableB,
  a => new {a.IntKeyA, a.StringKeyA},
  b => new {b.NullIntKeyB, b.StringKeyB}
 (tabA, tabB) => new {tabA, tabB});

尝试在 TableA 中强制转换键的类型

a => new (int?, string) {a.IntKeyA, a.StringKeyA}

a => (int?, string)(new  {a.IntKeyA, a.StringKeyA})

尝试合并 TableB 中的键,魔术数字 0 不是很好,但在这种情况下会起作用。

b => new {b.NullIntKeyB ?? 0, b.StringKeyB} 

尝试了 GetValueOrDefault

b => new {b.NullIntKeyB.GetValueOrDefault(), b.StringKeyB}

我想我可能会定义一个类来保存密钥,但我真的不想每次出现这个问题时都这样做。

C# LINQ 匿名类型

评论

0赞 NetMage 1/26/2023
我认为您不了解如何在 C# 中使用 cast。您需要将值转换为匿名类型,而不是对象本身,例如 .new { (int?)a.IntKeyA, a.StringKeyA }
0赞 spiral 1/26/2023
哦,我忘了列出它,但我试过了,它也不起作用。“无效的匿名类型成员声明符。匿名类型成员必须使用成员分配、简单名称或成员访问权限进行声明。

答:

0赞 spiral 1/26/2023 #1

目前,这似乎奏效了,但我还不打算将其标记为答案,希望有更简单的方法。

class ReportKey
{
    private int? IntKey { get; }
    private string StringKey { get; } = string.Empty;
   
    internal ReportKey(int? intKey, string stringKey)
    {
        IntKey = intKey;
        StringKey = stringKey;
    }
    
    public override bool Equals(object obj)
    {
        var item = obj as ReportKey;
    
        if (item == null) return false;
    
        return this.IntKey == item.Intkey &&
           StringKey == item.StringKey;
    }
    
    public override int GetHashCode()
    {
        return $"{IntKey}{StringKey}".GetHashCode();
    }
}

...

TableA.GroupJoin(TableB,
    a => new ReportKey(a.IntKeyA, a.StringKeyA),
    b => new ReportKey(b.NullIntKeyB, b.StringKeyB),
   (tabA, tabB) => new {tabA, tabB});