2016-03-03 47 views
1
--folder 
    ----book.h 
    ----book.cpp 
    ----library.h 
    ----library.cpp 
    ----main.cpp 

這是目錄結構和我創建了產生在同一目錄中的目標文件和可執行文件這一make文件。如何創建生成文件指定ifferent目錄中的目標和可執行文件

main : main.o book.o library.o 
     g++ main.o book.o library.o -o main 

    main.o : main.cpp book.h library.h 
     g++ -c main.cpp 

    library.o : library.cpp library.h book.h 
     g++ -c library.cpp 

    book.o : book.cpp book.h 
     g++ -c book.cpp 

    clean: 
     rm -f *.o main 

但我想分別爲文件夾中的對象文件和可執行文件創建文件夾obj和bin。我該怎麼做?

回答

2

也許這樣的事情

TARGET = bin/main 
SOURCES = main.cpp book.cpp library.cpp 
OBJ_DIR = obj 

OBJECTS = $(SOURCES:%.cpp=$(OBJ_DIR)/*.o) 

$(TARGET): $(OBJECTS) 
    $(LD) $(LDFLAGS) $^ -o [email protected] $(LIBS) 

$(OBJ_DIR)/%.o: %.cpp 
    $(CXX) $(CXXFLAGS) $< -c -o [email protected] 

這就要求binobj目錄首先存在。

閱讀the GNU Make manual瞭解更多信息。


我有一段時間,所以我寫了一個完整的,自動化的Makefile給你。這將創建目錄,如果它們不存在。

BINDIR = bin/ 
OBJDIR = obj/ 

TARGET = $(BINDIR)target 
SOURCES = main.cpp book.cpp library.cpp 

LD  = g++ 

OBJECTS = $(SOURCES:%.cpp=$(OBJDIR)%.o) 

.PHONY: all 
all: target 

.PHONY: target 
target: before_target actual_target after_target 

.PHONY: before_target 
before_target: $(OBJDIR) $(BINDIR) 

.PHONY: actual_target 
actual_target: $(TARGET) 

.PHONY: after_target 
after_target: 

$(TARGET): $(OBJECTS) 
    $(LD) $(LDFLAGS) $^ -o [email protected] $(LIBS) 

$(OBJDIR)%.o: %.cpp 
    $(CXX) $(CXXFLAGS) $^ -c -o [email protected] 

$(OBJDIR) $(BINDIR): 
    mkdir [email protected] 

.PHONY: clean 
clean: 
    -rm -rf $(BINDIR) 
    -rm -rf $(OBJDIR) 
+0

這是迄今爲止我發現的最好的makefile,但我不知道這個$(CXX)$(CXXFLAGS)$^-c -o $ @'可以在沒有聲明'CXX'的情況下工作 - OK定義'LDFLAGS'和'CXXFLAGS' - 只是傳遞空白或沒有標誌。 – SBF

+0

@SBF GNU默認將'CXX'設置爲'g ++'。 –

1

使用VPATH!這裏有一篇文章向你展示瞭如何:Multi-Architecture Builds

這裏是基本理論:

首先,將有遞歸的一個級別。這將自動處理obj等目錄,而不是任何目錄層次結構的原因。

其次,你將使用VPATH指定源代碼相對於對象目錄的位置:VPATH=../src

三......嗯......利潤!

這裏有一個簡化的例子(未測試)。您可以擴大這一點,或請跟隨本文,以得到一個「富」的版本:

ifneq (obj,$(notdir $(CURDIR))) 
    # Not in object directory, so we must be in root (src) directory! 

    .SUFFIXES: 

    OBJDIR := obj 

    MAKETARGET = $(MAKE) --no-print-directory -C [email protected] -f $(CURDIR)/Makefile \ 
      SRCDIR=$(CURDIR) $(MAKECMDGOALS) 

    .PHONY: $(OBJDIR) 
    $(OBJDIR): 
     ;[email protected][ -d [email protected] ] || mkdir -p [email protected] 
     [email protected]$(MAKETARGET) 

    Makefile : ; 
    %.mk :: ; 

    % :: $(OBJDIR) ; : 

    .PHONY: clean 
    clean: 
     rm -rf $(OBJDIR) 
else 
    VPATH=../src 
    CXX := g++ # The default, just so you know it's here 

    # CXXFLAGS = ... 
    # LDFLAGS = ... 
    # LDLIBS = ... 

    main : main.o book.o library.o 

    main.o : main.cpp book.h library.h 

    library.o : library.cpp library.h book.h 

    book.o : book.cpp book.h 

endif 
1

你可以只是obj/前綴你的對象和你的可執行文件bin/,並添加一個命令使目錄mkdir -p bin等。 。

# make your subfolders targets 
all: bin obj bin/main 

bin/main : obj/main.o obj/book.o obj/library.o 
    g++ -o bin/main obj/main.o obj/book.o obj/library.o 

obj/main.o : main.cpp book.h library.h 
    g++ -c -o obj/main.o main.cpp 

obj/library.o : library.cpp library.h book.h 
    g++ -c -o obj/library.o library.cpp 

obj/book.o : book.cpp book.h 
    g++ -c -o obj/book.o book.cpp 

# create subfolders if not present 
bin obj: 
    mkdir -p bin 
    mkdir -p obj 

clean: 
    rm -f bin/* obj/* 

然後只需輸入make(使得targer all)。

+0

感謝您的回答,它運作良好 –

相關問題