2012-09-20 53 views
1

我有一個makefile,當我需要添加另一個作爲項目一部分的文件時,我還需要大量編輯以使其全部工作。我想只編寫一次我的makefile並完成它!所以,這是腳本:如何使我的生成文件更一般?

CC=g++ 
CFLAGS=-c -Wall 

#All paths start in the main directory which has this makefile, object/ and code/. 
OBJPATH=object#All compiled .o files need to be placed here. 
CODEPATH=code#All .cpp and .hpp header files reside here. 

#The names of all the object files that need to be made. 
OBJ=$(OBJPATH)/World.o $(OBJPATH)/Block.o $(OBJPATH)/Creep.o $(OBJPATH)/Food.o $(OBJPATH)/Brick.o 

all : World.a 


$(OBJPATH)/World.o : $(CODEPATH)/World.hpp $(CODEPATH)/World.cpp 
    $(CC) $(CFLAGS) $(CODEPATH)/World.cpp 
    mv World.o $(OBJPATH)/ 

$(OBJPATH)/Block.o : $(CODEPATH)/Block.hpp $(CODEPATH)/Block.cpp 
    $(CC) $(CFLAGS) $(CODEPATH)/Block.cpp 
    mv Block.o $(OBJPATH)/ 

$(OBJPATH)/Creep.o : $(CODEPATH)/Creep.hpp $(CODEPATH)/Creep.cpp 
    $(CC) $(CFLAGS) $(CODEPATH)/Creep.cpp 
    mv Creep.o $(OBJPATH)/ 

$(OBJPATH)/Food.o : $(CODEPATH)/Food.hpp $(CODEPATH)/Food.cpp 
    $(CC) $(CFLAGS) $(CODEPATH)/Food.cpp 
    mv Food.o $(OBJPATH)/ 

$(OBJPATH)/Brick.o : $(CODEPATH)/Brick.hpp $(CODEPATH)/Brick.cpp 
    $(CC) $(CFLAGS) $(CODEPATH)/Brick.cpp 
    mv Brick.o $(OBJPATH)/ 


#This archive is the final result of the compilation: 
World.a : $(OBJ) 
    ar rvs World.a $(OBJ) 
    cp $(CODEPATH)/World.hpp . #I need both the World.a file and the World.hpp file from code/ for this library to function. 


#Delete all object files and the archive: 
clean : 
    rm $(OBJPATH)/*.o World.a World.hpp *~ $(CODEPATH)/*~ 

#Delete all backup files made by Gedit: 
pretty : 
    rm *~ $(CODEPATH)/*~ 

什麼這通常做的就是編譯文件夾object/中的所有.o文件,然後把它們放在一個名爲World.a文件。然後它只複製World.hpp,因爲這是庫的頭文件。我相信很多代碼可以最小化,因此它更具可讀性和通用性(每次創建新課程時都不需要編輯它)。

+1

你使用什麼版本的Make? (GNUMake,我希望。) – Beta

+0

Ubuntu的默認版本。我目前不在家,所以我無法馬上檢查。 – corazza

回答

2

看爲一個目標文件的規則:

$(OBJPATH)/World.o : $(CODEPATH)/World.hpp $(CODEPATH)/World.cpp 
    $(CC) $(CFLAGS) $(CODEPATH)/World.cpp 
    mv World.o $(OBJPATH)/ 

讓我們來構建,而不是使用mv我們所希望的對象,:

$(OBJPATH)/World.o : $(CODEPATH)/World.hpp $(CODEPATH)/World.cpp 
    $(CC) $(CFLAGS) $(CODEPATH)/World.cpp -o $(OBJPATH)/World.o 

然後使用自動變量:

$(OBJPATH)/World.o : $(CODEPATH)/World.hpp $(CODEPATH)/World.cpp 
    $(CC) $(CFLAGS) $(CODEPATH)/World.cpp -o [email protected] 

然後顛倒先決條件的順序,以便我們可以使用另一個automati C變量:

$(OBJPATH)/World.o : $(CODEPATH)/World.cpp $(CODEPATH)/World.hpp 
    $(CC) $(CFLAGS) $< -o [email protected] 

現在的命令中沒有提到World的名字,所以我們可以使用相同的規則對所有的對象。爲了使這個答案總之我會先使其靜態模式規則:

$(OBJPATH)/World.o : $(OBJPATH)/%.o : $(CODEPATH)/%.cpp $(CODEPATH)/%.hpp 
    $(CC) $(CFLAGS) $< -o [email protected] 

然後結合他們都:

OBJ=$(OBJPATH)/World.o $(OBJPATH)/Block.o $(OBJPATH)/Creep.o $(OBJPATH)/Food.o $(OBJPATH)/Brick.o 

$(OBJ) : $(OBJPATH)/%.o : $(CODEPATH)/%.cpp $(CODEPATH)/%.hpp 
    $(CC) $(CFLAGS) $< -o [email protected] 

現在,當你想添加一個新的文件,所有你需要做的將其添加到OBJ=...行。還有幾個可以改進的地方,但這足夠一天。

+0

真棒,它的工作原理! – corazza