I’ve been using c++ casually for a couple of months with a makefile I don’t even remember where I got or if I did it myself (the actual structure it has. I know I’ve added some libraries and flags though):
SRC = filename.cpp
TARG = filename
CC = g++
CPPFLAGS = -g -Wall -Werror -Wextra -pipe -pedantic -Weffc++ -std=c++0x -O2 -Wno-unused-function `pkg-config --cflags opencv`
LDFLAGS = `pkg-config --libs opencv` -lboost_regex -lboost_filesystem
OBJ = $(SRC:.cpp=.o)
all: $(TARG)
clean:
rm -f *~ *.o $(TARG)
I wanted to use it to compile a class, but first I have to understand what is going on since I have to modify it a bit. Also, are there any bad practices in it?
If you want to compile a class instead of a program, you need to do a little surgery on the file. I’m assuming that you want an object file, not a library; the rules for libraries are more complex. But this should do the trick.
It is not immediately clear whether
$(CPPFLAGS)will automatically appear in the compilation or linking commands.If you end up wanting to build the program from two files, then you use a hybrid:
Note that I’ve changed the macro for the C++ compiler from CC to CXX. The standards are not clear on the name for the C++ compiler. POSIX doesn’t mention C++ in its description of
make. However, CC is clearly intended for compiling C rather than C++. That needn’t stop your version ofmakefrom using CC for C++ compilation, but it would be a little unusual. (GNU Make 3.81 on MacOS X 10.6.8 uses CXX for the C++ compilation.) The link line now uses$(CXXFLAGS)(thanks to eriktous); it is still not clear whether the C++ source to object file compilation would do so. Ultimately, that’s why you end up seeing makefiles with rules such as:This guarantees that the compilation rule is what you see for this object file. You might write that as an old-fashioned but portable suffix rule (
.cpp.o:) instead; the POSIX specification formakesupports these. Or you might use the more modern but not necessarily quite as portable%.o : %.onotation instead (not required by POSIX). Either of these replaces any previous (built-in) definition of how to compile an object file from C++ source.I assume you are using
opencv(and some of Boost); if not, your compilation and linking flags include irrelevant options. The dependencies are guessed;makewill infer the dependency of the object file on the C++ source code, so I only listed header dependencies. But you may have many more if you’re usingopencvand Boost.(Makefiles not formally tested.)