我正在尝试链接一个用C / C ++构建的编译research experiment project。 该项目依赖于HyperNEAT和机器人模拟软件WeBots。 我已成功克隆并构建了HyperNEAT项目(在该项目中还有其他依赖项,如Boost,TinyXML,JGTL(自定义库)和其他不相关的子项目)。
我制作了一个包含所有必要的头部搜索路径和库路径的makefile,并编译了两个主要的.cpp文件:
/ModHyperNEAT/mod_ctrler7.cpp
/ModSupervisor/mod_supervisor.cpp
工作,给我2个.o文件。
但是,在 make link 步骤中,当我想创建(单独)两个文件的可执行文件时,我收到'未定义的架构x86_64 符号'错误(请参阅此处的pastebin:http://pastebin.com/kiwwCcUf)。看来C ++标准的数据类型和函数如
无法找到std::string::end() const
。
我搜索了搜索SO以获得有关此问题的答案,如果我理解正确的话,似乎缺少任何库或二进制不兼容,但是库存在并且两个项目都使用-lstdc++
标志进行编译。
这是make链接步骤(以及makefile中使用的宏):
CC = gcc
CFLAGS = -v -g -lstdc++ -Wall -Wno-error -ferror-limit=100 -fmessage-length=0
DEFINES = -DHCUBE_NOGUI -DTIXML_USE_STL
FLAGS = $(CFLAGS) $(DEFINES)
LIB_TINYXML = -L/Users/michahell/Documents/projects_c++/HyperNEAT/tinyxmldll/out
LIB_HYPERNEAT = -L/Users/michahell/Documents/projects_c++/HyperNEAT/NE/HyperNEAT/out
LIB_BOOST = -L/usr/local/Cellar/boost/1.57.0/lib
LIB_WEBOTS = -I/Applications/Webots/lib
LIBS = $(LIB_TINYXML) $(LIB_HYPERNEAT) $(LIB_BOOST) $(LIB_WEBOTS)
LIBFLAGS = -ltinyxmlpluslib -lboost_filesystem-mt -lboost_random-mt -lboost_system-mt -lNEATLib_d -lHypercube_NEAT_Base_d
WEBOTS_DYLIB = -dylib_file /Applications/Webots/lib/libController.dylib:/Applications/Webots/lib/libController.dylib
$(CC) $(FLAGS) $(LIBS) ./mod_ctrler7.o $(WEBOTS_DYLIB) $(LIBFLAGS)
我发现链接到 .dylib的我必须使用特定的标志并指定完整路径,因此 $(WEBOTS_DYLIB)宏。
我正在使用-lstdc++
标志,因为在HyperNEAT项目中该标志也用于构建该库。如果我排除这个标志,我在编译过程中会遇到很多错误(我现在理解的是libc ++和libstdc ++不兼容)。所有图书馆路径都会检出,并且存在 .a 和/或 .dylib 文件。
我对C / C ++和GCC工具的了解非常有限,因为我以前从未使用它。 我认为这可能与HyperNEAT项目包含一个用于构建的Boost 1.57.0发行版的事实有关,而且我在我的系统上安装了一个单独的(使用自制程序)Boost版本,这是相同的版本:
$ brew info boost
boost: stable 1.57.0 (bottled), HEAD
http://www.boost.org
/usr/local/Cellar/boost/1.57.0 (10572 files, 439M) *
导致此错误的原因可能是我的链接步骤失败?如果克隆 HyperNEAT 和我的项目并将其根目录放在同一位置,则任何人都应该能够重现我的链接器错误。应该下载WeBots,但仅限于头部包含和库。当然,我的makefile路径应该被修改。
如果有人可以给我提示如何解决这个问题,我会非常感激!
答案 0 :(得分:0)
事实证明,由于某种原因,我必须将lstdc++
标志包含在库链接标志中而不是作为编译器标志,并且stdlib=libstdc++
作为编译器标志。