minidocx: 在C++11环境下运行的解决方案(二)
目录
1.背景
2.改造过程
3.编译运行
4.总结
1.背景
minidocx: 一个轻量级的跨平台的C++操作word的开源库-CSDN博客
之前我们详细讲了minidocx的安装、编译和简单使用。它的编译环境提到了minidocx使用了C++20的一些东西,所以需要编译器(vs2022、gcc9.3.0等)支持C++20。但是现在在客户的麒麟服务器系统上只有gcc5.4.0,而且麒麟服务器上还有其它的程序编译也是gcc5.4.0基础之上的,还不能通过升级gcc版本来解决这个问题。如果有需要通过升级gcc版本来解决这个问题,可参考我的另外一篇博客:
银河麒麟系统GCC5.4.0升级到GCC9.3.0指南_kylin如何升级libstdc++6-CSDN博客
在gcc5.4.0只支持C++11,于是决定研究一下minidocx的源码,改造下,看能否在gcc5.4.0环境下编译运行。
2.改造过程
1.打开CMakeLists.txt文件,发现CMake显示设置需要C++20支持
把C++支持的版本从20改为11,重新编译一下,报错:
原来是C++11不支持std::filesystem,于是想到了用boost库,用boost::filesystem来代替std::filesystem。
2.编译boost库
1)下载 Boost 1.80.0 源码
# 官网下载(推荐)
wget https://boostorg.jfrog.io/artifactory/main/release/1.80.0/source/boost_1_80_0.tar.gz# 或国内镜像(速度更快)
wget https://mirrors.aliyun.com/boost/boost_1_80_0.tar.gz# 解压
tar -zxvf boost_1_80_0.tar.gz
cd boost_1_80_0
2)配置编译选项
a.执行 bootstrap 脚本
# 生成b2编译工具(默认配置,支持大部分模块)
./bootstrap.sh# 如需指定编译器(如ARM架构下的aarch64-g++)
# ./bootstrap.sh --with-toolset=gcc --prefix=/usr/local/boost-1.80.0# 查看可用选项
./bootstrap.sh --help
b.自定义编译配置(可选)
编辑project-config.jam
文件,可指定:
- 编译器路径
- 安装目录(默认
/usr/local
) - 启用 / 禁用特定模块
例如,仅编译必要模块(减少编译时间):
echo "using gcc ;" > project-config.jam
echo "option set prefix : /opt/boost-1.80.0 ;" >> project-config.jam
3) 编译与安装
a.编译 Boost
# 基本编译(使用所有CPU核心加速)
./b2 -j$(nproc)# 高级选项(按需选择)
# ./b2 -j$(nproc) toolset=gcc variant=release link=shared runtime-link=shared# 仅编译特定模块(如system、thread、filesystem)
# ./b2 -j$(nproc) --with-system --with-thread --with-filesystem
- 参数说明:
-j$(nproc)
:使用所有 CPU 核心,加速编译variant=release
:编译发布版本(默认)link=shared
:生成动态链接库(.so)link=static
:生成静态链接库(.a)--with-<module>
:指定编译的模块(不指定则编译所有)
b.安装 Boost
# 安装到默认目录(/usr/local)
sudo ./b2 install# 若自定义了prefix,需指定--prefix
# sudo ./b2 install --prefix=/opt/boost-1.80.0
4) 环境配置
a.配置动态链接库路径
# 创建配置文件
sudo tee /etc/ld.so.conf.d/boost-1.80.0.conf << EOF
/usr/local/lib # 默认安装路径
# /opt/boost-1.80.0/lib # 若自定义安装目录
EOF# 更新动态链接库缓存
sudo ldconfig
b.配置环境变量(可选)
# 临时生效
export BOOST_ROOT=/usr/local
export PATH=$BOOST_ROOT/bin:$PATH# 永久生效(添加到~/.bashrc或/etc/profile)
echo 'export BOOST_ROOT=/usr/local' >> ~/.bashrc
echo 'export PATH=$BOOST_ROOT/bin:$PATH' >> ~/.bashrc
source ~/.bashrc
5) 在CMakeLists.txt引入boost
#######################################################################################
# 设置 Boost 的根目录
if (WIN32)set(BOOST_ROOT "D:/OpenProject/boost_1_80_0")
else()set(BOOST_ROOT "/home/zdxiao/boost_1_80_0")
endif()
set(Boost_USE_STATIC_LIBS ON) # 使用静态库,如果需要动态库则设置为 OFF
set(Boost_USE_MULTITHREADED ON) # 使用多线程库
set(Boost_USE_STATIC_RUNTIME OFF) # 如果使用静态运行时库,则设置为 ON
# 查找 Boost 库
find_package(Boost 1.80.0 COMPONENTS filesystem system REQUIRED)
if(Boost_FOUND)include_directories(${Boost_INCLUDE_DIRS})link_directories(${Boost_LIBRARY_DIRS})
else()message(FATAL_ERROR "Boost not found")
endif()
######################################################################################
if(Boost_FOUND)target_link_libraries(minidocx PRIVATE ${Boost_LIBRARIES})
endif()
3.把源代码涉及到std::filesystem的地方修改
头文件从 #include <filesystem> 改为 #include <boost/filesystem>
std::filesystem 改为 boost::filesystem
4.修改其它不支持C++20的写法
main.cpp
package.hpp
paragraph.hpp
richtext.hpp
package.cpp
file.cpp
zip.cpp
修改的源码下载地址:
通过网盘分享的文件:minidocx_arm_boost20250722.zip 链接: https://pan.baidu.com/s/1PDbMsA1G6D69jTdRpdAQ_g?pwd=1234 提取码: 1234
3.编译运行
在源码目录下新建build目录,进入build目录执行:
#1 步骤
cmake ../# 如果需要指定gcc的路径,则为:
# cmake .. -DCMAKE_C_COMPILER=/usr/local/gcc-9.3.0/bin#2 步骤
make
然后在build目录下的Release目录生成minidocx静态库:minidocx.a
在build目录下的examples的Release生成了四个示例,运行也是跟之前一样的效果,说明修改的源代码是对的。
默认编译成静态库。如需编译成动态库,开启 CMake 选项 BUILD_SHARED
。
4.总结
遇到问题,需要综合评估解决的可行的方案。如本文的通过修改源码的方式来解决客户的问题,那是因为minidocx的源码不多,修改的地方不是很多,花费的时间也不是很多。否则就会出现费时费力,而且如果测试不充分,会出现很不稳定的情况。总之,一般来说修改源码不是一种最好的方案,只是在特定的环境下没有办法了,不失为一种好的解决方案。