c# - 如何从 Array.ConstrainedCopy 获取 InvalidCastException

标签 c# .net arrays

这里是讨论的示例代码(考虑 Reptile"is"Animal 和 Mammal“也是”Animal)

Animal[] reptiles = new Reptile[] 
    { new Reptile("lizard"), new Reptile("snake") };

Animal[] animals = new Animal[]
    { new Reptile("alligator"), new Mammal("dolphin") };

try
{
  Array.ConstrainedCopy(animals, 0, reptiles, 0, 2);
}
catch (ArrayTypeMismatchException atme)
{
  Console.WriteLine('[' + String.Join<Animal>(", ", reptiles) + ']');
}

当我运行这段代码时,我得到一个 ArrayTypeMismatchException,作为注释

Array.ConstrainedCopy will only work on array types that are provably compatible, without any form of boxing, unboxing, widening, or casting of each array element. Change the array types (i.e., copy a Derived[] to a Base[]), or use a mitigation strategy in the CER for Array.Copy's less powerful reliability contract, such as cloning the array or throwing away the potentially corrupt destination array.

但是,当我查看 MSDN 时我看到此方法还会抛出 InvalidCastException。抛出 InvalidCastException 的条件是:

At least one element in sourceArray cannot be cast to the type of destinationArray.

所以我很困惑,如果正如它所说永远不能对数组元素进行任何转换,您如何从该方法中得到 InvalidCastException?

最佳答案

如果无法访问 Array.Copy 的实际 native 实现,我们最多只能检查 Shared Source CLI .以下是 clr\src\vm\comsystem.cpp 中的相关代码行:

FCIMPL6(void, SystemNative::ArrayCopy, ArrayBase* m_pSrc, INT32 m_iSrcIndex, ArrayBase* m_pDst, INT32 m_iDstIndex, INT32 m_iLength, CLR_BOOL reliable)
{
    // ...

    r = CanAssignArrayTypeNoGC(gc.pSrc, gc.pDst);

    if (r == AssignWrongType) {
        // [Throw ArrayTypeMismatchException]
    }

    if (r == AssignWillWork) {
        // [Copy the array using memmove, which won't throw any exception]
        return;
    }
    else if (reliable) {
        // [Throw ArrayTypeMismatchException]
    }

    // [Handle other cases]
}

Array.ConstrainedCopy 调用 SystemNative::ArrayCopy 并将 reliable 参数设置为 TRUE 时,要么使用 memmove 复制数组或抛出 ArrayTypeMismatchException。在这两种情况下都不会抛出 InvalidCastException

关于c# - 如何从 Array.ConstrainedCopy 获取 InvalidCastException,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/18865207/

相关文章:

c# - C# 窗体的大小和位置

c# - 获取联系人容器 Xamarin.iOS 时出现问题

c# - 从 .net 的角度来看,exe 和 dll 之间有什么特别的区别吗?

Perl 数值排序 : how to ignore leading alpha character

javascript - 通过 ng-repeat 循环中其他数组的包含来过滤数组

java - Android 手机上的文本文件

c# - 如何刷新 Entity Framework Core DBContext?

c# - Form.Owner - 拥有的表单不递归关闭/隐藏

c# - 连续发送鼠标位置到另一台机器

.net - 如何去除 MAUI 控件中的粗焦点边框?