虽然函数之外的声明和初始化(例如main
)没有问题,但您不能在函数之外拥有代码。您要么需要在初始化时正确设置值(如在 C++11 中),要么在 main 中填充全局对象:
std::vector<string> Aries;
/* ... */
int main() {
Aries.push_back("Taurus");
/* ... */
}
其他方式(不填充 main 中的向量)
单一值
还有其他不需要的方法.push_back
或主要的其他代码。例如,如果Aries
只包含一项,您可以使用std::vector<T>::vector(size_t s, T t)
withs == 1
和t == "Taurus"
:
std::vector<string> Aries(1, "Taurus");
/* ... */
int main() { /* ... */ }
如果您多次需要相同的值,您可以简单地调整s
。
多个不同的值
现在这变得有点棘手。您想vector
使用合适的构造函数来填充 。std::vector<T>
在 C++03 中提供了四种不同的构造函数:
std::vector<T>::vector()
std::vector<T>::vector(size_t, T = T())
template <class InputIt> std::vector<T>::vector(InputIt, InputIt)
std::vector<T>::vector(const vector&)
请注意,它们实际上都将分配器作为附加的最后一个参数,但这不是我们关心的问题。
我们可以忘记std::vector<T>::vector()
,因为我们想用值填充向量,std::vector<T>::vector(size_t, T)
但也不适合,因为我们想要不同的值。剩下的是模板构造函数和复制构造函数。以下示例显示了如何使用模板化构造函数:
std::string const values[] = {"Taurus", "Ares", "Testos"};
template <class T, size_t N>
T* begin(T (&array)[N]){ // this is already in C++11, very helpful
return array;
}
template <class T, size_t N>
T* end(T (&array)[N]){
return array+N;
}
std::vector<std::string> Aries(begin(values), end(values));
请注意,begin
并且end
不是必需的 - 我们可以简单地使用Aries(values, values+3)
. 但是,事情往往会发生变化,您通常会添加一个值或删除一个值。如果您忘记更改偏移量3
,您将忘记输入或跨越values
.
然而,这个解决方案引入了一个新的全局变量,这不是很好。让我们退后一步。我们需要,values
因为我们想使用std::vector<T>::vector(InputIt, InputIt)
,它需要一个有效的范围。并且范围在我们使用构造函数的时候必须是已知的,所以它需要是全局的。诅咒!但是请注意:我们的工具箱仍然包含一个构造函数,即复制构造函数。为了使用它,我们创建了一个附加函数:
namespace {
std::vector<std::string> initializer(){
const std::string dummy_array[] = {"Taurus", "Ares", "Testos"};
return std::vector<std::string>(begin(dummy_array), end(dummy_array));
}
}
std::vector<std::string> Aries(initializer());
此示例同时使用复制构造函数和范围构造函数。您还可以创建一个临时向量并用于std::vector<T>::push_back
在函数中填充它。