求助:C# Dictionary遇到的问题。

Jave.Lin 2011-10-24 11:50:01
异常描述:

System.ArgumentNullException: Value cannot be null.
Parameter name: key
at System.ThrowHelper.ThrowArgumentNullException(ExceptionArgument argument)
at System.Collections.Generic.Dictionary`2.FindEntry(TKey key)
at System.Collections.Generic.Dictionary`2.ContainsKey(TKey key)


public static void CloneKeyTo(ASObject sourceASO, out ASObject desASO)
{
desASO = new ASObject();

string[] keys;
lock (sourceASO.Keys)
{
keys = sourceASO.Keys.ToArray();
}
foreach (string key in keys)
{
lock (sourceASO)
{
if (sourceASO.ContainsKey(key))//这里出异常,说key==null
{
desASO[key] = sourceASO[key];
}
}
}
}


测试代码:

Dictionary<string,object> demoObj = new Dictionary<string,object>();
demoObj[null]=1;//这是更加不可能的,直接异常。


我想问一下:什么情况下,Dictionary<string,object>中,的Keys的元素,中,会有子元素,有可能为:null的情况?

而这个Keys是只读的属性。
...全文
965 10 打赏 收藏 转发到动态 举报
写回复
用AI写文章
10 条回复
切换为时间正序
请发表友善的回复…
发表回复
Jave.Lin 2011-10-24
  • 打赏
  • 举报
回复
[Quote=引用 5 楼 stonespace 的回复:]

foreach (string key in keys)
{
lock (sourceASO)
{
string strKey=key;
if (strKey==null)
……
[/Quote]

谢谢您的回复。

我目前只能用这方法来避免了。

public static void CloneKeyTo(ASObject sourceASO, out ASObject desASO)
{
desASO = new ASObject();

string[] keys;
lock (sourceASO.Keys)
{
keys = sourceASO.Keys.ToArray();
}
lock (sourceASO)
{
foreach (string key in keys)
{
if (key == null) continue;
if (sourceASO.ContainsKey(key))
{
desASO[key] = sourceASO[key];
}
}
}
}
Jave.Lin 2011-10-24
  • 打赏
  • 举报
回复
我现在问题就是在于,我不知道key何时为null我没有任何地方对key值有赋值的地方
stonespace 2011-10-24
  • 打赏
  • 举报
回复
和你重写没关系,string本身就有GetHashCode,而Dictionary要调用key.GetHashCode,如果你传入null作为key,那么Dictionary就要调用null.GetHashCode然后就出现引用空的异常,

[Quote=引用 4 楼 linjf520 的回复:]



我没有重写GetHashCode方法
[/Quote]
stonespace 2011-10-24
  • 打赏
  • 举报
回复
foreach (string key in keys)
{
lock (sourceASO)
{
string strKey=key;
if (strKey==null)
{ strKey="";
}
if (sourceASO.ContainsKey(strKey))//这里出异常,说key==null
{
desASO[strKey] = sourceASO[strKey];
}
}
}
Jave.Lin 2011-10-24
  • 打赏
  • 举报
回复
[Quote=引用 2 楼 stonespace 的回复:]

Dictionary会对key计算散列,也就是调用key的Gethashcode方法,如果key是null,调用gethashcode就失败了,所以key不能是null,

key绝对不可能是null,
[/Quote]

我没有重写GetHashCode方法
stonespace 2011-10-24
  • 打赏
  • 举报
回复
空字符串可以用""表示,不需要用null,在外边自己转一下就行了,比如

if (key==null)
{
key="";
}
stonespace 2011-10-24
  • 打赏
  • 举报
回复
Dictionary会对key计算散列,也就是调用key的Gethashcode方法,如果key是null,调用gethashcode就失败了,所以key不能是null,

key绝对不可能是null,
Jave.Lin 2011-10-24
  • 打赏
  • 举报
回复
忘记了说,这个ASObject是这样的:


public class ASObject : Dictionary<string,object>
{

}

stonespace 2011-10-24
  • 打赏
  • 举报
回复
其实也不一定用continue,像我在5楼的代码,加一个变量strKey,判断key==null就用""代替,

[Quote=引用 8 楼 linjf520 的回复:]

引用 5 楼 stonespace 的回复:

foreach (string key in keys)
{
lock (sourceASO)
{
string strKey=key;
if (strKey==null)
……


谢谢您的回复。

我目前只能用这方法来避免了。
C# code

public static void CloneKey……
[/Quote]
youzelin 2011-10-24
  • 打赏
  • 举报
回复
我觉得如果 Key 设成 Null 是没有什么意义的。且不管他能不能为 Null。
Key 本身来说,可以理解为对 Value 的概括的唯一标示。比如 { 'S00212', new Student(...) }
如果 Key 为 Null,那 Value 也是没有意义的。

110,533

社区成员

发帖
与我相关
我的任务
社区描述
.NET技术 C#
社区管理员
  • C#
  • Web++
  • by_封爱
加入社区
  • 近7日
  • 近30日
  • 至今
社区公告

让您成为最强悍的C#开发者

试试用AI创作助手写篇文章吧