325

Shall this be the example:

#include <iostream>
using namespace std;

int main()
{
    cout << "Hola, moondo.\n";
}

It throws the error:

gcc -c main.cpp gcc -o edit main.o  main.o: In function `main':
main.cpp:(.text+0xa): undefined reference to `std::cout'
main.cpp:(.text+0xf): undefined reference to `std::basic_ostream<char,std::char_traits<char> >& std::operator<< <std::char_traits<char>>(std::basic_ostream<char, std::char_traits<char> >&, char const*)'
main.o: In function `__static_initialization_and_destruction_0(int,int)':
main.cpp:(.text+0x3d): undefined reference to `std::ios_base::Init::Init()'
main.cpp:(.text+0x4c): undefined reference to `std::ios_base::Init::~Init()' collect2: error: ld
returned 1 exit status make: *** [qs] Error 1

Also, this example:

#include <iostream>

int main()
{
    std::cout << "Hola, moondo.\n";
}

throws the error:

gcc -c main.cpp gcc -o edit main.o  main.o: In function `main':
main.cpp:(.text+0xa): undefined reference to `std::cout'
main.cpp:(.text+0xf): undefined reference to `std::basic_ostream<char,std::char_traits<char> >& std::operator<<<std::char_traits<char>>(std::basic_ostream<char,std::char_traits<char> >&, char const*)'
main.o: In function `__static_initialization_and_destruction_0(int,int)': main.cpp:(.text+0x3d): undefined reference to `std::ios_base::Init::Init()'
main.cpp:(.text+0x4c): undefined reference to `std::ios_base::Init::~Init()' collect2: error: ld
returned 1 exit status make: *** [qs] Error 1

Note: I am using Debian 7 (Wheezy).

Peter Mortensen
  • 30,738
  • 21
  • 105
  • 131
D1X
  • 5,025
  • 5
  • 21
  • 36
  • 300
    Try `g++` instead of `gcc`. `gcc` is for C and will not give you access to the C++ standard library. – juanchopanza Jan 30 '15 at 13:21
  • 4
    Well, that definitely solved the problem. As I understand, GCC is the acronym for Gnu Compiler Collection. Shouldn't it call the g++ compiler when needed? So the command gcc calls the c compiler instead... – D1X Jan 31 '15 at 14:42
  • 3
    @D1X it's because you invoked the linker separately from the compiler. when you write `gcc -o edit main.o` it doesn't know that `main.o` is going to need C++ startup libraries. – M.M Feb 26 '15 at 04:22
  • 6
    RTFM https://gcc.gnu.org/onlinedocs/gcc/Invoking-G_002b_002b.html – Jonathan Wakely Jun 04 '15 at 14:11
  • 5
    Q: Shouldn't it call the g++ compiler when needed? A: No more than gcc should call gfortran, gjc, ... etc. etc. as needed. – paulsm4 Jul 16 '15 at 03:29
  • And if using clang instead of gcc, try with clang++ instead. – Stéphane Jun 30 '20 at 15:07
  • Isn't it *"[Hola, mundo](https://es.wikipedia.org/wiki/Hola_mundo)"*? Is Portuguese different? – Peter Mortensen Apr 03 '22 at 13:15
  • What is the canonical question for this? The confusion with the two executables `g++` and `gcc` must have been one of the very first questions in 2008. – Peter Mortensen May 08 '22 at 14:05

6 Answers6

446

Compile the program with:

g++ -Wall -Wextra -Werror -c main.cpp -o main.o
     ^^^^^^^^^^^^^^^^^^^^ <- For listing all warnings when your code is compiled.

as cout is present in the C++ standard library, which would need explicit linking with -lstdc++ when using gcc; g++ links the standard library by default.

With gcc, (g++ should be preferred over gcc)

gcc main.cpp -lstdc++ -o main.o
Peter Mortensen
  • 30,738
  • 21
  • 105
  • 131
shauryachats
  • 9,975
  • 4
  • 35
  • 48
  • 25
    It *can* be used to compile C++ code, the thing is that it doesn't *link* with the C++ library. `gcc` will work just fine if you just add `-lstdc++`. – Some programmer dude Jan 30 '15 at 13:24
  • 6
    Please always include `-Wall` when giving gcc/g++ command line examples - it helps to get noobs into good habits at an early stage and saves everyone time time further down the road. ;-) – Paul R Jan 30 '15 at 13:29
  • You might want to toss in `-Wextra` as well for good measure. I am not sure about the edit though, because `g++` **is** to be preferred over `gcc -lstdc++`... – DevSolar Jan 30 '15 at 13:30
  • since we are here, why not do it right to the end: add a `-Werror` – bolov Jan 30 '15 at 13:30
  • 5
    Since when is iostreams and `std::cout` part of the Standard Template Library? – T.C. Jan 30 '15 at 13:45
  • @T.C. Since SGI's STL became conflated with the standard library? – sjdowling Jan 30 '15 at 13:48
  • 1
    Why is -Werror needed? I have revised the documentation and if I understand well will make the warnings errors and will make my projects less easy to compile. – D1X Jan 31 '15 at 15:02
  • 12
    @D1X: Because there's a nasty habit among programmers to *ignore* warnings. Virtually everything that `-Wall` and even `-Wextra` warn about is either a very real problem, or sloppy coding that can very easily be fixed. The message here is to get into a habit where you consider compiler warnings a helpful pointer to where your code could be improved, instead of a nuisance. There are *hundreds* of questions here on SO that wouldn't have been necessary in the first place if the OP had used `-Wall -Wextra`. `-Werror` is simply reinforcing that. – DevSolar Feb 02 '15 at 11:54
  • @shauryachats, re:"g++ should be preferred over gcc" Is the exception that you may prefer gcc because it compiles .c files as C and .cpp files as C++, whereas g++ will compile both file types as C++? So, you might have institutional conventions or practical reasons (maybe speed?) for preferring your .c files to compile as C rather than as C++? – Kaleb Coberly May 21 '21 at 20:18
  • I was having a very similar problem with an application built by someone else. This solution helped me immensely. In my case, they were using cmake to setup the compile operations, so to the end of the cmake command I needed to add: `-DCMAKE_EXE_LINKER_FLAGS="-lstdc++"`. – Maculin Dec 22 '21 at 15:48
  • For those (like me) wondering why use g++ instead of gcc: https://stackoverflow.com/a/172592/1169233 – Waldir Leoncio Mar 28 '23 at 08:26
78

Yes, using g++ command worked for me:

g++ my_source_code.cpp
shauryachats
  • 9,975
  • 4
  • 35
  • 48
A B
  • 888
  • 6
  • 4
9

Assuming code.cpp is the source code, the following will not throw errors:

make code
./code

Here the first command compiles the code and creates an executable with the same name, and the second command runs it. There is no need to specify g++ keyword in this case.

Peter Mortensen
  • 30,738
  • 21
  • 105
  • 131
losnihciL
  • 127
  • 1
  • 5
6

Makefiles

If you're working with a makefile and you ended up here like me, then this is probably what you're looking or:

If you're using a makefile, then you need to change cc as shown below

my_executable : main.o
    cc -o my_executable main.o

to

CC = g++

my_executable : main.o
    $(CC) -o my_executable main.o
iggy12345
  • 1,233
  • 12
  • 31
  • 3
    You should use `$(CXX)` for the c++ compiler in Make. – unDeadHerbs Apr 03 '22 at 13:31
  • Aren't *make* files dependent on a TAB character? There aren't any in the Markdown source in this answer. At least it could be mentioned (if it is the case). – Peter Mortensen Apr 03 '22 at 13:57
  • @unDeadHerbs That's a good point, yes, you should. – iggy12345 Apr 05 '22 at 05:02
  • @PeterMortensen It's common knowledge that you need to use the literal tab character in make, I don't know how to insert tab characters into markdown, but you're more than welcome to fix it if you can – iggy12345 Apr 05 '22 at 05:04
  • 1
    @iggy12345: A TAB character can be *pasted* into the Markdown source. It is preserved (not converted), but it is rendered as spaces on the web page (thus probably too subtle to be useful). – Peter Mortensen May 11 '22 at 13:44
1

Adding the following line in your CMake makes gcc link with std and therefore recognize std::cout

target_link_libraries(your_project
        PRIVATE
        -lstdc++
        )
0

FWIW, if you want a makefile, here is how you can do either answer by switching the compiler at the top.

# links stdc++ library by default
# CC := g++
# or
CC := cc

all: hello

util.o: util.cc
        $(CC) -c -o util.o  util.cc

main.o: main.cc
        $(CC) -c -o main.o  main.cc

# notice -lstd++ is after the .o files
hello: main.o util.o
        $(CC) -o hello main.o util.o -lstdc++

clean:
        -rm util.o main.o hello
Peter Mortensen
  • 30,738
  • 21
  • 105
  • 131
netskink
  • 4,033
  • 2
  • 34
  • 46
  • Aren't *make* files dependent on a TAB character? There aren't any in the Markdown source in this answer. At least it could be mentioned (if it is the case). – Peter Mortensen Apr 03 '22 at 13:55
  • it was spaced over to make it into format for viewing as a code block in the markdown. If you know how to edit it so it looks like code and yet has makefile tabs, i would appreciate it. – netskink Apr 04 '22 at 17:06