0

我需要在 C# 中将 short[] 转换为 ushort[]

public ushort[] Pixels16bits;

 GrayscalePixelDataS16 Pixeldata = PixelDataFactory.Create(img.PixelData, 0) as GrayscalePixelDataS16; //Pixeldata has short[] values

Pixels16bits = pixeldata; //Here's where I struggle, I need to convert to ushort prior to assign to pixels16bits

谢谢

4

2 回答 2

3

我看到几个选项:

img.PixelData.Cast<ushort>().ToArray();

也许:

img.PixelData.Select(Convert.ToUInt16).ToArray();

两者都利用 LINQ 将转换函数应用于集合的能力。

于 2014-06-20T17:06:03.610 回答
1

作为正常的解决方案,我建议:

unsigned = ConvertAll(signed, i => (ushort)i)

这比 LINQ 解决方案产生的垃圾更少,同时同样简洁易读。

一个好的老式循环也是一个考虑因素,因为它允许您转换为现有数组,而不是分配一个新数组。

作为价值转换功能,您可以使用:

  • i => (ushort)i默认情况下不抱怨整数溢出的 C 风格转换(您可以在编译器设置中更改它)

    要真正明确,您可以编写i => unchecked((ushort)i)i => checked((ushort)i)取决于您想要的行为。

  • Convert.ToInt16OverflowException如果输入大于short.MaxValue编译器设置,则抛出一个。

有一个有趣/邪恶的技巧可以让您在不实际转换的情况下将 ashort[]视为 a :ushort[]

short[] signed = new short[]{-1};
signed.GetType().Dump();// short[]

ushort[] unsigned = (ushort[])(object)signed;

unsigned.GetType().Dump();// still short[]
unsigned[0].Dump(); // 65535

它编译并且不会引发运行时错误。

CLR 规范说明了这一点ushort[]并且short[]是兼容的,因为转换shortushort保留表示。这是一种类似于数组协方差的机制。

另一方面,C# 规范不允许这种转换。这就是为什么中间转换object是必要的。

于 2014-06-20T17:15:27.117 回答