mirror of
https://github.com/zh-google-styleguide/zh-google-styleguide.git
synced 2026-08-13 22:13:27 +08:00
Merge pull request #19 from HorkyChen/master
更改Forward Declaration的翻译从前向声明改为前置声明
This commit is contained in:
@@ -44,7 +44,7 @@
|
||||
|
||||
.. _forward-declarations:
|
||||
|
||||
1.3. 前向声明
|
||||
1.3. 前置声明
|
||||
~~~~~~~~~~~~~~~~~~~~~~
|
||||
|
||||
.. tip::
|
||||
@@ -53,7 +53,7 @@
|
||||
|
||||
定义:
|
||||
|
||||
所谓「前向声明」(forward declaration)是类,函数和模板的纯粹声明,没伴随着其定义。代码中用到了哪些 symbols, 往往可以用其前向声明来代替对应的 ``#includes``.
|
||||
所谓「前置声明」(forward declaration)是类,函数和模板的纯粹声明,没伴随着其定义。代码中用到了哪些 symbols, 往往可以用其前置声明来代替对应的 ``#includes``.
|
||||
|
||||
优点:
|
||||
|
||||
@@ -62,19 +62,19 @@
|
||||
|
||||
缺点:
|
||||
|
||||
* 如果前向声明关系到模板,typedefs, 默认参数和 using 声明,就很难决定它的具体样子了。
|
||||
* 很难判断什么时候该用前向声明,什么时候该用 ``#includes``, 特别是涉及隐式转换运算符的时候。极端情况下,用前向声明代替 ``includes`` 甚至都会暗暗地改变代码的含义。
|
||||
* 前向声明了不少来自头文件的 symbol 时,就会比单单 ``includes`` 一行冗长。
|
||||
* 前向声明函数或模板有时会害得头文件开发者难以轻易变动其 API. 就像扩大形参类型,加个自带默认参数的模板形参等等。
|
||||
* 前向声明来自命名空间 ``std::` 的 symbol 时,其行为未定义。
|
||||
* 仅仅为了能前向声明而重构代码(比如用指针成员代替对象成员),后者会变慢且复杂起来。
|
||||
* 还没有实践证实前向声明的优越性。
|
||||
* 如果前置声明关系到模板,typedefs, 默认参数和 using 声明,就很难决定它的具体样子了。
|
||||
* 很难判断什么时候该用前置声明,什么时候该用 ``#includes``, 特别是涉及隐式转换运算符的时候。极端情况下,用前置声明代替 ``includes`` 甚至都会暗暗地改变代码的含义。
|
||||
* 前置声明了不少来自头文件的 symbol 时,就会比单单 ``includes`` 一行冗长。
|
||||
* 前置声明函数或模板有时会害得头文件开发者难以轻易变动其 API. 就像扩大形参类型,加个自带默认参数的模板形参等等。
|
||||
* 前置声明来自命名空间 ``std::` 的 symbol 时,其行为未定义。
|
||||
* 仅仅为了能前置声明而重构代码(比如用指针成员代替对象成员),后者会变慢且复杂起来。
|
||||
* 还没有实践证实前置声明的优越性。
|
||||
|
||||
结论:
|
||||
|
||||
* 函数:用 ``#include``.
|
||||
* 类模板:优先用 ``#includes``.
|
||||
* 类:用前向声明固然不错,但小心点。若说不定,还是用 ``#includes`` 好了。
|
||||
* 类:用前置声明固然不错,但小心点。若说不定,还是用 ``#includes`` 好了。
|
||||
* 千万别为了避免 ``includes`` 而把数据成员改成指针。
|
||||
|
||||
至于什么时候包含头文件,参见 :ref:`name-and-order-of-includes`。
|
||||
@@ -193,6 +193,6 @@ C/C++ 函数参数分为输入参数, 输出参数, 和输入/输出参数三种
|
||||
|
||||
#. 原来还真有项目用 ``#includes`` 来插入文本,且其文件扩展名 ``.inc`` 看上去也很科学。
|
||||
#. Google 已经不再提倡 ``-inl.h`` 用法。
|
||||
#. 注意,前向声明的类是不完全类型(incomplete type),我们只能定义指向该类型的指针或引用,或者声明(但不能定义)以不完全类型作为参数或者返回类型的函数。毕竟编译器不知道不完全类型的定义,我们不能创建其类的任何对象,也不能声明成类内部的数据成员。
|
||||
#. 注意,前置声明的类是不完全类型(incomplete type),我们只能定义指向该类型的指针或引用,或者声明(但不能定义)以不完全类型作为参数或者返回类型的函数。毕竟编译器不知道不完全类型的定义,我们不能创建其类的任何对象,也不能声明成类内部的数据成员。
|
||||
#. 类内部的函数一般会自动内联。所以某函数一旦不需要内联,其定义就不要再放在头文件里,而是放到对应的 ``.cc`` 文件里。这样可以保持头文件的类相当精炼,也很好地贯彻了声明与定义分离的原则。
|
||||
#. 在 ``#include`` 中插入空行以分割相关头文件, C 库, C++ 库, 其他库的 ``.h`` 和本项目内的 ``.h`` 是个好习惯。
|
||||
|
||||
Reference in New Issue
Block a user