最近在学习log4cpp库时,使用g++去编译,却发现自己不会链接...,这哪能行,于是网上钻研,终于解决,现在记录下来分享给遇到同样问题的人。
gcc和g++类似,这里就以g++为例!
刚好用到的log4cpp日志库有头文件和动态库.so和静态库.a,这里就以log4cpp库为例。
在安装好log4cpp库后,在路径 /usr/local/ 下有 lib库 和 include头文件
注意:任何库的默认安装路径都是在此 !
然后新建一个文件夹作为项目文件夹,进入此文件夹,然后新建include文件夹,将上图的log4cpp文件夹拷贝到刚刚新建的include文件夹下;然后新建lib文件夹,将上图的liblog4cpp.*全都拷贝到刚刚新建的lib文件夹中;
最终效果如下图:
然后根据自己的项目需求写好mian函数。
然后就可以开始编译了!
g++ MyLog.cpp test_log4cpp.cpp -std=c++11 -I ./include/ -L ./lib/ -llog4cpp -lpthread -o test_log4cpp
这样就可以正常编译链接了!
介绍
-std=c++11 : 指明项目使用c++11;
-I ./include/ : 指定项目使用的头文件路径,这样项目中使用头文件就不用写全路径了;
例如:(否则得 include "./include/log4cpp/Category.hh" 这样使用)
-L ./lib/ : 指定项目链接的库路径;
-llog4cpp :链接liblog4cpp.so库;(链接动态库和静态库都是这样使用,默认链接动态库)
如果需要链接静态库,可以将静态库改个名字,例如改成liblog4cpp1.a,然后就可以这样去链接静态库:-llog4cpp1
具体 -I -L 指定的路径根据自己项目存放的头文件和库的路径去指定!
具体参数介绍:
-L :表示要链接的库所在的目录。-L 表示要链接的库在当前目录, -L /usr/lib 表示要连接的库在/usr/lib下。目录在/usr/lib时,系统会自动搜索这个目录,不用指明。当库不在 /usr/lib 下,就得使用 -L 去指定需要链接的库的路径,否则编译时无法正常链接,会编译失败!
-l (L的小写) :表示需要链接库的名称,注意不是库文件名称,比如库文件为liblog4cpp.so,那么库名称为log4cpp;静态库也是如此!
-I (i 的大写) :指定头文件的所在的目录,可以使用相对路径。在代码中使用头文件可以不用指明具体路径。
例如:
再次提醒注意:
如果动态库和静态库名字一样,例如:liblog4cpp.so 和 liblog4cpp.a
使用 -llog4cpp 去链接此库时,默认链接的是动态库(.so),如果需要链接静态库,可以将动态库删掉,也可以将静态库改个名字,例如改成liblog4cpp1.a;这样再链接时:-llog4cpp1 就可以正确连接到静态库了。
另外:
如果需要链接多个头文件路径或库路径,可以继续使用 -I 和 -L 去链接,例如:
g++ ./commonLog/MyLogger.cpp MyLog.cpp test_log4cpp.cpp -std=c++11 -I ./include/ -I ./commonLog/ -L ./lib/ -L ./commonLog/ -llog4cpp1 -lpthread -o test_log4cpp
小插曲
c++如何调用c的库呢?
如下c代码,编译成库:
c_ku.h
#ifndef _C_KU_H_
#define _C_KU_H_
#include <stdio.h>
void print_hello();
void say_hello(char *str);
#endif // _C_KU_H_
c_ku.c
#include "c_ku.h"
void print_hello() {
printf("hello world!\n");
}
void say_hello(char *str) {
if (!str) {
return;
}
printf("say %s\n", str);
}
编译成动态库(.so)和静态库(.a)
gcc -c c_ku.c
ar -rsv libc_ku.so c_ku.o
ar -rsv libc_ku.a c_ku.o
main.cpp : c++文件
#include <iostream>
#include "c_ku.h"
int main(int argc, char **argv) {
std::cout << "hello world!" << std::endl;
print_hello();
return 0;
}
然后进行编译链接:
g++ main.cpp -I ./ -L ./ -lc_ku -o c_ku
此时会发现报错:
解决方案:
在c头文件中使用 extern "C"{ } 去将头文件声明包裹起来!
#ifndef _C_KU_H_
#define _C_KU_H_
#include <stdio.h>
extern "C"{
void print_hello();
void say_hello(char *str);
}
#endif _C_KU_H_
再一次去编译运行:
问题完美解决了!
c++可以调用c写的库了。