C++ 用C++在头文件中编写函数定义
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/453372/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me):
StackOverFlow
Writing function definition in header files in C++
提问by Navaneeth K N
I have a class which has many small functions. By small functions, I mean functions that doesn't do any processing but just return a literal value. Something like:
我有一个有很多小功能的类。对于小函数,我的意思是不做任何处理而只返回一个文字值的函数。就像是:
string Foo::method() const{
return "A";
}
I have created a header file "Foo.h" and source file "Foo.cpp". But since the function is very small, I am thinking about putting it in the header file itself. I have the following questions:
我创建了一个头文件“Foo.h”和源文件“Foo.cpp”。但是由于函数很小,我想把它放在头文件本身中。我有以下问题:
- Is there any performance or other issues if I put these function definition in header file? I will have many functions like this.
- My understanding is when the compilation is done, compiler will expand the header file and place it where it is included. Is that correct?
- 如果我将这些函数定义放在头文件中,是否有任何性能或其他问题?我会有很多这样的功能。
- 我的理解是编译完成后,编译器会展开头文件并将其放在包含它的位置。那是对的吗?
回答by Johannes Schaub - litb
If the function is small (the chance you would change it often is low), and if the function can be put into the header without including myriads of other headers (because your function depends on them), it is perfectly valid to do so. If you declare them extern inline, then the compiler is required to give it the same address for every compilation unit:
如果函数很小(您经常更改它的机会很小),并且可以将函数放入标头而不包含无数其他标头(因为您的函数依赖于它们),那么这样做是完全有效的。如果您将它们声明为 extern inline,则编译器需要为每个编译单元提供相同的地址:
headera.h:
标题a.h:
inline string method() {
return something;
}
Member functions are implicit inline provided they are defined inside their class. The same stuff is true for them true: If they can be put into the header without hassle, you can indeed do so.
成员函数是隐式内联的,前提是它们是在它们的类中定义的。同样的事情对他们来说也是如此:如果他们可以毫不费力地放入标题中,你确实可以这样做。
Because the code of the function is put into the header and visible, the compiler is able to inline calls to them, that is, putting code of the function directly at the call site (not so much because you put inline before it, but more because the compiler decides that way, though. Putting inline only is a hint to the compiler regarding that). That can result in a performance improvement, because the compiler now sees where arguments match variables local to the function, and where argument doesn't alias each other - and last but not least, function frame allocation isn't needed anymore.
因为函数的代码放在header里面并且是可见的,所以编译器可以内联对它们的调用,也就是直接把函数的代码放在调用处(不是因为你在它之前放了内联,而是更多因为编译器是这样决定的。仅将内联放置是对编译器的一个提示)。这可以提高性能,因为编译器现在可以看到参数匹配函数局部变量的位置,以及参数不会相互别名的位置 - 最后但并非最不重要的是,不再需要函数框架分配。
My understanding is when the compilation is done, compiler will expand the header file and place it where it is included. Is that correct?
我的理解是编译完成后,编译器会展开头文件并将其放在包含它的位置。那是对的吗?
Yes, that is correct. The function will be defined in every place where you include its header. The compiler will care about putting only one instance of it into the resulting program, by eliminating the others.
对,那是正确的。该函数将在您包含其标题的每个地方定义。编译器会关心只将它的一个实例放入生成的程序中,通过消除其他实例。
回答by Ferruccio
Depending on your compiler and it's settings it may do any of the following:
根据您的编译器及其设置,它可能会执行以下任何操作:
- It may ignore the inline keyword (it is just a hint to the compiler, not a command) and generate stand-alone functions. It may do this if your functions exceed a compiler-dependent complexity threshold. e.g. too many nested loops.
- It may decide than your stand-alone function is a good candidate for inline expansion.
- 它可能会忽略 inline 关键字(它只是对编译器的提示,而不是命令)并生成独立函数。如果您的函数超过依赖于编译器的复杂性阈值,它可能会这样做。例如太多的嵌套循环。
- 它可能会决定您的独立函数是否适合内联扩展。
In many cases, the compiler is in a much better position to determine if a function should be inlined than you are, so there is no point in second-guessing it. I like to use implicit inlining when a class has many small functions only because it's convenient to have the implementation right there in the class. This doesn't work so well for larger functions.
在许多情况下,编译器在确定函数是否应该内联方面比您处于更好的位置,因此没有必要再猜测它。当一个类有很多小函数时,我喜欢使用隐式内联,只是因为在类中实现它很方便。这对于较大的函数效果不佳。
The other thing to keep in mind is that if you are exporting a class in a DLL/shared library (not a good idea IMHO, but people do it anyway) you need to be really careful with inline functions. If the compiler that built the DLL decides a function should be inlined you have a couple of potential problems:
要记住的另一件事是,如果您要导出 DLL/共享库中的类(恕我直言,这不是一个好主意,但无论如何人们都会这样做),您需要非常小心内联函数。如果构建 DLL 的编译器决定应该内联一个函数,那么您会遇到一些潜在的问题:
- The compiler building the program using the DLL might decide to not inline the function so it will generate a symbol reference to a function that doesn't exist and the DLL will not load.
- If you update the DLL and change the inlined function, the client program will still be using the old version of that function since the function got inlined into the client code.
- 使用 DLL 构建程序的编译器可能决定不内联函数,因此它会生成对不存在的函数的符号引用,并且 DLL 将不会加载。
- 如果您更新 DLL 并更改内联函数,则客户端程序仍将使用该函数的旧版本,因为该函数已内联到客户端代码中。
回答by Qubeuc
There will be an increase in performance because implementation in header files are implicitly inlined. As you mentioned your functions are small, inline operation will be so beneficial for you IMHO.
因为头文件中的实现是隐式内联的,所以性能会有所提高。正如您提到的,您的功能很小,恕我直言,内联操作对您非常有益。
What you say about compiler is also true.There is no difference for compiler—other than inlining—between code in header file or .cpp
file.
你说的编译器也是对的。编译器除了内联外,在头文件或.cpp
文件中的代码之间没有区别。
回答by sykora
If your functions are that simple, make them inline, and you'll have to stick them in the header file anyway. Other than that, any conventions are just that - conventions.
Yes, the compiler does expand the header file where it encounters the #include statements.
如果您的函数如此简单,请将它们内联,无论如何您都必须将它们粘贴在头文件中。除此之外,任何约定都只是-约定。
是的,编译器会在遇到 #include 语句的地方展开头文件。
回答by INS
It depends on the coding standards that apply in your case but:
这取决于适用于您的情况的编码标准,但:
Small functions without loops and anything else should be inlined for better performance (but slightly larger code - important for some constrained or embedded applications).
没有循环和其他任何东西的小函数应该被内联以获得更好的性能(但稍微大一点的代码 - 对于某些受限或嵌入式应用程序很重要)。
If you have the body of the function in the header you will have it by default inline(d) (which is a good thing when it comes to speed).
如果您在标题中有函数的主体,则默认情况下您将拥有它 inline(d) (这在速度方面是一件好事)。
Before the object file is created by the compiler the preprocessor is called (-E option for gcc) and the result is sent to the compiler which creates the object out of code.
在编译器创建目标文件之前,预处理器被调用(gcc 的 -E 选项)并将结果发送到编译器,编译器从代码中创建对象。
So the shorter answer is:
所以更简短的答案是:
-- Declaring functions in header is good for speed (but not for space) --
-- 在头文件中声明函数有利于速度(但不利于空间)-
回答by Pushpak Sharma
C++ won't complain if you do, but generally speaking, you shouldn't.
when you #include a file, the entire content of the included file is inserted at the point of inclusion. This means that any definitions you put in your header get copied into every file that includes that header.
For small projects, this isn't likely to be much of an issue. But for larger projects, this can make things take much longer to compile (as the same code gets recompiled each time it is encountered) and could significantly bloat the size of your executable. If you make a change to a definition in a code file, only that .cpp file needs to be recompiled. If you make a change to a definition in a header file, every code file that includes the header needs to be recompiled. One small change can cause you to have to recompile your entire project!
Sometimes exceptions are made for trivial functions that are unlikely to change (e.g. where the function definition is one line).
如果您这样做,C++ 不会抱怨,但一般来说,您不应该抱怨。
当您 #include 文件时,包含文件的全部内容将插入到包含点。这意味着您放入标题中的任何定义都会被复制到包含该标题的每个文件中。
对于小型项目,这可能不是什么大问题。但是对于较大的项目,这可能会使编译时间更长(因为每次遇到相同的代码都会重新编译)并且可能会显着增加可执行文件的大小。如果对代码文件中的定义进行更改,则只需重新编译该 .cpp 文件。如果对头文件中的定义进行更改,则需要重新编译包含该头文件的每个代码文件。一个小改动可能会导致您必须重新编译整个项目!
有时,对于不太可能改变的琐碎函数(例如,函数定义为一行的情况)会产生例外。
Source: http://archive.li/ACYlo(previous version of Chapter 1.9 on learncpp.com)
来源:http: //archive.li/ACYlo(learncpp.com 上第 1.9 章的先前版本)
回答by Naveen
You should use inline functions. Read this Inline Functionsfor a better understanding and the tradeoffs involved.
您应该使用内联函数。阅读此内联函数以获得更好的理解和所涉及的权衡。