在main()中为通用模板类选择数据类型

Choosing the data type for a generalized template class in main()

本文关键字:选择 数据类型 main      更新时间:2023-10-16

所以我被要求编写一个简单的向量模板,我相信我已经正确地编写了这个类,看看我们教科书(Savitch)中的一些广义列表的例子。现在,我试图通过让用户选择数据类型来调用main()中的类。在声明标识符list1之后,我遇到了问题。在使用if语句切换数据类型之后,我希望能够使用相同的标识符。但是,我不认为if语句主体中的语法是正确的,因为list1已经声明了。在java中,我一直认为在类被声明后,你可以随时调用它的构造器,但我不知道如何在C++中做到这一点。

#include <iostream>
using namespace std;
template <class T>
class SimpleVector {
public:
SimpleVector();
SimpleVector(int);
SimpleVector(const SimpleVector & copy);
~SimpleVector();
int size();
T getElementAt(int n);
T & operator[](int index);
private:
T * item;
int length;
};

int main() {

int dType;
int dataSize;
cout << "What type of data do you want to enter?n(1 for integer, 2 for double and 3 for strings)" << endl;
cin >> dType;
cout << "How many data inputs? " << endl;
cin >> dataSize;
SimpleVector <int> list1; // if I dont declare then for loop doesn't recognize list as a declared variable.
if (dType == 0) {
SimpleVector <int> list1(dataSize);
}
else if (dType == 1) {
SimpleVector <double> list1(dataSize);
}
else {
SimpleVector <string> list1(dataSize);
}
cout << "Please enter the data:" << endl;
for (int i = 0; i < dataSize; i++) {
cin >> list1[i];
}

return 0;
}
template <class T> SimpleVector<T>::SimpleVector() {
item = NULL;
length = 0;
}
template <class T> SimpleVector<T>::SimpleVector(int s) {
length = s;
item = new T[length];
}
template <class T> SimpleVector<T>::SimpleVector(const SimpleVector & copy) {
int newSize = copy - > size();
item = new T[newSize];
for (int i = 0; i < newSize; i++)
item[i] = copy.item[i];
}
template <class T> SimpleVector<T>::~SimpleVector() {
delete[] item;
}
template <class T> int SimpleVector<T>::size() {
return length;
}
template <class T> T SimpleVector<T>::getElementAt(int n) {
return *(item + n);
}
template <class T> T & SimpleVector<T>::operator[](int index) {
return this->item[index];
}

您不能切换数据类型。变量一旦声明为特定类型,就不能更改为其他类型。

变量具有作用域。

{
int a;
.....stuff.....
}
// a cannot be accessed here.

CCD_ 4现在只能在打开的{和关闭的}之间使用。

{
int a; // First a
.....stuff..... // a refers to the first a here
{
int a;
.....stuff..... // a refers to the second a here
}
.....stuff..... // a refers to the first a here
}

第二个CCD_ 7是与第一个不同的变量。它只能在它的范围内访问,即在离它最近的开括号和闭括号之间

如果您确实想要动态类型,请尝试Boost.variantBoost.Any

C++与Java一样,是一种静态类型和静态作用域的语言。这意味着在编译时必须知道变量的类型和生存期。

在java中,我一直认为在声明一个类之后,你可以随时调用它的构造器,但我不知道如何在C++中做到这一点。

这与Java没有什么不同。在Java中,您正在尝试的操作相当于:

MyClass c;
if (cond) {
MyClass c = new MyClass(1);
} else  {
MyClass c = new MyClass(2);
}

这与调用构造函数无关。这与在嵌套作用域中声明新变量有关,并且它们完全独立于外部作用域中的同名变量。

如果您需要运行时多态性,那么(根据定义),您实际上需要使用多态性。也就是说,您需要创建一个具有虚拟函数的公共基类:

class SimpleVectorBase
{
public:
SimpleVectorBase() { }
virtual ~SimpleVectorBase() { }
virtual int size() const { return length; }
// ... etc. ...
private:
int length;
}
template <class T>
class SimpleVector : public SimpleVectorBase {
// ...
}
int main() {
// ...
SimpleVectorBase* list1;
if (dType == 0) {
list1 = new SimpleVector<int>(dataSize);
} else if (dType == 1) {
list1 = new SimpleVector<double>(dataSize);
} else {
list1 = new SimpleVector<string>(dataSize);
}
// ...
}

然而,这样做并不能真正帮助您完成for循环。在您的特定情况下,您可能最好将整个事情模板化:

template<typename T>
void doWork(int dataSize)
{
SimpleVector<T> list1(dataSize);
std::cout << "Please enter the data:" << std::endl;
for (int i = 0; i < dataSize; i++) {
std::cin >> list1[i];
}
// ... Do other stuff with list1 ...
}

然后你的main()函数会做:

if (dType == 0) {
doWork<int>(dataSize);
} else if (dType == 1) {
doWork<double>(dataSize);
} else {
doWork<string>(dataSize);
}