我对编程比较陌生,目前正在学习C ++。我怀疑我的逻辑是否正确,但这是我一直试图解决的问题:
我有一个简单的程序,可以输出矢量的大小和内容;
vector<int> v1;
vector<int> v2(10);
vector<int> v3(10, 42);
vector<int> v4{ 10 };
vector<int> v5{ 10, 42 };
vector<string> v6{ 10 };
vector<string> v7{ 10, "hi" };
//and so on...........
bool firstPass= true;
for (auto i : v3){
if (firstPass) cout << "Vector size: " << v3.size() << ".\nElements: " << i << ", ";
cout << i << ", ";
firstPass= false;
}
如果我想迭代另一个向量,我必须手动将v3更改为vX,但我喜欢的是这段代码通过所有向量。
我尝试了几种方法,比如创建一个
vector<string> V8{"v1","v2","v3"..}
for (auto i : V8[counter])
但基本上我已经失败了因为&#34; v1&#34; != v1。(这是我得到&#34;将字符串转换为向量&#34;想法的地方,但有些东西告诉我这不是这样做的方法......)
任何帮助&amp;我会非常感谢批评,并且道歉,因为我可能会在过于具体甚至无用的情况下提出批评,考虑到我试图解决这个问题的方式可能有问题而且我提出了错误的问题!
答案 0 :(得分:1)
解决通过表示变量名称的字符串查找变量的文字问题:POSIX提供的唯一一个按名称查找全局变量的工具是dlsym()
。它只适用于全局变量,你必须使用extern "C"
声明你的函数来抑制C ++名称修改(全局变量名称不会被破坏)。
#include <vector>
#include <assert.h>
#include <dlfcn.h>
std::vector<int> v1;
int main () {
void *h = dlopen(0, RTLD_NOW);
void *v = dlsym(h, "v1");
assert(v == &v1);
}
要使上面的示例正常工作,您需要使用g++ -rdynamic prog.cpp -ldl
进行编译。
这种技术的局限在于你需要知道先验返回的指针的类型,并相应地进行投射。
如果你愿意&#34;通过&#34;你的数组为一个函数打印出每个数组,你可以实现一个可变参数模板函数来做到这一点。
template <typename Vector>
void print_all_vectors (Vector v) {
/* enforce we are only interested in vectors */
const std::vector<typename Vector::value_type> &vr = v;
std::cout << "Vector size: " << vr.size() << ".";
if (!vr.empty()) std::cout << "\nElements";
bool first = true;
for (auto i : vr) {
std::cout << (first ? ": " : ", ") << i;
first = false;
}
std::cout << '\n';
}
template <typename Vector, typename... Vectors>
void print_all_vectors (Vector v, Vectors... vectors) {
print_all_vectors(v);
print_all_vectors(vectors...);
}
上面代码中的第一个模板打印出一个矢量。第二个模板函数递归地解包variadic参数列表,并将每个参数列表传递给第一个模板函数。
使用这些功能很简单,如下所示:
std::vector<int> v1{1, 3, 5, 7};
std::vector<std::string> v2{"doh", "ray", "me"};
print_all_vectors(v1, v2);
答案 1 :(得分:1)
你需要C ++ 11,但这绝对是可能的:
template<typename V>
void PrintVector(V const& v) {
for (auto elem : v) std::cout << elem << " ";
std::cout << std::endl;
}
template <typename V, typename ... Vectors>
void PrintAll(V const& v1, Vectors... vtail)
{
PrintVector(v);
PrintAll(vtail...);
}
PrintAll(v1, v2, v3, v4, v5, v6, v7, v8, v9);
答案 2 :(得分:0)
如果你需要在运行时解析的东西,你需要迭代一些东西,你可以使用矢量矢量但它们应该是相同的类型(与int混合的字符串向量是不可能的,因为它们是不同的类型由于模板即时) 另一方面,您可以对静态内容或模板使用预处理器和宏扩展
答案 3 :(得分:0)
(这是一个评论而不是一个答案,但我列出了一些代码太长的评论......)
如果您不想清除代码只有vector<vector<int>>
+ vector<vector<string>>
,vector<vector<boost::variant<int,string>>>
或类似代码,那么您可以创造例如vector<vector<int>*>
和vv.push_back(&v1); vv.push_back(&v2);
等人避免了复制费用。
没有办法轻松迭代调用v1
,v2
,v3
等变量。(预处理器可以做到但是它& #39;很复杂 - 如果你想追求那个,请参阅boost预处理器库。
最简单的方法是使用更简洁的便利功能来执行push_backs ......就像这样:
vector<vector<int>>& operator<<(vector<vector<int>>& vv, vector<int>& v)
{
vv.push_back(v);
return vv;
}
然后你可以编码......
vv << v1 << v2 << v3 << v4 << v5;
理想情况下,您将操作符放在匿名命名空间中,以便只有您的代码才能看到它,避免意外使用或其他代码中的潜在冲突。
答案 4 :(得分:0)
如果您只是将string
转换为vector<int>
,那么此示例可能会让您了解如何执行此操作。
#include <iostream>
#include <string>
#include <vector>
using namespace std;
int main()
{
string str = "1234567890";
vector<int> intedStr;
for (size_t i = 0; i < str.length(); i++)
{
intedStr.push_back((int)str[i] - '0');
}
for (size_t i = 0; i < intedStr.size(); i++)
{
cout << intedStr[i] << " ";
}
system("pause");
}
注意:这不是安全功能。如果您想将"abcsd"
转换为vector<int>
会怎样?