STL喜欢容器typedef快捷方式?

时间:2008-09-24 03:04:27

标签: c++ stl

STL容器的常见模式是:

map<Key, Value> map;
for(map<Key, Value>::iterator iter = map.begin(); iter != map.end(); ++iter)
{
  ...
}

因此,为了避免编写模板参数的声明,我们可以在某处执行此操作:

typedef map<Key, Value> TNiceNameForAMap;

但是如果这个映射仅用于单个函数或单个迭代,则这是一个烦人的开销。

这种typedef有什么方法吗?

7 个答案:

答案 0 :(得分:10)

不确定“开销”是什么意思。如果它简化了你编写代码的方式,那就使用它,否则坚持使用简写。

如果它仅在限制范围内使用,请将typedef放在同一范围内。然后,它不需要发布,记录或出现在任何UML图表上。例如(我并不认为这是其他方面的最佳代码):

int totalSize() {
    typedef std::map<Key, Value> DeDuplicator;
    DeDuplicator everything;

    // Run around the universe finding everything. If we encounter a key
    // more than once it's only added once.

    // now compute the total
    int total = 0;
    for(DeDuplicator::iterator i = everything.begin(); i <= everything.end(); ++i) {
        total += i->second.size(); // yeah, yeah, overflow. Whatever.
    }
    return total;
}

结合Ferruccio的建议(如果你正在使用boost),循环变为:

BOOST_FOREACH(DeDuplicator::pair p, everything) {
    total += p.second.size();
}

结合bk1e的建议(如果你正在使用C ++ 0x或具有来自它的功能),并假设BOOST_FOREACH以我认为应该基于以下事实与auto交互:它通常可以处理隐式转换兼容类型:

std::map<Key, Value> everything;
// snipped code to run around...
int total = 0;
BOOST_FOREACH(auto p, everything) {
    total += p.second.size();
}

不错。

答案 1 :(得分:5)

您可以使用Boost.Foreach

答案 2 :(得分:3)

C ++标准的未来版本(称为C++0x)将引入new use for the auto keyword,允许您编写如下内容:

map<Key, Value> map;
for(auto iter = map.begin(); iter != map.end(); ++iter)
{
  ...
}

答案 3 :(得分:2)

我个人认为 MYMAP :: iterator map&lt; int,string&gt; :: iterator 甚至 std :: map&lt; int,std更具可读性:: string&gt; :: iterator 所以我总是做typedef。唯一的开销是一行代码。

编译代码后,可执行文件的大小或速度没有差异。这只是可读性。

答案 4 :(得分:0)

如果typedef是单个函数的本地函数,则它甚至不需要是 nice 名称。使用X或MAP,就像在模板中一样。

答案 5 :(得分:0)

C ++ 0x还将提供基于范围的for循环,类似于迭代循环用于其他语言。

不幸的是,GCC尚未实现基于范围的(但 实现自动)。

编辑:同时,还要考虑键入解码迭代器。它没有绕过一次使用的typedef(除非你把它放在一个标题中,这总是一个选项),但是它使得结果代码缩短了一个:: iterator。

答案 6 :(得分:0)

在过去的几年里,我真的试图摆脱使用手动编写的循环而不是使用STL算法。您的上述代码可以更改为:

struct DoLoopBody {
  template <typename ValueType>
  inline void operator()(ValueType v) const {
    // ...
  }
};

std::for_each (map.begin(), map.end(), DoLoopBody ());

不幸的是,DoLoopBody类不能是本地类,这通常被强调为缺点。但是,我认为这是一个优势,因为循环体现在可以单独进行单元测试。