gpt4 book ai didi

c# - STL/CLR 库使用 IComparable 实现 == 运算符并抛出 NullReferenceException

转载 作者:行者123 更新时间:2023-11-30 04:23:28 25 4
gpt4 key购买 nike

我有一个 .NET 类没有实现 IComparable 接口(interface)。在我在此类上实现 IComparable 接口(interface)后,一些使用我的类的 c++ 代码意外地改变了它的行为。现在它抛出一个 NullReferenceException

DWORD UnitsAdapter::GetUnitNames([Out]array<MyClass^>^% unitNames)
{

...

unitNames = gcnew array<MyClass^>(10);

DWORD dwRet = BUMC_OK;
for (int i = 0; i < unitNames->Length; ++i)
{
unitNames[i] = nullptr;
unitNames[i] = CoCliUnitsHelper::getUnitName(unitIds[i]);

if (nullptr == unitNames[i])
dwRet = BUMC_NOT_COMPLETE;
}

return dwRet;

问题出在 if (nullptr == unitNames[i]) 行中,它开始使用 IComparable 实现来执行 ==运行!

原因是来自 cliext 实用程序头文件的模板。

//
// System::IComparable TEMPLATE COMPARISONS
//
template<typename _Value_t>
bool operator==(System::IComparable<_Value_t>^ _Left,
System::IComparable<_Value_t>^ _Right)
{ // test if _Left == _Right
return (_Left->CompareTo(_Right) == 0);
}

问题 1:我不是 C++ 专家,所以有人能解释一下为什么这个实现不对 _Left 执行空检查吗在调用 CompareTo() 方法之前?根据MSDN Guidelines for Overloading Equals() and Operator ==== 运算符中执行任何操作之前,必须先进行空检查。

 ...
// If both are null, or both are same instance, return true.
if (System.Object.ReferenceEquals(a, b))
{
return true;
}

// If one is null, but not both, return false.
if (((object)a == null) || ((object)b == null))
{
return false;
}
...

问题 2: 是否可能存在导致这种不可预测行为的使用缺陷?

最佳答案

so can someone explain me why this implementation does not perform a null check on _Left before calling CompareTo() method

因为编写它的人忽略了检查空值。

Is there probably some flaw in usage which leads to such an unpredictable behavior?

好吧,将空指针与某物进行比较可能是一种极端情况,但我当然不会将其称为“缺陷”。 == 的实现不正确。

要解决此问题,您可以撤销相等性检查和/或检查 null:

if (unitNames[i] == nullptr)
dwRet = BUMC_NOT_COMPLETE;

关于c# - STL/CLR 库使用 IComparable 实现 == 运算符并抛出 NullReferenceException,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/13346081/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com