0

In C++, I need to define some inline general functions. However, when I write the prototype in a header file and the implementation in a.cpp file, I encounter with "LNK2001 unresolved external symbol" error.

Shall I remove the .cpp file and implement the function in the header file?

I am trying to define some shared non-member math functions that can be used by other classes.

Header file:

inline void foo()
{
    //some code
}

.cpp file

//nothing
  • 3
    Please provide a [mcve]. – Passer By Feb 15 '19 at 08:38
  • This is a linking problem. – schorsch312 Feb 15 '19 at 08:40
  • 1
    Yes, inline functions should be in the header file. There's (usually) no need for seperate prototype and implementation. – john Feb 15 '19 at 08:40
  • How should the compiler inline a function if cannot see the code? It's only possible if implementation is provided in header. (This is independent of keyword `inline` which has a different meaning nowadays.) – Scheff's Cat Feb 15 '19 at 08:42
  • Quite similar to [why templates can only be implemented in header files](https://stackoverflow.com/questions/495021/why-can-templates-only-be-implemented-in-the-header-file), just that the explicit instantiation trick cannot be applied... – Aconcagua Feb 15 '19 at 08:43
  • 1
    _Shall I remove the .cpp file and implement the function in the header file?_ - Yes, if you only have inline functions in the header file, there's no reason for a `cpp` file. – Ted Lyngmo Feb 15 '19 at 08:43
  • Possible duplicate of [inline function linker error](https://stackoverflow.com/questions/953710/inline-function-linker-error) – Ayxan Haqverdili Feb 15 '19 at 08:44
  • 1
    Concerning `inline`: [inline specifier](https://en.cppreference.com/w/cpp/language/inline). – Scheff's Cat Feb 15 '19 at 08:46

2 Answers2

4

The name of the inline specifier is somewhat misleading, as it suggests that the function be inlined. However, inline foremost specifies the linkage of the function (it's also a hint to the compiler to consider inlining). For a function declared inline no linkable symbol is generated in the compiled object.

Therefore, inline functions only make sense when defined (not merely declared) in a header file, which is included by, possibly, many compilation units. The inline specifier than prevents multiple (in fact any) symbols for this function to be emitted by the compiler in the respective object files.

If you need a small function only once for one compilation unit, you don't need to declare it anywhere else. Moreover, you don't need to declare it inline, but place it in the anonymous namespace to prevent it from being visible (in the object file generated).

So, either (that's most likely your use case)

// foo.hpp:
inline void foo(bar x) { /* ... */ }  // full definition

// application.cpp:
#include "header.hpp"

/* ... */ foo();

or

// application.cpp:
namespace {
    inline void foo(bar x)   // inline specifier redundant
    { /* ... */ }
}

/* ... */ foo();
Ted Lyngmo
  • 37,764
  • 5
  • 23
  • 50
Walter
  • 40,885
  • 16
  • 97
  • 176
0

If you want your function to be in-line, you have to provide the definition in the header. If you have it in a separate cpp file it wont be in-lined. The link error is usually due to not including the cpp file during linking stage.