Ano*_*non 5 c++ stl vector return-value stdvector
我知道这是一个非常糟糕的主意,所以有关如何有效地做到这一点的其他建议将会受到好评.
这就是事情.我有map<string,vector<string> >,我想搜索一个键并返回其相应的值(在这种情况下字符串的向量).我坚持返回(而不是仅仅迭代)的原因是我需要搜索其他向量中返回的值.
一个例子可以说明这一点:
Input:
key1 ---> {2,3,4}
key2 ---> {1}
key3 ---> {2,12,11,9}
Run Code Online (Sandbox Code Playgroud)
对于key1作为输入,应返回值为2,3,4的向量.现在需要在其他字符串向量中搜索这些2,3,4值.最有效的方法是什么?
我试过这样的事情:
vector<string> returnEdges(string key)
{
for (map<string, vector<string> >::iterator it=outgoing.begin();
it!=outgoing.end();++it)
{
if (key.compare((*it).first)==0)
{
return (*it).second;
}
}
//return string<;//what should I return here????
}
Run Code Online (Sandbox Code Playgroud)
1)如果找不到密钥,我应该如何返回空向量?
2)实现这个的最佳方法是什么?
我希望这个问题很清楚.
编辑:当我写这个问题时,我想为什么不返回迭代器?SO的人是否批准了这个想法?
1)返回迭代器是个好主意.当你这样做时,指示"未找到"情况的自然方式是返回.end()迭代器.这有一个缺点,即抽象有点漏洞:调用者必须能够得到这个.end()值以便与它进行比较以进行错误检查,并且返回的迭代器暴露出比你更丰富的接口喜欢(客户端代码不应该真正使用递增和递减迭代器).
2)返回一个空向量就像创建一个空向量并返回它一样简单.创建一个空向量=构造一个空的向量.这就是你得到的结果 - 鼓roll - vector类的默认构造函数.
3)您不需要也不应该自己实现搜索循环.标准库已经为您实现了这一点.(有专门find的功能map,因为键/值的区别秒.对于像序列list,vector并且deque,更喜欢自由的功能std::find,它来自<algorithm>.
4)您应该更喜欢接受函数参数(当它们是类的实例时std::string),并通过const引用返回数据(尤其是复杂的东西,如字符串向量).按价值传递和返回意味着副本; 有时编译器可以优化它,但它不如我们所希望的那样可靠.此外,你首先使用C++的原因是对事物有这种程度的控制权,对吧?如果没有,那就不要用它来折磨自己.
但是,如果您要在某些时候返回新创建的值,则无法执行此操作.另一种设计接口的方法是在映射中返回指向字符串向量的指针(注意这些字符串上的指针算法无效),如果找不到值,则返回NULL指针.这避免了复制和区分"未找到"结果与数据中的实际空向量,但这意味着客户端代码必须处理一个icky原始指针.
5)在函数名称中"返回"是无用的,因为返回是函数的作用.OTOH,以某种方式命名事物是一个好主意,这使得参数就是它们的原因.
6)对于复杂类型的迭代器,设置typedef通常是个好主意.
返回迭代器非常简单:
typedef map<string, vector<string> >::iterator graph_iterator;
graph_iterator edges_named(const string& node_name) {
return outgoing.find(node_name);
}
Run Code Online (Sandbox Code Playgroud)
返回字符串向量非常简单:
typedef map<string, vector<string> >::iterator graph_iterator;
vector<string> edges_named(const string& node_name) {
graph_iterator it = outgoing.find(node_name);
return it == outgoing.end() ? vector<string>() : it->second;
}
Run Code Online (Sandbox Code Playgroud)
返回指针很简单:
typedef map<string, vector<string> >::iterator graph_iterator;
vector<string>* edges_named(const string& node_name) {
graph_iterator it = outgoing.find(node_name);
return it == outgoing.end() ? NULL : &(it->second);
}
Run Code Online (Sandbox Code Playgroud)
做出明智的选择.