您的位置:首页 > 产品设计 > UI/UE

C#操作注册表REG_DWORD类型键异常(RegistryValueKind.DWord异常)解决方案

2012-11-28 16:28 519 查看
在用C#操作注册表时,如果注册表键的类型是REG_DWORD,有可能遇到溢出BUG。网上这方面的资料很少,在这共享一下。

C#可以用RegistryKey类的SetValue方法来设置键值,例如:



看起来一切正常,但是这个RegistryValueKind.DWord是有问题的。

注册表中的REG_DWORD是无符号32位数值,而C#中的RegistryValueKind.DWord是有符号32位数值。这就意味着RegistryValueKind.DWord的表示范围比REG_DWORD小,因此导致直接传入一些大数时会抛出异常提示类型不正确。

那么如何解决这个BUG呢?

读者可能试图这样做:

openKey.SetValue("NoViewOnDrive",Convert.ToInt32("ffffffff",16), RegistryValueKind.DWord);

目的是强制把参数转换成32位有符号数,这样是不行的,同样提示异常,因为ffffffff已经超出了有符号32位数的表示范围,无法转换。

或者这样做:

openKey.SetValue("NoViewOnDrive",Convert.ToUInt32 ("ffffffff",16), RegistryValueKind.DWord);

目的是把参数强制转换成无符号32位表示,这样同样不行,SetValue方法内部会自动把参数转换成有符号32位表示,因此,我们的转换是徒劳的,还会被转换回去,而转换回去后,又会提示超出范围。

其实,解决这个问题的方法很简单,只要把转换过程放在unchecked语句里就行了,unchecked语句块内的转换,不做溢出检查,溢出了直接用补码表示。例如:

Int32 tempInt = 0; //预先定义一个有符号32位数

//unchecked语句块内的转换,不做溢出检查
unchecked
{
tempInt = Convert.ToInt32("ffffffff", 16); //强制转换成有符号32位数
}

//此时的tempInt已经是有符号32位数,可以直接写入注册表
openKey.SetValue("NoViewOnDrive", tempInt, RegistryValueKind.DWord);


这样转折一下,就可以成功写入注册表了。
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: 
相关文章推荐