一.起因
安裝和使用 blitz++ 時經常遇到問 , 檢視了 ccboy 寫的《 VC++ _NET 2003 –安裝和使用 Boost 1_30 和 Blitz++0_6 》,但他寫的不詳細 , Blitz 的官方文檔也不清楚 , 隻好自己來 , 花了不少時間才初步弄清楚。
二. Blitz 簡介
大家知道 Fortran 是公認的科學計算程式設計語言 , 大量數值計算庫都是基于 fortran 的 , 如 lapack. 而 blitz++ 則為科學計算人員提供了面向對象的 C++ 的數值計算程式庫 , 速度能與 fortran77/90 比對 .
用過 matlab 的人知道 , matlab 是一種基于矩陣的第四代語言 , 它将每個變量都視作矩陣 , 指派起來比起 c/c++/java 等主流語言起來非常友善 , 而 blitz++ 也提供了這種矩陣的強大操作 , 而且性能比起 matlab 要快很多 , 這是因為兩種的語言特性所決定的 .
Blitz++ 最新的版本中提供了數組和向量 ( 即矩陣 ), 随機數産生器 , 小向量和矩陣 .
值得注意的是 , 與其它數值計算包相比較 , blitz 是非常有個性的 , 它不求高大全 , 如它并沒有提供所有的矩陣操作功能 , 如求特征向量 ,FFT 分析 等 . 它的特點在于面向對象、數組操作文法和模闆操作( But the main focus of blitz is on array syntax and stencil operations ) <b>[4] </b>。矩陣操作功能,想起 STL 中的VALARRY 了嗎? VALARRAY 中的功能這裡都實作和加強了。這個在測試項目 MT1 中可以初步顯示 .
三.安裝與測試
1) 安裝 Blitz++-0.7 通用代碼
首先要安裝最原始的代碼包 , 源代碼是跨平台的 , 隻要 blitz 支援 .
2) 安裝 Blitz-VS.NET1.5 -FOR vs.net2003 項目
将 blitz-VS.NET zip 解壓縮 , 它的主目錄與 C:\vc\Blitz++-0.7 的相同 , 我們假設它為 C:\vc\Blitz-VS.NET1.6 , 目錄結構如下 :
Blitz\
Blitz-Testsuite\
Blitz-Library.ncb
Blitz-Library.sln
Blitz-Library.suo
blitz\ 裡面是 config.h, 它定義了 blitz 相關的宏變量 , 如 BZ_HAVE_COMPLEX, BZ_HAVE_STL 等等 , 這是每個項目必須用到的 .
blitz 目錄裡面還有一個 VC 項目檔案 , 這個項目是用來生成 blitz.lib 檔案的, 稍後我們将提到如何設定生成。
3) 生成 blitz.lib
啟動 vs.net2003, 設定 : 工具 -> 選項 -> 項目 ->VC++ 目錄 , 在 ” 包含檔案 ” 中添加 blitz-0.7 的路徑 ( 即 cl 中的 /I 參數 ) ,如 C:\vc\blitz 。 下圖為我的配置
使用 vs.net2003 打開為 C:\vc\Blitz-VS.NET1.6\blitz\ blitz.vcproj, 如上所述 , 我們正是用這個項目來産生 blitz.lib 的 . 它所使用的源檔案就是Blitz++-0.7\src\globals.cpp, 因為代碼原作者為了保持代碼的唯一份 , 是以沒有包括到這個 for vs.net 的壓縮包中 , 你要将原 Blitz++ 目錄下的 src 目錄拷貝到這裡 . 如将 C:\vc\Blitz++-0.7\src 拷貝到 C:\vc\Blitz-VS.NET1.6\src
編譯生成 blitz.lib. 編譯時會出現錯誤提示 , 如 error PRJ0019: 工具從 ”copying blitz_d.lib..” 不必理會 , 這是 blitz 的 BUG, 在 DEBUG 或 release目錄下已經生成了我們所需的檔案 ,debug 版本的為 blitz_d.lib, release 版本的為 blitz.lib.
此時 , 為了以後的版本都能使用此 lib 檔案 , 我們可以配置一下全局選項 :
首先在 \Blitz-VS.NET1.6\ 下建立一 lib 目錄 , 将 blitz.lib 和 blitz_d.lib 拷貝進去 . 在工具 -> 選項 -> 項目 ->VC++ 目錄 -> 庫檔案下添加我們 lib 的路徑
4) 編譯和測試 blitz-testsuit
用 vs.net2003 打開 Blitz-Library.sln, 裡面包括了 54 個測試用例 .
将 Blitz++-0.7 下的 testsuite 目錄拷貝到 Blitz-VS.NET1.6, 原因也是為了保持代碼的唯一性 , 據作者所說 [4] .
要确認這點 , 可以打開項目配置檔案 vsproj, 用文本編輯器如 notepad 打開 , 檢視
<Files>
<Filter
Name="Source Files"
Filter="cpp;c;cxx;def;odl;idl;hpj;bat;asm">
<File
RelativePath="..\..\testsuite\ctors.cpp">
</File>
</Filter>
</Files>
确定項目選項輸入庫為 blitz_d.lib 或 blitz.lib
編譯 , 執行 .
1) 如測試 ABA1, 這是求數組的最大值的測試
源代碼為 :
#include
BZ_USING_NAMESPACE(blitz)
int main()
{
Array<double,1> psiElem(3);
psiElem =
-0.121990517304243,-0.099118834514638,-0.164750336116265;
double psi_max = blitz::max(psiElem);
cout << "psiElem = " << psiElem << endl;
cout << "psi_max = " << psi_max << endl;
}
結果為 :
psiElem = 3
[ -0.121991 -0.0991188 -0.16475 ]
psi_max = -0.0991188
2) 測試 MT1 – 主要測試矩陣指派與操作文法 ,index 的使用等等 .
源碼 :
#if 0
BZ_DECLARE_STENCIL2(kinEnergy,A,B)
B=Laplacian3D(A);
BZ_END_STENCIL_WITH_SHAPE(shape(-1,-1,-1),shape(1,1,1))
typedef complex<double> T_num;
typedef Array array3d;,3>
const int N=5;
array3d A(N,N,N);
array3d B(N,N,N);
// Fill a three-dimensional array with a Gaussian function
firstIndex i;
secondIndex j;
thirdIndex k;
float midpoint = 15/2.;
float c = - 1/3.0;
A = exp(c * (sqr(i-midpoint) + sqr(j-midpoint)
+ sqr(k-midpoint)));
applyStencil(kinEnergy(), A, B);
Array out_view(B.data(),shape(N*N*N));,1>
cout << out_view;
#endif
BZ_DECLARE_STENCIL2(footprint,A,B)
B = Laplacian2D4(A);
BZ_END_STENCIL_WITH_SHAPE(shape(-2,-2),shape(+2,+2))
int N = 9;
Array<double,2> A(N,N), B(N,N);
A = 0;
A(4,4) = 1;
applyStencil(footprint(), A, B);
cout << B(Range(2,6),Range(2,6)) << endl;
5 x 5
[ 0 0 -1 0 0
0 0 16 0 0
-1 16 -60 16 -1
0 0 -1 0 0 ]
五.在自己的項目中使用
一個很簡單的例子 ,
建立個人項目後 , 注意以下幾件事 :
1. 添加了 lib 或正确配置了 lib 的路徑 : 将 blitz.lib 拷貝到項目下或在項目屬性中配置好引用路徑 .
2. 添加了 config.h, 将原來我們編譯 blitz.lib 的宏定義檔案拷貝過來 .
3. 使用了 using namespace blitz
4. 正确使用 blitz 的庫對象
#include "stdafx.h"
#include "config.h"
using namespace blitz;
complex<int> c(4,8);
cout << c << endl;
Array<int,2> ar(2,2) ;
ar =1,1,
2,2;
cout << ar <;>
在編譯時 , 各種配置都要非常小心 , 一不小心就會出錯 , 按照以上的步驟一步一步來 , 應該不會有太大的錯誤 , 有任何問題或建議 , 可與我聯系 [email protected]
六.參考文獻:
1. [blitz] blitz 官方首頁,文檔
3. [ccboy] ccboy 寫的 VC++ _NET 2003 –安裝和使用 Boost 1_30 和 Blitz++0_6
4. [Julian C.]emails
/File/DIV>