【发布时间】:2013-06-20 01:02:11
【问题描述】:
对于我的面向对象编程课程,我必须完成一个期末项目(学术目的)。我想以“正确的方式”制作一个项目(即:makefile、模块化、DRY、易于扩展等),以便更好地理解类、makefile 和 C++。
我的想法是有一个“tree-source-file-structure-directory”,所以在每个子文件夹中,我都有源文件及其标题、测试文件和单个 makefile。 因此,如果我想在界面上工作,我会转到子文件夹界面,编辑文件,运行测试,如果一切正常,只需将对象链接到我的根目录中即可。如果我想处理我的数据结构,同样的事情,等等。不错的功能是在每个子文件夹中都驻留在源代码和目标文件中,因此我根目录中的链接器将搜索已在子文件夹上编译的目标文件并将它们链接在一起
我一直在互联网上搜索,我可以看到许多不同的解决方案: - 递归地做,例如:
SUBDIRS=eda
.PHONY: subdirs $(SUBDIRS)
$(SUBDIRS):
$(MAKE) -C $@
我发现的问题是我对“eda”文件夹的先决条件是“古怪”
-使用自动变量 $(@D),但我不太明白它是如何工作的 -也许使用通配符功能,但我对这个选项有点困惑。
无论如何,对我来说最诱人的解决方案是第一个(递归使用make),但我发现很多cmets说不建议使用make递归Interesting article
所以我想问你们一些建议:我怎样才能实现我的目标并将每个重要的模块放在一个单独的文件夹中?递归是最好的解决方案吗?也许我应该潜入“automake”?或者最好将所有对象文件放到根目录上的一个新“对象”子文件夹中,然后将它们链接在一起?
顺便说一句,我通过嗅探Amarok源代码获得了这个树形结构的灵感:它有一个名为“src”的子文件夹,当你进入那里时,你可以看到很多子文件夹:均衡器,播放列表、动态、状态栏、核心、播放列表生成器、播放列表管理器等。许多子文件夹都有自己的子目录……结果是一个令人难以置信的音乐播放器。如果这种方法对 Amarok 团队有效……我可以做类似的事情!
欢迎任何 cmet、反馈、建议和其他人,提前谢谢!
编辑#1
Beta,我有一些隐式规则(后缀)和链接器的目标,该链接器需要我的 eda 文件夹中的对象。此目标的所有其他先决条件都建立在当前文件夹上。 我遇到的问题是,当我运行 make 来构建该目标时,它会将 “eda”文件夹上的先决条件的名称 作为使用隐式规则构建的目标。这是我的项目中 makefile 递归的棘手/不干净的部分:我想我必须为 make 必须在子文件夹中搜索的每个目标文件创建一个特殊的隐式规则。
这就是我想要一些反馈的原因:¿有更好的选择吗?还是在我的项目中使用 make recursive 的优势压倒了其他替代方案?
无论如何,如果让您更好地理解,这是我的 Makefile 草案(它是 spnish-english :P)
#Makefile hecho para las pruebas de los archivos dentro de esta carpeta
FLAGS=-g -DDEBUG
OUT_TI=TIndividuo
OUT_TP=TProfesor
OUT_TA=TAula
.SUFFIXES: .cpp .c .h .o
.c.o: ; cc $(FLAGS) -c $*.c
.cc.o: ; gcc $(FLAGS) -c $*.cc
.cpp.o: ; g++ $(FLAGS) -c $*.cpp
SUBDIRS=eda
.PHONY: subdirs $(SUBDIRS)
$(OUT_TI): eda/TAula.o CandidatoHorario.o TIndividuo.o TIndividuoTest.o TGen.o
g++ CandidatoHorario.o TIndividuo.o TIndividuoTest.o TGen.o eda/TAula.o -o $@
CandidatoHorario.o: CandidatoHorario.cpp CandidatoHorario.h
TIndividuoTest.o: TIndividuoTest.cpp TIndividuo.h
TIndividuo.o: TIndividuo.cpp TIndividuo.h
TGen.o: TGen.cpp
#eda/TAula.o: eda/TAula.cpp eda/TAula.h
# g++ -c eda/TAula.cpp -o $@
$(SUBDIRS):
$(MAKE) -C $@
clean:
rm -f *.o $(OUT_TI) $(OUT_TA) eda/TAula.o
【问题讨论】:
-
您能详细解释一下
eda的先决条件吗? -
好的,我会编辑我的主帖!
-
只是我的两分钱:使用“非递归制作”论文,您已经得到了正确的方法,至少在我看来……您可能已经知道 Android 使用(并且仍在使用?)这个方法。我会遵循evbergen.home.xs4all.nl/nonrecursive-make.html 中给出的细节,因为这是相当具体的。此外,我认为您需要一些“目标”来生成+运行每个子目录的测试,但我认为这并不复杂......
-
Ok Ingo,所以您告诉我您的方法将使用“非递归生成”以便将每个对象文件放在“对象”文件夹中,然后在需要时链接它们,对吧?我要找杯咖啡看你的文件,谢谢!顺便说一句,在我的帖子中,我写了我的“测试文件夹”的生成文件:它们是故意的几个“运行目标”,因为在这个“测试文件夹”中我使用了最小的 source-stable-files-已经测试过来测试我在互联网上找到的关于 Makefiles 和子文件夹的材料。
-
scons 也是一个不错的构建系统。每个目录脚本的清晰性(如果需要),没有递归 make 的缺点。
标签: c++ recursion tree makefile