Fortran Coder

查看: 9703|回复: 5
打印 上一主题 下一主题

[混编] QT调用Fortran 传递字符串问题

[复制链接]

25

帖子

10

主题

0

精华

熟手

F 币
158 元
贡献
82 点
跳转到指定楼层
楼主
发表于 2019-6-29 00:51:09 | 只看该作者 回帖奖励 |倒序浏览 |阅读模式

   我现在学习用qt调用Fortran的dll文件,向dll传递一个文件名,但是我将他输出来是乱码不知道是为啥,请大神帮忙指出错误。
FORTRAN 代码:
   SUBROUTINE SUB(c)
   !DEC$ ATTRIBUTES DLLEXPORT::SUB
  !DEC$ ATTRIBUTES REFERENCE:: c
       character ::c
   write(*,*)c
END SUBROUTINE SUB


  QT代码:
    QString a;   typedef void(*QTsub)(QString b);    QLibrary dll("DLL2.dll");   
if(dll.load())
   {     
               QTsub sub=(QTsub)dll.resolve("SUB");            
              a=“hello,World”;               
           sub(a);  
}



分享到:  微信微信
收藏收藏 点赞点赞 点踩点踩

954

帖子

0

主题

0

精华

大师

F 币
184 元
贡献
75 点

规矩勋章元老勋章新人勋章水王勋章热心勋章

QQ
沙发
发表于 2019-6-29 10:21:38 | 只看该作者
Qt 的 QString 用的是 unicode 编码,需要转换成ANSI编码,才能“直接”被fortran使用

QByteArray ba = a.toLocal8Bit();
sub(ba.data());

25

帖子

10

主题

0

精华

熟手

F 币
158 元
贡献
82 点
板凳
 楼主| 发表于 2019-7-1 15:11:35 | 只看该作者
vvt 发表于 2019-6-29 10:21
Qt 的 QString 用的是 unicode 编码,需要转换成ANSI编码,才能“直接”被fortran使用

QByteArray ba = a. ...

您好,首先很感谢您的解答,但是我按照您的方式修改了qt代码 ,发现输出的还是一堆乱码,是不是因为我Fortran的dll程序有问题啊?

25

帖子

10

主题

0

精华

熟手

F 币
158 元
贡献
82 点
地板
 楼主| 发表于 2019-7-1 17:12:14 | 只看该作者
感谢大神 已经解决 ,谢谢指导。

2033

帖子

12

主题

5

精华

论坛跑堂

臭石头雪球

F 币
1641 元
贡献
709 点

美女勋章热心勋章星光勋章新人勋章贡献勋章管理勋章帅哥勋章爱心勋章规矩勋章元老勋章水王勋章

5#
发表于 2019-7-1 17:30:15 | 只看该作者
问题有2个:

1. typedef void(*QTsub)(QString b); 应该为 typedef void(*QTsub)(char*);
因为 ba.data() 的返回值就是 char* , 只有这种原生的类型才能混编。
你不能把 QString 传进来,fortran不能解析它。

2. Fortran的虚参没有定义长度,这样就算传进来,也只得到第一个字符“h”


实际上,你这种混编方式非常不规范。(换个编译器可能就不行了)
你可以考虑换一个方式:

[Fortran] 纯文本查看 复制代码
SUBROUTINE SUB(pc,n) Bind(C,Name="sub")
   !DEC$ ATTRIBUTES DLLEXPORT::SUB
   use , intrinsic :: ISO_C_Binding
   integer , value :: n
   type(c_ptr) , value :: pc
   character(len=n) , pointer :: c
   call c_f_pointer( pc , c )
   write(*,*) c
END SUBROUTINE SUB


[C++] 纯文本查看 复制代码
#include "main.h"
#include <QLibrary>

extern "C" {
  typedef void(*QTsub)(char*, int);
}
int main() {
  QString a;  
  QLibrary dll("DLL2.dll");
  if (dll.load()) {
    QTsub sub = (QTsub)dll.resolve("sub");
    a = "hello, World";
    QByteArray ba = a.toLocal8Bit();
    sub(ba.data(),ba.size());
  }
}

25

帖子

10

主题

0

精华

熟手

F 币
158 元
贡献
82 点
6#
 楼主| 发表于 2019-7-1 19:57:51 | 只看该作者
fcode 发表于 2019-7-1 17:30
问题有2个:

1. typedef void(*QTsub)(QString b); 应该为 typedef void(*QTsub)(char*);

是雪球大人嘛?谢谢指导, 我会努力改正规范
您需要登录后才可以回帖 登录 | 极速注册

本版积分规则

捐赠本站|Archiver|关于我们 About Us|小黑屋|Fcode ( 京ICP备18005632-2号 )

GMT+8, 2024-12-24 08:18

Powered by Tencent X3.4

© 2013-2024 Tencent

快速回复 返回顶部 返回列表