2

我在头文件中声明了一个静态无序映射,如下所示:

static boost::unordered_map<KeyAction, sf::Key::Code> WindowKeyMap;

在同一个头文件中,我有一个用一些值填充地图的函数:

static void Initialize(std::string &file)
{
    WindowKeyMap[MoveLeft] = sf::Key::Code::Left;
    WindowKeyMap[MoveRight] = sf::Key::Code::Right;
    WindowKeyMap[MoveUp] = sf::Key::Code::Up;
    WindowKeyMap[MoveDown] = sf::Key::Code::Down;
    std::cout << std::endl << WindowKeyMap.size() << std::endl;
}

稍后在我的程序中,在一个单独的类/函数中,我尝试读取其中一个值:

std::cout << std::endl << WindowKeyMap.size() << std::endl;
auto test2 = WindowKeyMap[MoveRight];

但地图总是空的。控制台的输出始终是初始化例程中的 4,然后是第二个 cout 中的 0。我认为静态地图在整个程序中是持久的,所以我对我的静态地图如何变成空有点困惑。任何人都可以解释一下吗?

谢谢

4

2 回答 2

9

当您在标头中声明变量时,每个编译单元 (*.cpp) 都会获得它自己的本地静态副本。你必须声明它extern

extern boost::unordered_map<KeyAction, sf::Key::Code> WindowKeyMap;

并在一个 cpp 中放置

boost::unordered_map<KeyAction, sf::Key::Code> WindowKeyMap;
于 2011-03-26T09:26:45.807 回答
1

很简单:只是不要这样做。虽然您可以按照@Eelke 的建议摆脱初始化和范围,但从长远来看,您将自取其辱……您真的希望每个人都可以访问哈希表吗?您真的接受无法控制访问(显然很重要)数据的风险吗?你真的想在你的应用程序中拥有一个不可测试的全局状态吗?您是否真的希望将引入的所有依赖项引入<unordered_map>程序的许多翻译单元中?我可以这样继续一段时间,但重点是:将逻辑和数据包装到一个类中,并通过接口提供服务。通过工厂或依赖容器创建接口实例并显式管理该对象的生命周期。

问候,

保罗

于 2011-03-26T09:43:55.917 回答