Ubuntu服务器下C++编译时Gurobi库链接失败问题求助
解决Gurobi库链接失败问题
问题背景
在Ubuntu服务器上使用Makefile编译包含Gurobi优化库的C++多类项目时,出现链接阶段的未定义引用错误,尽管已配置环境变量和Makefile的库路径。
核心代码片段(SaaS_Problem.cpp)
#include "SaaS_Problem.hpp" #include "SaaS.hpp" #include "application.hpp" #include "WS.hpp" #include "/home/Library/gurobi911/linux64/include/gurobi_c++.h" #include <iostream> #include <vector> #include <string> #include <algorithm> #include <cmath> #include <memory> std::vector<std::pair<double, double>> SaaS_Problem::set_param_B ( WS & w, application& app) { // 该方法代码省略 } void SaaS_Problem::solve(void) { try { rejected_requests = 0; rejected_requests_vec.resize(0); GRBEnv env = GRBEnv(); GRBModel model = GRBModel(env); GRBLinExpr obj = 0.0; // 变量创建、约束添加等代码省略 } // 代码省略 }
Makefile配置
CXXFLAGS += -Wall -std=c++11 -I/home/Library/gurobi911/linux64/include -L/home/Library/gurobi911/linux64/lib -lgurobi_c++ -lgurobi91 EXE = exe OBJS = main.o Game.o Set_System.o SaaS_Problem.o SaaS.o application.o WS.o IaaS.o IaaS_Problem.o // 其余依赖规则与编译命令省略
.bashrc环境配置
export GUROBI_HOME="/home/Library/gurobi911/linux64" export PATH="${PATH}:${GUROBI_HOME}/bin" export LD_LIBRARY_PATH="${LD_LIBRARY_PATH}:${GUROBI_HOME}/lib" export GRB_LICENSE_FILE="/home/Library/gurobi.lic" export PATH="${PATH}:${GUROBI_HOME}/include"
链接错误信息
g++ -Wall -std=c++11 ... -o exe ... SaaS_Problem.o: In function `SaaS_Problem::solve()': SaaS_Problem.cpp:(.text+0x1523): undefined reference to `GRBModel::addVar(double, double, double, char, std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char> >)' // 其余未定义引用错误信息省略 collect2: error: ld returned 1 exit status Makefile:26: recipe for target 'exe' failed make: *** [exe] Error 1
解决方法
1. 调整链接库的顺序
链接器按从左到右的顺序解析依赖,gurobi_c++.a依赖gurobi91.so,因此需要将基础库放在C++库之前。修改Makefile中的链接参数:
# 修改后 CXXFLAGS += -Wall -std=c++11 -I/home/Library/gurobi911/linux64/include -L/home/Library/gurobi911/linux64/lib -lgurobi91 -lgurobi_c++
2. 分离编译与链接参数
CXXFLAGS主要用于编译阶段,链接阶段的库参数建议放在LDFLAGS中,避免编译时无效传递,确保链接器正确获取:
CXXFLAGS += -Wall -std=c++11 -I/home/Library/gurobi911/linux64/include LDFLAGS += -L/home/Library/gurobi911/linux64/lib -lgurobi91 -lgurobi_c++ EXE = exe OBJS = main.o Game.o Set_System.o SaaS_Problem.o SaaS.o application.o WS.o IaaS.o IaaS_Problem.o # 链接命令示例 $(EXE): $(OBJS) g++ $(OBJS) $(LDFLAGS) -o $(EXE)
3. 验证Gurobi库的C++标准匹配
Gurobi的gurobi_c++库是用特定C标准编译的,确保你的项目编译标准与之一致。如果Gurobi9.1.1是用C11编译的,你的-std=c++11是匹配的;如果不确定,可以尝试添加ABI适配参数:
CXXFLAGS += -Wall -std=c++11 -D_GLIBCXX_USE_CXX11_ABI=0 -I/home/Library/gurobi911/linux64/include
4. 确认库文件存在与权限
检查Gurobi库路径下的文件是否存在且有读取权限:
ls -l /home/Library/gurobi911/linux64/lib/ # 应包含 libgurobi91.so 和 libgurobi_c++.a / libgurobi_c++.so
如果权限不足,执行:
chmod +r /home/Library/gurobi911/linux64/lib/*
5. 刷新环境变量
确保.bashrc的配置生效,执行:
source ~/.bashrc
或者直接在终端临时导出变量后再执行make。
内容的提问来源于stack exchange,提问作者Hami
相关产品推荐
相关产品推荐

