最近需要更改一段C++的程序,其中使用到了C语言的线性代数库lapack,在window上的使用(在官网下载的CLAPACK-3.1.1-VisualStudio版本,打开工程分别编译,将生成的lib路径和文件放入到工程属性的链接器中),成功运行。但是在linux上安装时,却遇到了问题,纠结了很久,现在终于解决了,贴出来仅供参考!
一、问题描述:
目的是在动态链接库中使用lapack库,但是编译的时候却遇到了这样的问题(安装过程见参考链接,这篇文章写得挺清楚的,本人下载的版本为lapack-3.2.1-CMAKE,可在linux上跨平台使用):
二、分析问题:
1.这个问题是由于引入的模块没有使用-fPIC(代码独立)进行编译。但是在什么地方更改?由于更改程序的需求,下载的版本为lapack-3.2.1-CMAKE版本的,因为这个之前的版本的头文件为lapack.h和f2c.h但是之后的版本进行了升级编程了lapacke.h,所以版本不考虑更换。
2.在这个版本中的编译文件由两部分组成make.inc和makeFile,make.inc中有CFLAS参数(-fPIC是在这个参数中设置的),各个模块中的makeFile文件都有使用这个make.inc文件的配置,那么这个是需要更改的关键参数。
3.如果只有这一个参数需要更改的地方,则会成功,否则,需要进一步的分析README.install。
//按照2去测试,发现运行之后还是会报这种错误
4.分析F2CLIBS文件下的makeFile的内容,发现有两处需要主要的地方,在生成f2clib.so链接库的时候,需要将make.inc中的CFLAS参数加上-fPIC和-DNON_UNIX_STDIO
//按照4去测试,发现仍是会有这样的错误,但是提示的错误略有不同,不同在于liblapack.a(slamch.o)不能读取
5.查找这个文件,发现是在INSTALL文件下,那么错误很有可能是在这个配置文件中,发现在这个.o生成的时候并没有引入-fPIC,而是使用了$(NOOPT),而在make.inc中NOOPT的设置为-O0,所以还要在这个地方进行变动。
//按照5去测试,发现成功,可以正常生成.so文件。
三、解决问题:
总结一下需要配置的地方和如何使用
1.需要更改的配置:
F2CLIBS的makeFile中
在INstall的makeFile里
make.inc里
2.测试代码testf2c.cpp
#include<iostream>
using namespace std;
#include "f2c.h"
//因为程序是C++,而CLAPACK是C语言写的,所以在此处用extern关键字
extern"C"
{
#include<clapack.h>
}
int main(void) {
integer M=3 ;
integer N=1;
real a[9]={4,3,11,2,-1,0,-1,2,3};
real b[3]={2,10,8};
integer lda;
integer ldb;
integer INFO;
lda=M;
ldb=M;
integer ipiv[M];
sgesv_(&M, &N, a, &lda,ipiv, b, &ldb, &INFO);
if(INFO==0)
{
for(int i=0;i<M;i++)
{
cout<<b[i]<<endl;
}
}
else
{
cout<<"Failed."<<endl;
}
return 0;
}
3.生成动态库
g++ -fPIC -shared testf2c.cpp -llapack -lblas -lf2c -o testf2c.so
4.不使用-fPIC和-shared结果为:
[root@VM_26_152_centos test]# ./test.so
-14
56
54
参考:http://blog.csdn.net/zxd675816777/artical/details/39484499