发布于 

g++和gcc知识点回顾

关于g++和gcc

首先我们先需要安装

1
yum install gcc gcc-c++ make cmake -y

然后我们测试一段简单的代码,文件名: main.cpp

1
2
3
4
5
6
7
#include <iostream>
using namespace std;

int main(){
cout << "hello" << endl;
return 0;
}

然后我们写一个简单的makefile:

1
2
3
build:
mkdir -p ./build
g++ -o ./build/hello main.cpp

然后我们构建一下:

1
make build

然后我们可以看到在文件夹build下面生成了一个hello的可执行文件,然后我们可以运行一下它:

1
2
cd build 
./hello

然后我们看到输出了hello文字。

查看依赖的系统动态链接库

1
ldd ./hello

然后我们看到输出了:

1
2
3
4
5
6
linux-vdso.so.1 (0x00007ffe23449000)
libstdc++.so.6 => /lib/x86_64-linux-gnu/libstdc++.so.6 (0x00007f4a24e00000)
libc.so.6 => /lib/x86_64-linux-gnu/libc.so.6 (0x00007f4a24a00000)
libm.so.6 => /lib/x86_64-linux-gnu/libm.so.6 (0x00007f4a25105000)
/lib64/ld-linux-x86-64.so.2 (0x00007f4a25208000)
libgcc_s.so.1 => /lib/x86_64-linux-gnu/libgcc_s.so.1 (0x00007f4a250e5000)

相当于它依赖了这些系统的库。

依赖的头文件怎么处理

  • -I 头文件所在的路径
  • -L 库文件所在的路径(包括动态库和静态库)
  • -l 指定库的名字

然后我们代码中引用头文件,两种

1
2
3
#include <iostream>

#include "hello.h"

#include <iostream> 引用系统的,一般在 /usr/include/usr/local/include 目录下,我们可以通过gcc -v查看。

#include "hello.h"这种则是当前项目中的头文件。

查看.a和.so文件中的接口

查看.a文件中都包含了哪些文件

1
ar -t xxx.a

查看.so文件接口

1
nm -D xxx.so

关于gcc,g++版本说明

一般C++从2011年(每三年一次,2011的新特性最多,目前使用的也最多,也最为人熟知)。

注:为了能够使用C++17的特性,需要gcc-7以上的版本

我们可以通过下面命令查看我们的编译器的版本

1
gcc --version
1
g++ --version

关于cmake说明

一个例子:

main.cpp

1
2
3
4
5
6
7
#include <iostream>
using namespace std;

int main(){
cout << "hello" << endl;
return 0;
}

然后CmakeLists.txt文件

1
2
3
4
cmake_minimum_required(VERSION 3.13)
project(helloworld)
set(CMAKE_CXX_FLAGS "-std=c++17")
add_executable(helloworld main.cpp)

然后我们新建一个build文件夹

1
2
mkdir -p build
cd build && cmake ..

然后默认 cmake 会生成 Unix Makefiles ,这个可以通过下面命令进行查看:

1
cmake --help

然后我们再进行build一下这个makefile的项目:

1
make

然后我们就看到生成了helloworld这个可执行文件了。

关于CmakeLists.txt的更多知识可以看:

https://www.jetbrains.com/help/clion/cmakelists-txt-file.html

cmake生成静态链接库和动态链接库和可执行文件的三个case

可执行文件

可执行文件:

1
2
3
4
cmake_minimum_required(VERSION 3.13)
project(helloworld)
set(CMAKE_CXX_FLAGS "-std=c++17")
add_executable(helloworld main.cpp)

这个前面已经有例子了,就不继续讲了。

静态链接库:

1
2
3
4
5
cmake_minimum_required(VERSION 3.13)
project(hello_libray)
set(CMAKE_CXX_FLAGS "-std=c++17")
add_library(hello_libray STATIC hello.cpp)
target_include_directories(hello_libray PUBLIC ./include)

对应的文件:

1
2
3
4
- include
hello.h
- hello.cpp
- CMakeLists.txt

hello.h:

1
2
3
4
5
6
7
8
9
10
11
#ifndef __HELLO__
#define __HELLO__

class Hello{
public:
Hello(){};
~Hello(){};
std::string hello();
};

#endif

hello.cpp:

1
2
3
4
5
6
7
#include <iostream>
#include "hello.h"
using namespace std;

string Hello::hello(){
return "hello world2";
}

然后我们还是创建一个build文件夹,进行构建:

1
2
mkdir -p build
cd build && cmake .. && make

最终会生成:

1
libhello_libray.a

如果另外一个项目要引用这个静态库怎么搞呢?

CMakeLists.tx

1
2
add_executable(helloworld main.cpp)
target_link_libraries(helloworld PRIVATE hello_libray)

动态链接库

我们上面静态库的时候,已经看到用到了 add_library(hello_libray STATIC hello.cpp)

add_library一共有三个参数,第一个表示:指定库的名字,第二个表示:动态还是静态,默认是静态。第三个表示: 指定生成库的源文件

1
2
3
4
5
6
7
8
cmake_minimum_required(VERSION 3.13)
project(hello_libray)
set(CMAKE_CXX_FLAGS "-std=c++17")
add_library(hello_libray SHARED hello.cpp)
target_include_directories(hello_libray PUBLIC ./include)

add_executable(helloworld main.cpp)
target_link_libraries(helloworld PRIVATE hello_libray)

有点像,编译出来这个有个libhello_library.so,然后我们可以用 nm -D libhello_library.so 可以看到它有暴露这个接口。

1
00000000000024da T _ZN5Hello5helloB5cxx11Ev

回忆了一下以前C语言开发的时候,做插件层,用以下方法

hello.h:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
#ifndef __HELLO__
#define __HELLO__

class Hello{
public:
Hello(){}
~Hello(){}
std::string hello();
};

extern "C" {
void helloworld();
}


#endif

hello.cpp:

1
2
3
4
5
6
7
8
9
10
11
#include <iostream>
#include "hello.h"
using namespace std;

string Hello::hello(){
return "hello world2";
}

void helloworld(){
cout << "hello hello hello" << endl;
}

这种编译出来的,我们用nm -D ./libhello_library.so可以看到:

1
00000000000025ae T helloworld

一些资料

cmake的资料:
https://github.com/Liuyvjin/notebook/tree/master/Cmake

cmake:add_library生成静态库和动态库:
https://blog.csdn.net/zhizhengguan/article/details/111713847


如果你有什么意见和建议,可以点击: 反馈地址 进行反馈。