正如标题所说,我的任务的一部分是实现一个数组类。教授为我们提供了标题样式,为我们创建了函数声明。使用前面的例子,我已经尽力定义这些函数,但是我在理解正在发生的事情时遇到了很多麻烦。发布整个头文件可能有点多,但我会尝试解释我遇到的问题。这是我的代码:
#ifndef ARRAY_H
#define ARRAY_H
#include <iostream>
#include <string>
using namespace std;
template <class T>
class Array {
private:
int size;
T * arr;
public:
int getSize();
Array();
Array(int size);
Array(Array & other);
Array(T[], int n);
~Array();
Array & operator=(Array & rhs);
Array & operator+(Array & rhs); // append
T & operator[](int i); //allow read and write
const T & operator[](int n) const; // readonly
void print(int n = 5);
void print(ostream & out, int n);
operator int *() { return arr; }
friend ostream & operator <<(ostream & out, Array <T>& rhs);
};
template <class T>
int Array<T>::getSize() {
return size;
}
template <class T>
Array<T>::Array() {
arr = new T[];
}
template <class T>
Array<T>::Array(int size) {
arr = new T[size];
}
template <class T>
Array<T>::Array(Array & other) {
size = other.getSize();
arr = new T[size];
copy(arr[0], arr[size + 1], other.arr[0]);
}
template <class T>
Array<T>::Array(T[], int n) {
size = n;
arr = new T[n];
}
template <class T>
Array<T>::~Array() {
if (arr) {
delete arr;
}
}
template <class T>
Array<T>& Array<T>::operator=(Array & rhs) {
if (this != &rhs) {
delete[] arr;
size = rhs.getSize();
arr = new T[size];
copy(arr[0], arr[size+1], rhs.arr[0]);
}
return *this;
}
template <class T>
Array<T>& Array<T>::operator+(Array & rhs) {
Array *tmp;
tmp = new Array(size + rhs.getSize());
return *tmp;
}
template <class T>
T& Array<T>::operator[](int i) {
assert(0 <= i && i < size);
return arr[i];
}
template <class T>
const T& Array<T>::operator[] (int n) const {
assert(0 <= i && i < size);
return arr[i];
}
template <class T>
void Array<T>::print(ostream &out, int n) {
for (size_t i = 0; i < n; i++) {
out << arr[i] << " ";
}
}
template <class T>
void Array<T>::print(int n = 5) {
print(cout, n);
}
template <class T>
ostream & operator << (ostream & out, Array<T> & rhs) {
out << "( " << rhs.getSize() << ")";
return out;
}
#endif
我会感谢任何和所有的提示,只是为了帮助我弄清楚这堂课里发生了什么。如果这最终要求很多,我很抱歉。
编辑:再次感谢大家的帮助!链接器错误是固定的。我应该指明印刷品是班级的成员,而不仅仅是自由。
答案 0 :(得分:2)
- 在第46行尝试为
醇>Array(Array & other);
执行复制构造时,我收到错误error C2664: 'char *strcpy(char *,const char *)' : cannot convert argument 1 from 'int *' to 'char *'
它一直指向strcpy
函数,但我不确定是什么它要我改变。我在同一行中遇到两个错误,第二个错误表示cannot convert argument 1 from 'std::string *' to 'char *'
这里的问题是strcpy
意味着在两个内存位置之间复制char
类型。但是,您的模板参数T
可以是任何类型,因此,如果您需要通用性,那么在此使用strcpy
是不合适的。复制构造函数的直接(但不是非常有效)实现类似于:
template <class T>
Array<T>::Array(const Array &other) : size(other.size), arr(new T[size])
{
for (int i = 0; i < size; ++i)
arr[i] = other.arr[i];
}
2)在编写
strcpy
overloader时,我在第71行尝试operator=
函数时遇到另一个错误。它告诉我cannot convert argument 1 from 'std::string *' to 'char *'
同样,它与一个问题相同:较旧的C风格str*
函数使用原始char *
指针指向包含字符的一些内存块。因此,这些函数组不能直接使用标准c ++库中的std::string
,而无需进行一些调整。大多数情况下,您不想这样做,因为这些函数可以在不保留其内部不变量的情况下变异std::string
。
对于赋值运算符,您只需执行复制和交换:
template <class T>
Array<T>& Array<T>::operator = (Array rhs)
{
std::swap(size, rhs.size);
std::swap(arr, rhs.arr);
return *this;
}
3)对于第85行的
T & operator[](int i); //allow read and write
,我想知道我是否应该创建一个包含i
个广告位的新数组。教授留下的允许,阅读和写评论使我感到困惑。另外,对于以下函数,Array<T>::T & operator[] (int n) const;
注释只读,所以我假设我应该用n
项返回数组。
operator []
用于提供语法糖,以便在给定某个索引Array<T>
时访问i
中的特定项目。如果没有它,以下将无法运作:
Array<int> arr(42);
std::cout << arr[0];
因此,您不必在此运算符内分配任何内容。您可以以相同的方式实现const和非const版本。唯一不同的是,最后会有一个const
限定符,因此这也适用于const Array<T>
:
template <class T>
T& Array<T>::operator[] (int i)
{
assert(0 <= i && i < size);
return arr[i];
}
template <class T>
const T& Array<T>::operator[] (int i) const
{
assert(0 <= i && i < size);
return arr[i];
}
4)我留下了对
void print(int n = 5);
函数的评论。但总而言之,我希望每行能够在数组中打印出一定数量的项目,但是没有多维数组。我尝试了两个for
循环,但它只是卡在同一个数组项上。5)我不确定为什么需要
void print(ostream & out, int n);
。它应该覆盖上面的print语句吗?
您正在寻找的正确术语是&#34;重载&#34;。 &#34;覆盖&#34;在C ++命名法中有一个非常具体的含义,在这种情况下并不适用。
从声明来看,似乎第二个print
签名的意图是支持不同类型的输出流(其中cout
是一种类型的btw)。您要做的是在第二个版本中实现print
的第一个版本。事实上,他们根本不需要成为模板功能:
void print(ostream &out, int n)
{
for (size_t i = 0; i < n; ++i)
out << pets[i] << " ";
}
void print(int n)
{
print(cout, n);
}
注意,应该修改print
以使数组打印出来而不是在这里引用一个(全局?)特定实例。
修改:修改print
以使阵列打印时,当然必须是模板。一个可能的签名:
template <typename T>
void print(const Array<T> &arr, int n)
{
print(arr, n, cout);
}