來(lái)源:LAPACKE官方文檔
1.介紹
本文檔描述了一個(gè)LAPACK的兩級(jí)C接口,包括一個(gè)高級(jí)接口和一個(gè)中級(jí)接口。高級(jí)接口在內(nèi)部處理所有工作空間內(nèi)存分配,而中級(jí)接口要求用戶像原始FORTRAN接口那樣提供數(shù)組的工作空間。這兩個(gè)接口都提供了對(duì)列主矩陣和行主矩陣的支持。這兩個(gè)接口的原型、相關(guān)宏和類型定義都包含在頭文件lapacke.h中。
1.1.命名方式
高級(jí)接口的命名方案是采用FORTRAN LAPACK例程名,使其小寫,并添加前綴LAPACKE_。例如,LAPACK子例程DGETRF變成了LAPACKE_dgetrf。
中級(jí)接口的命名方案是采用FORTRAN LAPACK例程名,將其設(shè)置為小寫,然后添加前綴LAPACKE_和后綴_work,后綴_work表示用戶將提供工作空間。例如,LAPACK子例程DGETRF變成了LAPACKE_dgetrf_work。
1.2.復(fù)數(shù)類型
復(fù)數(shù)由宏lapack_complex_float和lapack_complex_double定義,它們分別表示單精度和雙精度復(fù)雜數(shù)據(jù)類型。始終假設(shè)實(shí)分量和虛分量連續(xù)存儲(chǔ)在內(nèi)存中,實(shí)分量先存儲(chǔ)。lapack_complex_float和lapack_complex_double宏可以是C99 _Complex類型、C結(jié)構(gòu)定義的類型、c++ STL復(fù)雜類型或自定義復(fù)雜類型。更多細(xì)節(jié)請(qǐng)參見lapacke.h。
1.3.數(shù)組參數(shù)
數(shù)組是作為指針傳遞的,而不是作為指向指針的指針。所有使用一個(gè)或多個(gè)二維數(shù)組(矩陣)作為指針的LAPACKE例程都接收一個(gè)int類型的額外參數(shù),這個(gè)參數(shù)必須等于LAPACK_ROW_MAJOR或LAPACK_COL_MAJOR,這兩個(gè)參數(shù)在lapacke.h中定義,指定該數(shù)組中的矩陣是按行主順序存儲(chǔ)還是按列主順序存儲(chǔ)。如果一個(gè)例程有多個(gè)數(shù)組輸入,它們必須都使用相同的順序。
注意,使用行-主順序可能比列-主順序需要更多的內(nèi)存和時(shí)間,因?yàn)槔瘫仨殞⑿?主順序轉(zhuǎn)換為底層LAPACK例程所需的列-主順序。FORTRAN LAPACK例程中的每個(gè)二維數(shù)組參數(shù)都有一個(gè)額外的參數(shù)來(lái)指定其前導(dǎo)維數(shù)(leading dimension)。對(duì)于以行為主的2D數(shù)組,假設(shè)一行中的元素是連續(xù)的,并且假設(shè)一行與下一行的元素之間存在領(lǐng)先維度的間隔。對(duì)于以列為主的2D數(shù)組,假定列中的元素是連續(xù)的,并且假定從一列到下一列的元素之間相隔一個(gè)前導(dǎo)維。例如:以列主序存儲(chǔ)M*N矩陣,用LDA表示leading dimension,則LDA = M,當(dāng)M=0時(shí),LDA=1。
1.4.參數(shù)別名
除非另外指定,只有輸入?yún)?shù)(即通過(guò)值和const限定符指定的數(shù)組傳遞的標(biāo)量)可以在調(diào)用LAPACK的C接口時(shí)合法地附加別名。
1.5.INFO參數(shù)
LAPACKE接口函數(shù)將它們的lapack_int返回值設(shè)置為INFO參數(shù)的值,該參數(shù)包含錯(cuò)誤和退出條件等信息。這與LAPACK例程不同,后者以FORTRAN整數(shù)參數(shù)的形式返回此信息。在LAPACKE,INFO的使用和在LAPACK完全一樣。如果INFO在FORTRAN中使用基于1的索引返回矩陣的行號(hào)或列號(hào),則該值不會(huì)為基于0的索引進(jìn)行調(diào)整。
1.6.NaN檢查
高級(jí)接口包括一個(gè)可選的,默認(rèn)的,在調(diào)用任何LAPACK例程之前對(duì)所有矩陣輸入進(jìn)行NaN檢查。此選項(xiàng)影響所有例程。如果輸入包含任何NaN,則輸入?yún)?shù)對(duì)應(yīng)的矩陣將被標(biāo)記為信息參數(shù)錯(cuò)誤。例如,如果發(fā)現(xiàn)第五個(gè)參數(shù)包含NaN,函數(shù)將返回值為-5??梢酝ㄟ^(guò)在lapacke.h中定義LAPACK_DISABLE_NAN_CHECK宏來(lái)禁用NaN檢查和其他參數(shù)。中間層接口不包含NaN檢查。
1.7.整型
在LAPACKE中,F(xiàn)ORTRAN類型為整數(shù)的變量被轉(zhuǎn)換為lapack_int。這符合可修改的整數(shù)類型大小,特別是給定的ILP64編程模型:將lapack_int重新定義為long int(8字節(jié))將足以支持該模型,因?yàn)閘apack_int默認(rèn)定義為int(4字節(jié)),支持LP64編程模型。
1.8.邏輯值
FORTRAN邏輯值被轉(zhuǎn)換為lapack_logical,它被定義為lapack_int。
1.9.內(nèi)存管理
所有的內(nèi)存管理都由函數(shù)LAPACKE_malloc和LAPACKE_free來(lái)處理。這允許用戶通過(guò)修改lapacke.h中的定義來(lái)輕松使用他們自己的內(nèi)存管理器,而不是默認(rèn)的內(nèi)存管理器。
這個(gè)接口應(yīng)該是線程安全的,只要這些內(nèi)存管理例程和底層的LAPACK例程是線程安全的。
1.10.新的錯(cuò)誤代碼
由于高級(jí)接口不使用工作數(shù)組,因此在用戶耗盡內(nèi)存時(shí)需要錯(cuò)誤通知。如果不能分配工作數(shù)組,函數(shù)將返回LAPACK_WORK_MEMORY_ERROR;如果沒(méi)有足夠的內(nèi)存來(lái)完成換位,則返回LAPACK_TRANSPOSE_MEMORY_ERROR。
2.舉例
LAPACK原生接口:
subroutine dgeqrf(????integer?M,
? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ?? integer?N,
? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ?? double precision,?
? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ?? dimension( lda, * )?A,
? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ?? integer?LDA,
? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ?? double precision, dimension( * )?TAU,
? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ?? double precision, dimension( * )?WORK,
? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ?? integer?LWORK,
? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ?? integer?INFO?)?
高層接口:
lapack_int m, n, lda, info;
double *a, *tau;
info = LAPACKE_dgeqrf( LAPACK_COL_MAJOR, m, n, a, lda, tau );
中層接口:
lapack_int m, n, lda, info, lwork;
double *a, *tau, *work;
info = LAPACKE_dgeqrf_work( LAPACK_COL_MAJOR, m, n, a, lda, tau, work, lwork);
其中,由于中層接口需要用戶提供所需要的工作空間,由一個(gè)work數(shù)組表示工作空間,其長(zhǎng)度用 lwork記錄,最小為n。
?