std :: map尽可能是静态的吗?

时间:2018-03-14 15:35:31

标签: c++ memory-management dynamic-memory-allocation

考虑具有相同效果的3个版本的代码:

版本1:

int main()  {
    std::map<int,int> x = {{0,0}, {1,1}, {2,2}};
    // Do some stuff...
    return 0;
}

第2版:

int main()  {
    std::map<int,int> x;
    x[0] = 0;
    x[1] = 1;
    x[2] = 2;
    // Do some stuff...
    return 0;
}

第3版:

int main()  {
    std::map<int,int> x;
    x.insert(std::pair<int,int>(0,0));
    x.insert(std::pair<int,int>(1,1));
    x.insert(std::pair<int,int>(2,2));
    // Do some stuff...
    return 0;
}

这些代码的效率是多少?

我认为版本1是完全静态的分配:x所需的空间被分配一次并设置值。 我还认为版本3需要动态分配:每次调用insert都会检查密钥是否尚未使用,检查插入位置并在分配值之前分配更多空间进行映射。 对于版本2,我不确定。你能帮帮我吗?

3 个答案:

答案 0 :(得分:4)

C ++标准对于在编译时或运行时是否发生分配没有要求。所有这些意味着实现可以自由地进行优化(或不是)。

所以要做的就是测试。

这种优化很可能尚未实施。尽管您在此处创建的constexpr可能是编译时常量(请注意,此处未执行聚合初始化),但std::map没有std::initializer_list构造函数。 p>

std::map<int,int> x = {{0,0}, {1,1}, {2,2}};

答案 1 :(得分:2)

虽然定义了它的实现,但std::map的分配永远不会是静态的。它使用RB tree 作为99个案例中的基础数据结构 在您的情况下,在所有三种情况下,您具有完全相同的时间和空间复杂性。

答案 2 :(得分:1)

在所有这些推测之后,我终于分析了代码。为此,我在问题中生成了3个代码,但有100,000个条目。以下是几次运行的平均结果,使用g ++编译而没有优化:

  • 版本1:26毫秒(编译时间:2.5秒)
  • 版本2:80毫秒(编译时间:10秒)
  • 第3版:73毫秒(编译时间:37秒)

很明显,最好的解决方案是第一个。版本2和版本3在执行时几乎相同,但版本3在编译时确实更差。