2

C# 问题 (.net 3.5)。我有一个类 ImageData,它有一个字段 ushort[,] 像素。我正在处理专有图像格式。ImageData 类在构造函数中获取文件位置,然后打开文件扩展名以确定如何解码。在几个图像文件中,标题中有一个“位深度”字段。在我解码标题后,我将像素值读入“像素”数组。到目前为止,我没有超过 16bpp,所以我没事。但是如果我有 32bpp 怎么办?

我想要做的是在运行时确定像素的类型。我想在从标头中读取位深度之后并将像素数据复制到内存中之前执行此操作。有任何想法吗?

4

3 回答 3

2

我会说不要在构造函数中做这项工作——在我看来,构造函数不应该做这么多的工作。使用读取文件的工厂方法来确定位深度,然后让它构造该类的正确泛型变体并返回它。

于 2008-09-18T22:23:46.577 回答
2

为了简化您的问题,您希望能够拥有一个有时具有ushort[,] 像素字段(每像素 16 位)和其他时候具有uint32[,] 像素字段(每像素 32 位)的类. 有几种不同的方法可以实现这一目标。

您可以通过创建一个具有 32 位和 16 位子类的 Pixel 类来创建 ushort / uint32 的替代品,在 wazoo 上覆盖各种运算符,但这会产生很多开销,很难正确定位,甚至更难以确定如果它是正确的。或者,您可以为像素数据创建代理类(其中将包含 ushort[,] 或 uint32[,] 数组,并具有所有有用的必要访问器)。不利的一面是,您可能最终会在 ImageData 类中使用许多特殊情况代码,这些代码根据某些 16 位/32 位模式标志以一种或另一种方式执行。

我认为更好的解决方案是将 ImageData 子类化为 16 位和 32 位类,并使用工厂方法创建实例。例如 ImageData 是基类,ImageData16bpp 和 ImageData32bpp 是子类,静态方法 ImageData.Create(string imageFilename) 是工厂方法,它根据头数据创建 ImageData16bpp 或 ImageData32bpp。例如:

public static ImageData Create(string imageFilename)
{
   // ...
   ImageDataHeader imageHeader = ParseHeader(imageFilename);
   ImageData newImageData;
   if (imageHeader.bpp == 32)
   {
      newImageData = new ImageData32(imageFilename, imageHeader);
   }
   else
   {
      newImageData = new ImageData16(imageFilename, imageHeader);
   }
   // ...
   return newImageData;
}
于 2008-09-18T22:48:56.580 回答
0

让您的 decode 函数返回一个 Array 类型的对象,它是所有数组的基类。然后关心类型的人如果想要通过像素可以执行“if (a is ushort[,])”等等。如果这样做,则需要在 ImageData 中分配数组,而不是相反。

或者,调用者可能知道他们希望您使用哪种像素阵列。即使是 8bpp 或 16bpp 的图像,如果您将其解码为 32bpp 的屏幕,您也需要使用 uint 而不是 ushort。因此,您可以编写一个 ImageData 函数,该函数将解码为任何类型 T 的整数。

您的问题的根源是您不知道如何决定您想要什么样的输出格式。您需要首先弄清楚这一点,然后是程序语法。

于 2008-09-18T22:39:08.130 回答