示例程序将图像的像素颜色数据装入到一个字节数组
ImagePixelData
中,然后,使用
Parallel.For()
方法对所有像素的颜色值取反,再显示到屏幕上,以下是实现并行图像处理的核心代码:
Parallel.For(0, ImagePixelData.Length, (i) =>
{
byte value = ImagePixelData[i];
ImagePixelData[i] = (byte)(~value);
});
有关此示例程序的技术关键点请看本节的“多懂一点”。
多懂一点:
示例程序MyImageProcessor的学习指导
示例程序MyImageProcessor是一个WPF应用程序,下面简要介绍一下它的技术关键点。
在WPF中,抽象类BitmapSource类用于指代一个图像,其子类BitmapImage代表一个“真实”的图像对象。
把图像文件路径字串作为参数,调用BitmapImage的构造函数可以创建一个BitmapImage对象。
在WPF中,显示图像使用的是Image控件,只需将它的Source属性设置为一个BitmapSource对象,它就能显示指定的图像,参见以下代码
BitmapSource bmpSource = new BitmapImage(new Uri(
图像文件名
));
image1.Source=bmpSource; //
显示图像
示例程序的关键之处在于如何从BitmapSource对象中提取像素的颜色数据。这里需要了解一下计算机图像处理领域的基础知识。
每个图像都有一个以像素个数为单位的尺寸,比如我们常用于设置桌面背景的壁纸通常拥有1024*768的尺寸,这个尺寸指的是“图像宽为1024个像素,高为768像素”。
对于不同类型的图像文件,很有可能每个像素所关联的数据量是不同的,比如有的图像使用3个字节来保存像素颜色的R、G、B三个分量,而有的则使用4个字节来保存像素的颜色数据(在R、G、B三个分量的基础上再加上一Alpha值,用于表示颜色的透明度)。
幸运的是,通过BitmapImage对象的Format.BitsPerPixel属性我们可以知道每个像素占用的位数,将其除以8就得到了单个像素所占用的字节数,而不需要编写代码处理各种类型的图像文件。
另一个知识点是需要知道图像每行像素数据的总字节数(这个数值在计算机图像处理领域被称为做位图图像的“stride”值)。为了提升性能,通常要求这个数值能被4整除,但图像文件不可能总满足这个要求,为此,有可能需要“补”上若干个字节以“凑”成一个可被4整除的数。
在WPF中,BitmapSource类提供了一个CopyPixels()方法可以将图像的像素数据复制到一个字节数组里,而另一个它的另一个Create()方法可以从字节数组中重新提取数据创建一个新的BitmapSource对象。
掌握了以上知识,就能看得懂示例程序中的代码了,以下是示例程序中的代码片断:
BitmapSource bmpSource=null;
int stride=0;
byte[] ImagePixelData=null;
//
装入图像的像素数据到字节数组中。
private void LoadImage(string ImagePath)
{
//
创建
BitmapSource
对象
bmpSource = new BitmapImage(new Uri(ImagePath));
//
计算图像的
stide
值
stride = bmpSource.PixelWidth * bmpSource.Format.BitsPerPixel / 8;
stride += 4-stride % 4; //
补上几个字节,使其可以被
4
整除
//
创建字节数组,注意其大小要合适,可以放得下所有的图像数据
int ImagePixelDataSize = stride * bmpSource.PixelHeight *
bmpSource.Format.BitsPerPixel / 8;
ImagePixelData = new byte[ImagePixelDataSize];
//
复制图像数据到字节数组中
bmpSource.CopyPixels(ImagePixelData, stride, 0);
}
其余的代码就很好懂了,请读者自行阅读示例源码。
19.6.2 并行计算的未来之路
当前计算机中普遍装备了“双核”
CPU
,一些新购置的计算机更是装备了“四核”
CPU
,随着
CPU
在“多核化”之路上越走越远,并行计算已成为软件技术确定无疑的发展方向。
与
CPU
多核化趋抛同时出现的是计算机网络的“无孔不入”,由此可知,分布式的软件系统也将成为软件技术发展的另一个方向,而分布式的软件系统“天生”就是“并行”的,因此,
未来的软件系统一定同时兼具有“并行”和“分布”两大特点
。
要开发并行的程序,可以利用
.NET 4.0
新加入的并行扩展;要开发分布式的软件系统,可以使用
.NET 4.0
中功能得到进一步增强的
WCF
。本书第
9
篇将详细
WCF
。
如果将本章介绍的并行计算技术与本书第
9
篇介绍的
WCF
技术结合起来,在微软平台之上,我们就拥有了前所未有的强有力的开发工具,可以用它来开发高度分布和高度并行的软件系统,解决更为复杂的问题,其应用前景非常广阔。
我们看到,
.NET 4.0
已经在并行计算之路上迈出了第一步,而这一步一旦迈出,就不会停止下来。
并行计算的大幕刚刚拉开,精彩的剧目即将上演,让我们拭目以待吧!