开发者

What's the difference between inline member function and normal member function?

Is there any difference between inline member function (function body inline) and other normal member function (function body in a separate .c开发者_如何学Pythonpp file)?

for example,

class A
{
  void member(){}
};

and

// Header file (.hpp)

class B
{
  void member();
};

// Implementation file (.cpp)

void B::member(){}


There is absolutely no difference.

The only difference between the two is that the member inside the class is implicitly tagged as inline. But this has no real meaning.

See: inline and good practices

The documentation says that the inline tag is a hint to the compiler (by the developer) that a method should be inlined. All modern compilers ignore this hint and use there own internal heuristic to determine when a method should be inlined (As humans are notoriously bad and making this decision).

The other use of inline is that it tells the linker that it may expect to see multiple definitions of a method. When the function definition is in the header file each compilation unit that gets the header file will have a definition of the function (assuming it is not inlined). Normally this would cause the linker to generate errors. With the inline tag the compiler understands why there are multiple definitions and will remove all but one from the application.

Note on inlining the processes: A method does not need to be in the header file to inlined. Modern compilers have a processes a full application optimization where all functions can be considered for inlining even if they have been compiled in different compilation units. Since the inline flag is generally ignored it make no difference if you put the method in the header or the source file.


Ignore the word inline here and compiler hints because it is not relevant.

The big practical difference in A and B is when they are used in different libraries.

With the case of A you can #include the header and are not required to link against anything. So you can use this class from different applications / libraries without any special linkage.

With the case of B, you need B.cpp and this should be compiled only into one library / application. Any other library or application that needs to use this class will need to link against the one that contains the actual body of the code.

With some setups / implementations you will need to specifically mark the class as "exported" or "imported" between libraries (for example with Windows you can use dllimport / dllexport and with GNU you can use attribute(visibility="default") )


The first one is implicitly inline, i.e. suggesting the compiler to expand it at the call site.


Other than the inline thing, there's a difference in that you could put more definitions in between the definition of class B, and the definition of the function.

For example, B.cpp might include header files that B.hpp doesn't, which can make a significant difference to the build process for large projects.

But even without a separate translation unit, you can occasionally have a circular dependency that's resolved by separating the definitions. For example the function might take a parameter of a type that's forward-declared before B is defined, then defined by the time the function is defined. If that type uses the definition of B in its own definition, it can't just be be defined before B.

0

上一篇:

下一篇:

精彩评论

暂无评论...
验证码 换一张
取 消

最新问答

问答排行榜