2

Let's say I want to rewrite this:

main.o: main.cpp
    g++ -c main.cpp

factorial.o: factorial.cpp
    g++ -c factorial.cpp

hello.o: hello.cpp
    g++ -c hello.cpp

in a more generic way as something like this:

SOURCES = main factorial hello

$(SOURCES).o: $(SOURCES).cpp
    g++ -c $(SOURCES).cpp

How do I do that?

1 Answers1

6

First we tell the compiler how to nme the output files, just to avoid misunderstanding:

main.o: main.cpp
    g++ -c main.cpp -o main.o

factorial.o: factorial.cpp
    g++ -c factorial.cpp -o factorial.o

hello.o: hello.cpp
    g++ -c hello.cpp -o hello.o

Then we put in automatic variables, to reduce redundancy:

main.o: main.cpp
    g++ -c $< -o $@

factorial.o: factorial.cpp
    g++ -c $< -o $@

hello.o: hello.cpp
    g++ -c $< -o $@

Then we realize that these rules all look the same, so we combine them as a static pattern rule:

main.o factorial.o hello.o: %.o : %.cpp
    g++ -c $< -o $@

Then we use a variable to store the names of the objects:

OBJECTS := main.o factorial.o hello.o

$(OBJECTS): %.o : %.cpp
    g++ -c $< -o $@
Beta
  • 96,650
  • 16
  • 149
  • 150
  • You don't need a static pattern rule. You can just use the built-in pattern rules. A one-line makefile `all: main.o factorial.o hello.o` is all you need. – MadScientist Sep 13 '13 at 03:54
  • @MadScientist: True. (In fact, since the the original makefile had no `all` rule, I can replace it with a one-*word* makefile `main.o:`.) But using the built-in rules like that kind of defeats the purpose of the question, which was to show how to use a variable as a target. – Beta Sep 13 '13 at 04:04