999精品在线视频,手机成人午夜在线视频,久久不卡国产精品无码,中日无码在线观看,成人av手机在线观看,日韩精品亚洲一区中文字幕,亚洲av无码人妻,四虎国产在线观看 ?

Fortran 90借用C++函數模板

2013-01-22 03:45:41畢蘇萍周振紅赫曉慧
鄭州大學學報(工學版) 2013年2期

畢蘇萍,周振紅,赫曉慧

(1.鄭州大學 土木工程學院,河南 鄭州450001;2.鄭州大學水利與環境學院,河南鄭州450001)

0 引言

在計算機科學與技術領域,泛型編程(Generic Programming)具有廣泛的意義.用泛型編程先驅(Alexander Stepanov)的話來說:泛型編程是對算法、數據結構進行抽象和分類,其目標是遞增式構造實用、高效、抽象的算法、數據結構的系統目錄結構或框架[1].簡言之,泛型編程是將算法、數據結構由具體的實例提升到一般、抽象的形式,使之可以操作不同的數據類型.

C++提供了模板(包括類模板和函數模板),并逐步積累有相對完善的標準模板庫STL[2],對泛型編程給予了很好的支持.Fortran從77到90[3]、2003[4]對泛型編程的支持不斷加強,但直至2008也沒能提供模板工具[5].假如 Fortran 90借用C++函數模板能夠獲得成果,那么無疑會極大地拓展C++的應用空間,給科學與工程計算增添新的活力.筆者就此展開探討,示例程序測試環境:C++為 VC 6.0,Fortran 90為 Compaq Visual Fortran 6.6.

1 C++特殊的重載函數簇—函數模板

C++支持函數重載,允許在參數表不同的前提下于同一編譯單元定義幾個同名函數,調用時依據參數表最佳匹配的原則自動選擇合適的函數.比如在編程計算中,1/2整數除結果為0,1.0/2.0實數除結果為0.5,筆者用兩個重載函數予以驗證(當中的參數采取引用傳遞,和Fortran 90的參數傳遞保持一致):

int divid(int&a,int&b){return a/b;}

float divid(float&a,float&b){return a/b;}.

測試上列重載函數的主函數為:

void main(void){

int a=1,b=2;float x=1.0,y=2.0;

cout<< ″1/2=″<< divid(a,b) << endl;//整數除

cout<<″1.0/2.0=″<< divid(x,y) <<endl;}//實數除.程序運行結果為:

1/2=0

1.0/2.0=0.5.

觀察上列重載函數,不難發現兩個特點:①是接口類同,惟有函數結果、參數的數據類型不同;②是算法相同.在這種情況下,將上列重載函數抽象為一個函數模板、用一個泛型T代替函數結果、參數的數據類型:

template<typename T>//亦可用class代替typename聲明函數模板中的泛型

T divid(T&a,T&b){return a/b;}//divid,a,b的類型均為泛型T

同樣的測試主函數,當調用divid(a,b)函數時構造的是divid<int>函數模板實例,而當調用divid(1.0,2.0)函數時則構造的是divid<float>函數模板實例,分別與整型和實型重載函數divid相當,所以測試結果與上列重載函數的相同.說明上列重載函數與函數模板的效果完全相同,從而證明,可以將函數模板看成是一特殊的重載函數簇.

2 Fortran 90模擬C++函數重載

要模擬C++函數重載,有必要先回顧一下Fortran 90接口塊的引入.Fortran 90共有4種程序單元:主程序、外部例程(子程序和函數統稱為例程)、模塊和數據塊,當被調程序為外部例程時,為使編譯器產生正確調用,Fortran 90要求在調用程序中建立被調外部例程的接口塊,以明確其接口信息:例程名、例程實現機制(函數,或者子程序)、函數類型、參數的類型、屬性及傳遞方式.當被調外部例程接口簡單時,是否在調用程序中建立其接口塊是可選的;當接口復雜時,建立其接口塊就成為必須的.比如:外部函數返回數組或變長字符串,參數中有可選參數,有假定形狀數組、指針或目標屬性參數,有例程參數(即例程作參數,類似于C語言中的函數指針作參數)等.接口塊的構造形式為:

Interface

Function/Subroutine例程名 (形參表)!接口

形參聲明(包括函數結果類型聲明)

End Function/Subroutine

End Interface.

Fortran 90不直接支持例程重載,不允許定義同名的外部例程,但允許將幾個外部例程接口置于同一接口塊內,并給接口塊命名、以接口塊名作為各個外部例程的統稱,調用時依據接口匹配的原則自動選擇相對應的外部例程,從而推出了支持泛型編程的接口塊(姑且稱為泛型接口塊).

Interface泛型接口塊名

接口體

End Interface.

其中,接口體由幾個外部例程或者模塊例程接口構成.

下面用Fortran 90實現前述C++函數重載示例.首先,用外部例程(函數)div_int和div_real分別實現C++整數除和實數除重載函數,其實現代碼只比各自的接口多一行.

div_int=x/y或div_real=x/y

包含其泛型接口塊(divid)的主程序為:

PROGRAM test_overloading

Implicit None

Interface divid!泛型接口塊

Integer Function div_int(x,y)!外部例程接口

Integer,Intent(IN)::x,y

End Function

Real Function div_real(x,y)!外部例程接口

Real,Intent(IN)::x,y

End Function

End Interface

WRITE(* ,*)'1/2=',divid(1,2)!整數除

WRITE(* ,*)'1.0/2.0=',divid(1.0,2.0)!實數除

END PROGRAM.程序運行結果為:

1/2=0

1.0/2.0=0.500 000 0.

調用程序使用了統一的泛型接口塊名divid,而真正調用的是與接口匹配的div_int、div_real外部例程或稱為“重載”例程;C++盡管重載函數名稱相同,但由于編譯時增加的特殊修飾其目標函數名并不相同,這樣才有可能依據不同的參數表調用與之匹配的重載函數.可見:這里的外部例程加泛型接口塊與C++重載函數的效果是相同的.

3 C++函數模板實例化為“重載”例程

無論是C++的重載函數還是C++的函數模板,都只有在C++環境中才能直接調用或實例化,即便在其子集C語言中也無法直接使用.推想背后的道理,可能是編譯器的功能所致.C++編譯器能夠添加特殊的命名修飾,據此可以判明對應的重載函數或構造不同的函數模板實例;C編譯器無此功能,所以它不支持函數重載或函數模板,C++的重載函數或函數模板也禁止使用C鏈接(其作用是消除C++編譯器的特殊命名修飾).

前面筆者已經探討過:Fortran 90在泛型接口塊的支持下,可以將普通外部例程當作是C++的重載函數,進而也可以看成是C++函數模板實例.這樣一來,如果設法在C++環境中將函數模板實例化為 Fortran 90“重載”例程,就可采取C++與 Fortran的混合編譯[6],從而在 Fortran 90環境中使用C++函數模板.循這一思路,在前述C++函數模板示例代碼下面增加包裝子

extern ″C″{

int__stdcall DIV_INT(int&a,int&b){return divid(a,b);}

float__stdcall DIV_REAL(float&a,float&b){return divid(a,b);}}

為使接口與Fortran 90的“重載”例程接口保持一致,上列設置采取C鏈接、__stdcall調用約定、大寫命名約定及引用參數傳遞方式.此處的包裝子有兩個作用:對內,實例化函數模板;對外,承擔Fortran 90“重載”例程.

將前述C++函數模板和包裝子單獨保存為一個文件(.cpp),并與 Fortran 90主程序文件(.f90)置于同一項目.程序運行結果,與模擬C++函數重載示例的結果相同.

4 結論

將C++函數模板看成接口相似、算法相同的特殊重載函數簇,在泛型接口塊支持下,將Fortran 90外部例程模擬成C++重載函數,然后在C++環境中添加包裝子,將函數模板實例化成Fortran 90“重載”例程,進而在Fortran 90環境中以正常方式使用C++函數模板.像C等其它語言要借用C++函數模板,也可采取同樣的思路.

[1]ALEXANDER A.STEPANOV.Generic programming[EB/OL].http://www.stepanovpapers.com/,2012.5.22.

[2]DAVID V,NICOLAI M J.C++Templates:The Complete Guide[M].Addison Wesley,2003.

[3]周振紅,郭恒亮,張君靜,等.Fortran 90/95高級程序設計[M].鄭州:黃河水利出版社,2005.

[4]Fortran 2003 standard[EB/OL].http://www.j3-fortran.org/doc/year/04/04-007.pdf,2012.5.22.

[5]CHIVERS S.Introduction to programming with fortran with coverage of fortran 90,95,2003,2008 and 77[M].Springer,2012.

[6]任慧,周振紅,張成才.Fortran與C/C++的混合編譯[J].計算機工程與設計,2007,28(17):4096-4098、4111.

主站蜘蛛池模板: 真实国产乱子伦视频| 在线视频亚洲欧美| 久久香蕉国产线看观看亚洲片| 精品免费在线视频| 99国产精品国产高清一区二区| 久青草网站| 亚洲精品第一在线观看视频| 一级毛片中文字幕| 欧美一区二区丝袜高跟鞋| 香蕉久久国产超碰青草| 美女裸体18禁网站| 久草性视频| 欧美日韩免费在线视频| 小说 亚洲 无码 精品| 日韩无码一二三区| 午夜在线不卡| 另类重口100页在线播放| 国产一级妓女av网站| 91精品情国产情侣高潮对白蜜| 国产美女91视频| 亚洲一区二区黄色| 98精品全国免费观看视频| 欧美日韩第二页| 国产成熟女人性满足视频| 噜噜噜久久| 在线播放91| 国产欧美另类| 亚洲人成网18禁| 青青操国产视频| 国产精品yjizz视频网一二区| 色综合国产| 波多野结衣在线se| 午夜国产理论| 色天天综合久久久久综合片| 国产综合色在线视频播放线视| 日韩福利视频导航| 极品性荡少妇一区二区色欲| 国产一级在线播放| 国产高清无码第一十页在线观看| 国产一级特黄aa级特黄裸毛片| 成人午夜久久| 国产在线观看第二页| 91视频首页| 亚洲精品成人片在线播放| 国产精品香蕉在线| 嫩草影院在线观看精品视频| 亚洲中文无码av永久伊人| 日韩精品久久无码中文字幕色欲| 国产一级毛片高清完整视频版| 亚洲无线观看| 午夜丁香婷婷| 国产小视频免费观看| 亚洲高清无码久久久| 99精品视频在线观看免费播放| 强乱中文字幕在线播放不卡| 国产福利免费视频| 在线亚洲小视频| 思思99热精品在线| 97在线免费| 婷婷亚洲视频| 亚洲婷婷在线视频| 日韩福利视频导航| 国产噜噜噜视频在线观看 | 国产视频久久久久| 精品伊人久久大香线蕉网站| 思思热精品在线8| 午夜久久影院| 久久九九热视频| 一级黄色网站在线免费看| 欧美激情成人网| 激情综合婷婷丁香五月尤物| 国外欧美一区另类中文字幕| 亚洲无码免费黄色网址| 欧美一区精品| 中文字幕欧美日韩| 国产日韩久久久久无码精品| 久久公开视频| 国产日韩欧美精品区性色| 麻豆AV网站免费进入| 欧美天堂在线| 成人亚洲国产| 蝌蚪国产精品视频第一页|