Fortran与VisualC_混合编程研究

  1. 1、下载文档前请自行甄别文档内容的完整性,平台不提供额外的编辑、内容补充、找答案等附加服务。
  2. 2、"仅部分预览"的文档,不可在线预览部分如存在完整性等问题,可反馈申请退款(可完整预览的文档不适用该条件!)。
  3. 3、如文档侵犯您的权益,请联系客服反馈,我们会尽快为您处理(人工客服工作时间:9:00-18:30)。

在数值计算的编程中 , 经常要借助于数组对同
86
武汉大学学报( 工学版)
2001
类型的有序数据进行处理 . 在 Visual C ++ 调用含 有数组参数的 Fortran 过程时 , 须注意它们在数组 的声明形式 、存储 顺序和下标起始 值规定上的差 异. 比如要声明一两行三列的二维数组 , 在 Fortran 中声明为 A( 2 , 3) , 下标从 1 开始 , 在内存中的存储 顺序为 :
程. Visual C ++ 缺省参数传递方式是值传递 , 在 传值方式下 , 所传递的是参数的当前值 , 被调用过 程对参数的修改不会对调用过程的参数值产生影 响. Fortran 中的 C 和 STDCALL 调用约定 , 不仅影 响目标程序的标识符 , 而且也影响过程参数的传递 方式 . 在 Fortran 过程中 , 通过声明 C 和 STDCALL 调 用约定 , 可以将参数的缺省引用传递方式改为值传 递. 对于具体的某个参数又可以用 REFERENCE 和 VALUE 属性规定其传递方式分别为引用传递和值 传递 , 且 REFERENCE 和 VALUE 属 性 覆 盖 C 和 STDCALL 调用约定对参数 传递方式的 规定 . 仍以 前面的 Fortran 函数 Fmax ( a , b) 为例 : ! DEC $ ATTRIBUTES C : : Fmax ! DEC $ ATTRIBUTES REFERENCE : : b 上面第一行规定了函数 Fmax 中的两个参数为 值传递方式 , 第二行又将其中的一个参数 b 规定为 引用传递方式 . Visual C ++ 中对应的声明为 extern ” C”{ float -cdecl fmax( float a , float & b) ; } , 其中 , & b 标示参数 b 为引用传递 . 需要注意的是 , 在进行函 数调用时 , 第二个参数须是一 float 型的变量 , 不能 为常量 .
1 标识符命名约定
标识符指全局变量名和过程名 , 它代表了特定 的地址 . 命名约定指在源程序编译生成目标程序的 过程中 , 源程 序 中的 标 识符 将 会发 生怎 样 的改 变 . Fortran 与 Visual C/C ++ 在不同的调用约定 下生成目标程序的标识符列于表 1 . 其中 : name 是 源程序中的标识符 ; n 是过程参数在堆栈中占据的
-name @n 保留原有大小写 ? name @@ 保留原有大小写 _decoration
Fortran 中过 程分 为子 程序 和函 数 , 而 Visual C ++ 中的过程只有函数 , Fortran 中的子程序相当 于 Visual C ++ 中返回数据类型为 void 的函数 . 现 以 Visual C ++ 调用 Fortran 函数为例 , 说明如何统 一两种语言的标识符命名约定 . Fortran( DIGITAL Visual Fortran) : REAL( 4)FUNCTION Fmax( a , b) ! DEC $ ATTRIBUTES DLLEXPORT : : Fmax ! DEC $ ATTRIBUTES VALUE : : a ,b
周振红 , 颜国红 , 吴虹娟
1 2 1
( 1.武汉大学水利水电 学院 , 湖北 武汉 430072 ; 2.长江 水利委员会计划局 , 湖北 武汉 430010)
对 32 位 Fortran 与 Visual C ++ 的混合编程进行了较为系统的 探索和 研究 . 指出关 键问题 是如何 使两种 摘要 : 语言在标识符命名约定 、参数传递方式和参数数 据类型上保持一致 , 并对此给出了具体的实施方法 . 混合编程 ; 动态链接库 ; 面向对象程序 设计 关键词 : TP 311 . 5 文献标识码 : A 中图分类号 :
收稿日期 : 2000 -04 -20
[ 5]
作者简介 : 周振红( 1963 -), 男 , 山 东蓬莱人 , 博士 , 从事河流水沙数值模拟及科学计算可视化方面的研究 .
第 2 期
周振红等 : Fortran 与 Visual C ++ 混合编程研究
85
REAL( 4) : : a,b END FUNCTION Visual C ++: extern ” C ” { float - -stdcall Fmax ( float a , float b) ; } 上述 Fortran 程序中的 ! DEC $ ATTRIBUTES DLLEXPORT : : Fmax 为动 态链 接库 函数 的导 出声 明 , ! DEC $ ATTRIBUTES VALUE : : a , b 将 参数 a 和 b 的传递方式规定为值传递( 缺省情况下 , Fortran 为引用传递 , Visual C ++ 为值传递) , 其 Fortran 动态链接库中的标识符为 -FMAX @8 , 恰好与 Visual C ++ 去掉修饰后的 — stdcall 约定保持一致 . 在上述 Fortran 程序中 , 若将属性规定改为 : ! DEC $ ATTRIBUTES C : : Fmax 或 ! DEC $ ATTRIBUTES STDCALL : : Fmax 目标程序的标识符分别为 -fmax 和 -fmax @ 8 , Visual C ++ 中对应的声明形式为 : extern ” C” { float - -cdecl fmax ( float a , float b) ; }或 extern ” C” { float - -stdcall fmax( float a , float b) ; } 如果在 Fortran 源程序中 使用 ALIAS 属性 , 可 强制目标程序中的标识保持原样 , 即保留原有的大 小写 . 如 在 Fortran 程 序 中 采 用 ! DEC $ ATTRIBUTES C , ALIAS : ' -Fmax ' : : Fmax 形式进行声 明 , 目标程序标识符由 ALIAS 属性规定为 Fmax , 忽略 C 将 标 识 符 全 部 转 为 小 写 的 约 定 , Visual C ++ 中对应的声明形式为 extern ”C” { float - cdecl Fmax( float a , float b) ; } .
Fortran INTEGER( 2) INTEGER( 4) REAL( 4) REAL( 8) Visual C ++ short int , long float double
2 参数传递方式
混合语言编程中 , 不同语言间相互交换和访问 数据的方法 之一是 参数传 递 . 在 Fortran 和 Visual C ++ 过程之间可以用参数传递的方法交换数据 . 参数的传递有值传递和引用传递两种方式 , 前者将 参数值压入堆栈 , 后者将参数地址压入堆栈 . 在混 合语言编程中必须保证参数传递方式的一致性 . 如果不对参数传递的方式进行特别声明 , 参数 将按照缺省方式传递 . 以一般的整型 、实型参数为 例 , Fortran 缺省参数传递方式是引用传递 , 在引用 方式下 , 所传递的是参数的地址 , 如果在被调用过 程中对参数进行了修改 , 这一修改将带回到引用过
第 34 卷第 2 期 2001 年 4 月
武汉大学学报( 工学版) Engineering Journal of Wuhan University
Baidu Nhomakorabea
Vol . 34 No . 2 Apr . 2001
文章编号 : 1006 -155X( 2001) 02 -084 -04
Fortran 与 Visual C ++ 混合编程研究
A( 1 , 1) A( 2 , 1) A( 1 , 2) A( 2 , 2) A( 1 , 3) A( 2 , 3)
件将动态链接库和调用程序链接在一起 . DLL 库文 件存有库函数的可执行代码 . 调用时 , 这两个库文 件都不可缺少 . 因此 , 需要将它们放于 Visual C ++ 应用程序路径或其搜索路径中 . 进行 Visual C + + 应 用 程 序 开 发 , 离 不 开 MFC , 其类的声明是在 <afx . h >头文件中进行的 , 所以该文件需直 接或间接地包 含在实现文件中 . MFC 支持的是多线程开发 , 所以要确认在 Project , Settings 对 话 框的 C/C + + 选 项卡 上 的 Category ( Code Generation) 中 , Use run _time library 项选择 的 是 Multithreaded . 另外 , 需将 LIB 文件加 到 Project , Settings 对话框的 Link 选项卡 ( Category : General) 中 的 Object/ library modules 编辑框中 . 上述准备工作执行完毕 , 就可在 Visual C ++ 中的实现文件中进行调用过程( 库函数) 的声明 , 并 确保与 Fortran 在标识符命名约定 、参数传递方式 以及参数数据类型方 面保持一致 , 然后 , 在 Visual C ++ 中的实现文件中就可直接使用动态链接库 中的库函数 .
表 1 不同 调用约定下目标文件中的标识符 语言 Fortran Fortran Fortran C C Visual C ++ 调用约定 编译后标识符 缺省 C STDCALL -name @n -name -name @n 大小写 全部大写 全部小定 全部小写 保留原有大小写
- -cdecl( 缺省) -name - -stdcall 缺省
3 参数数据类型和数组
在 Visual C ++ 对 Fortran 过程实现调用的过 程中 , 如果两种语言的过程标识符不一致 , 会产生 链接错误 ; 如果过程参数的传递方式不一致 , 会导 致非法操作 ; 如果过程参数的数据类型不一致 , 会 出现不正确的调用结果 . 所以在两种语言的混合编 程中 , 除了要注意标识符命名约定和参数传递方式 外 , 还要注 意两种语言间数据类型的一致 性 . Fortran 和 Visual C ++ 的数据类型不完全一一对应 , 但就计算常用到的整型和实型而言 , 它们有着精确 的对应关系 . 现将两种语言整型 、 实型的对应关系 列于表 2 . 表 2 数据类型的对应关系
在科 学 、工 程计算 领域 中 , 大 量的源 程序由 Fortran 语言编写 . Fortran 语言的自然表达方式 、 结 [ 1] 构化编程特点以及强大的数值计算功能 , 使其在 众多语言林立的今天 仍保持强劲的势头 . 90 年代 初出 现 的 面 向 对 象 程 序 设 计 语 言 ( 如 Visual C ++ ) , 不仅使程序设计方法发生改变 , 而且使应 用程序 的结构 和功 能产 生了重 大变 化 . 用 Visual C ++ 编程[ 2 , 3] , 可以产生友好的图形界面 , 并能与 程序进行交 互 , 可以利 用 Windows 应用编 程接口 API[ 4] ( 或 OpenGL 图形库) 绘制图形 , 借助于开放性 数据库互连 ODBC 来进行数据库存取操作等 . 上述 两种语言的结合 —混合 编程 , 可 给 Fortran 计算程 序增添强大的综合功能 . 本文研究 32 位 Fortran 与 Visual C ++ 的混合 编程问题 , 重点解决当 Visual C ++ 调用 Fortran 过 程( 子程序和函数的统称) 时 , 两种语言在不同约定 下目标文件中的标识符和参数传递方式的一致性 , 以及两种语言间参数数据类型的统一问题 .
总的字节数 , 以十进制表示 ; decoration 为 C ++ 编 译程序对标识符所做的修饰 , 其形式视具体情况而 定 , 通过使用 extern ”C” 对标识符进行说明 , 可以去 掉 Visual C ++ 对标识符所做的修饰 , 也唯有如此 , 才可能实现 Visual C ++ 对 Fortran 过程的调用 .
相关文档
最新文档