【问题标题】:Why are these global variables when they have namespace scope?为什么这些全局变量具有命名空间范围?
【发布时间】:2015-08-11 17:39:21
【问题描述】:

在以下代码中,this 正在调用 globals.cpp 命名空间中的变量实际全局变量

globals.h

#ifndef GLOBALS_H_
#define GLOBALS_H_

namespace Constants
{
    // forward declarations only
    extern const double pi;
    extern const double avogadro;
    extern const double my_gravity;
}

#endif

globals.cpp

namespace Constants
{
    // actual global variables
    extern const double pi(3.14159);
    extern const double avogadro(6.0221413e23);
    extern const double my_gravity(9.2); // m/s^2 -- gravity is light on this planet
}

source.cpp

#include <iostream>
#include <limits>

#include "globals.h"

int main()
{
    double value_of_pi = Constants::pi;

    std::cout << value_of_pi;

    std::cin.clear();
    std::cin.ignore(std::numeric_limits<std::streamsize>::max(), '\n');
    std::cin.get();

    return 0;
}

我知道extern 用于访问其他翻译单元中的全局变量。我可能对此读得太多了,但是为什么 globals.cpp 命名空间中的变量在它们具有命名空间范围时被认为是全局的?另外,我是否可以假设 Constants::pi 从 globals.h 命名空间中的前向声明中检索标识符 pi

这个问题是我之前提出的问题的延续here

【问题讨论】:

    标签: c++ namespaces scope global-variables forward-declaration


    【解决方案1】:

    全局大致意味着可以从每个翻译单元访问,无论变量是否在命名空间中。最好的例子是std::cout,它是namespace std中定义的一个全局变量,代表std::basic_ostream&lt;&gt;的一个实例化。

    关于您的第二个问题,Constants::pi 是可访问的,因为您包含标题 globals.h,它声明了 extern const double Constants::pi;。此声明指示编译器该变量具有外部链接,您有责任在某个 .cpp 文件中定义它(您在 globals.cpp 中执行此操作)1)。所以链接器能够在globals.cpp 中找到符号,就是这样。


    1) 请注意,您甚至可以直接在头文件中提供定义extern const double pi = 3.14;,但不建议这样做,因为在多个翻译单元中包含头文件会导致重复符号。

    【讨论】:

    • 非常感谢!现在在我的脑海中,这个世界变得更有意义了。
    猜你喜欢
    • 2012-05-03
    • 1970-01-01
    • 2012-03-13
    • 2011-03-25
    • 1970-01-01
    • 2012-07-17
    • 2016-08-19
    • 2011-08-31
    相关资源
    最近更新 更多