使用键值对初始化字典

3

在包含许多不同类型子对象的大型对象初始化期间...

我有一个返回 KeyValuePair<string, object> 的函数。当初始化 Dictionary<string, object> 时,我想要调用它,就像这样:

AdditionalProperties = new Dictionary<string,object>(ams.GetKVP(AvaloqTypes.Person.PersonDocm.CountryId))

这会导致编译错误,错误提示为“无法将 KeyValuePair 转换为 IDictionary”。 我可以通过以下方式解决该问题:
AdditionalProperties = new Dictionary<string,object>()
{
    { ams.GetKVP(AvaloqTypes.Person.PersonDocm.DocmItem).Key,
      ams.GetKVP(AvaloqTypes.Person.PersonDocm.DocmItem).Value 
    }
}

然而,这意味着GetKVP方法被调用了两次。
有没有更好的解决方案,不需要改变GetKVP方法?

1
Dictionary没有接受KeyValuePair参数的构造函数,不清楚为什么你认为会起作用。 - DavidG
为什么要加上C# 8标签?问题中并没有特指C# 8。 - Panagiotis Kanavos
既然只有一个键值对,为什么不使用字典初始化语法呢? - Panagiotis Kanavos
@PanagiotisKanavos 这样人们就知道我正在使用的 C# 版本,并提供可能仅在该版本或更高版本中可用的解决方案。 - Rob Bowman
@RobBowman 这个库是由运行时提供的,而不是语言。您是针对.NET Core还是旧框架进行开发?所有接受“IEnumerable<KVP>”答案的版本都适用于.NET Core 2.0及以上。没有构造函数接受单个KVP。字典初始化程序在所有版本中都可以使用。 - Panagiotis Kanavos
4个回答

6

Dictionary没有接受 IKeyValuePair 作为参数的构造函数重载。但是在实例化新的 Dictionary时,可以传递一个包含 KeyValuePair 的集合:

var kvp = new Dictionary<string,object>(new [] 
{ 
   ams.GetKVP(AvaloqTypes.Person.PersonDocm.CountryId)
});

编辑:此构造函数仅存在于.NET Core中。

链接


由于DavidG的方法返回KeyValuePair<string,object>,如果您有疑问,请发表更有意义的评论。 - OlegI
@DavidG 在这种情况下,有一个 Dictionary<TKey,TValue>(IEnumerable<KeyValuePair<TKey,TValue>>),而 OP 尝试传递 单个 实例。在这种情况下,将使用该单个实例构造一个新列表。 - Panagiotis Kanavos
@OlegI 你本可以使用数组而不是列表。 - Panagiotis Kanavos
@PanagiotisKanavos,有吗?您能告诉我是哪一个构造函数吗?https://learn.microsoft.com/en-us/dotnet/api/system.collections.generic.dictionary-2.-ctor?view=netframework-4.8 - DavidG
如果您保留 C#8 参考,则它确实存在于那里。这可能需要指定。 - DavidG
@DavidG 它是在 .NET Core 2.0 中添加的(https://learn.microsoft.com/en-us/dotnet/api/system.collections.generic.dictionary-2.-ctor?view=netcore-2.0#System_Collections_Generic_Dictionary_2__ctor_System_Collections_Generic_IEnumerable_System_Collections_Generic_KeyValuePair__0__1___),同时还添加了许多其他构造函数,因此它并不特定于C# 8。但它从未被添加到 .NET Old中,甚至不是在4.8版本中。 - Panagiotis Kanavos

5

你可以将键值对提取到一个变量中,并使用该变量,这样方法就不会被调用两次。

var kvp = ams.GetKVP(AvaloqTypes.Person.PersonDocm.DocmItem);
AdditionalProperties = new Dictionary<string,object>() { { kvp.Key, kvp.Value } }

但是我会质疑在只有一个键值对的情况下选择使用kvp或字典。

抱歉,我应该说明需要在更大的初始化块中完成此操作 - 因此无法声明变量。 - Rob Bowman

0

其他选项

AdditionalProperties = new Dictionary<string,object>(new List<KeyValuePair<string, object>> { ams.GetKVP(AvaloqTypes.Person.PersonDocm.DocmItem) });

这个无法编译。 - Panagiotis Kanavos

0

实际上,您可以使用Add-Method,它以KeyPairValue作为参数。

问题在于:这是ICollection Add-Method的显式实现。

这意味着只能通过将您的Dictionary转换为ICollection或任何继承ICollection并由Dictionary实现的接口来调用它。

而有一个接口正好可以做到这一点,并公开了Dictionary-Type的功能: IDictionary

因此,通过将AdditionalProperties定义为IDictionary<string,object> AdditionalProperties,您可以执行以下操作:

AdditionalProperties = new Dictionary<string,object>();
AdditionalProperties.Add(ams.GetKVP(AvaloqTypes.Person.PersonDocm.DocmItem));

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接