带有指针的运算符重载
Operator overloading with pointers
大家好,有c++程序员。我遇到了一个我不能理解的问题。出于可读性的原因,我删除了以下程序,并留下了我遇到的问题。我正在尝试重载一个+和=运算符,但要使用动态创建的数组。+和=运算符方法本身就产生了正确的结果。然而,当我试图将+运算符的结果分配给*poly3时,我从编译器中得到"*poly3需要初始化"。如果我真的初始化了它,就不会有任何东西被分配给它(我指的是+的结果)。我的问题是,做这件事的正确方法是什么。我需要结果poly3是动态数组或指针,这样我就可以在后面使用它。
非常感谢您提前提供的帮助。
class Polynomial
{
private:
int *poly;
int size;
public:
Polynomial();
Polynomial(int);
Polynomial(string,int);
~Polynomial();
void setPoly(string);
int *getPoly() const;
Polynomial operator+(Polynomial&);
void operator=(const Polynomial&);
};
Polynomial::Polynomial(string polyInput, int s)
{
size = s+1;
poly = new int[size];
//set all coef position to 0
for(int i = 0; i < size; i++){
*(poly + i) = 0;
}
setPoly(polyInput);
}
Polynomial Polynomial::operator+(Polynomial &polyRight)
{
Polynomial *result = new Polynomial(size);
for(int i = 0; i < size; i++)
result->poly[i] = poly[i] + polyRight.poly[i];
return *result;
}
void Polynomial::operator=(const Polynomial &polyRight)
{
size = polyRight.size;
for(int i = 0; i < size; i++){
*(poly + i) = polyRight.poly[i];
}
}
int main()
{
int highestExp = 4;
Polynomial *poly1;
Polynomial *poly2;
Polynomial *poly3;// = new Polynomial(highestExp); // for the result
string input1,input2;
ifstream inputFile("data.txt");
getline(inputFile, input1);
getline(inputFile, input2);
poly1 = new Polynomial(input1,highestExp);
poly2 = new Polynomial(input2,highestExp);
*poly3 = *poly1 + *poly2;
system("pause");
return 0;
}
赋值运算符必须返回对分配给的实例的引用
Polynomial& operator=(const Polynomial&);
在实现中,您应该return *this;
。您还必须确保实现对于不同大小的多项式的分配是稳健的。目前情况似乎并非如此。
然后,在main
中,poly3
未初始化。只需删除指针并将所有poly
实例化为自动存储,即main()
:中的本地变量
Polynomial poly1(input1,highestExp);
Polynomial poly2(input2,highestExp);
Polynimial poly3 = poly1 + poly2;
顺便说一句,您的operator+
内存泄漏。您不应该使用new
int it。创建一个本地Polynomial
并返回它。
此外,您没有负责释放资源的析构函数,因此Polynomial
的每个实例化都会导致内存泄漏。你的班级有太多的责任:管理资源和做多项式。您应该让另一个类负责内存管理。使用std::vector<int>
,或者,如果这是一个练习,编写自己的类似动态数组的类,并在Polynomial
中使用它。
指针指向明确分配给它的内存位置。
Ptr* pt = new Ptr();//pt points to a valid address in memory
Ptr* pt;//pt has not yet been initialized
即它没有指向任何有效地址。使用pt可能会导致意外行为。默认情况下,指针应该指向NULL,并且应该检查它们!NULL,然后使用。
在上述代码中多项式*poly3;没有指向任何位置,当我们指向时*pol3我们实际上是在取消引用一个从未创建过的位置。
当您执行多项式*poly3=新多项式(highestExp);时;,您将poly3指向某个有效位置,因此*pol3=*poly1+*pol2是有意义的。但是要注意,当您为poly3做一个新的操作时,您正在创建一个又一个堆存储,所以您必须确保释放堆上分配的所有内存。
一个更好的解决方案是让您的oper+返回一个有效的指针,并将其映射到poly3,如下所示:
Polynomial* Polynomial::operator+(Polynomial &polyRight)
{
Polynomial *result = new Polynomial(size);
for(int i = 0; i < size; i++)
result->poly[i] = poly[i] + polyRight.poly[i];
return result;
}
//并且在主中
poly3 = (*poly1 + *poly2);
开始于:
// allow adding const
const Polynomial Polynomial::operator+(const Polynomial &polyRight) const
{
Polynomial result(size); // don't use a pointer
for(int i = 0; i < size; i++)
result.poly[i] = poly[i] + polyRight.poly[i];
return result;
}
使返回常量避免(A+B)=C;
的愚蠢
Polynomial& Polynomial::operator=(const Polynomial &polyRight) // return a reference
{
size = polyRight.size;
for(int i = 0; i < size; i++){
*(poly + i) = polyRight.poly[i];
}
return *this; // allow chaining
}
请注意,一旦您对此进行了修补,就需要防止operator =()
:中的A=A
if (this == &rhs)
{
// do stuff
}
return *this;
这是一个相当大的清理,有一些稍微不同的功能和更好的内存管理。由于我不知道你输入文件的格式,我跳过了从文件中读取的部分,只使用了Polynomial(countOfExponents, x0, x1, x2, x3, ... , xn)
形式的新构造函数
#include <cstdio>
#include <cstdlib>
#include <cstring>
#include <string>
#include <fstream>
#include <iostream>
#include <sstream>
#include <cstdarg>
using namespace std;
class Polynomial
{
private:
int *poly;
int size;
public:
Polynomial() : size(0), poly(NULL) {}
Polynomial(int size, ... );
~Polynomial() { delete[](poly); }
void allocate(int size) {
if (NULL!=poly) {
delete[](poly);
}
Polynomial::size = size;
poly=new int[size];
}
Polynomial operator+(const Polynomial&) const;
Polynomial &operator=(const Polynomial&);
int exponent(int p) const {
return (p<size) ? poly[p] : 0;
}
string str() const;
};
Polynomial::Polynomial(int size, ...) : size(size) {
va_list varargs;
va_start(varargs, size);
poly = new int[size];
for (int i=0; i<size; i++) {
poly[i] = va_arg(varargs, int);
}
va_end(varargs);
}
Polynomial Polynomial::operator+(const Polynomial &polyRight) const
{
int newSize = max(size, polyRight.size);
Polynomial result;
result.allocate(newSize);
for(int i = 0; i < newSize; i++)
result.poly[i] = exponent(i) + polyRight.exponent(i);
return result;
}
Polynomial &Polynomial::operator=(const Polynomial &polyRight)
{
allocate(polyRight.size);
memcpy(poly, polyRight.poly, sizeof(int) * size);
return *this;
}
string Polynomial::str() const {
stringstream out;
for (int i=size-1; i>=0; i--) {
out << poly[i];
if (0<i) {
out << " ";
}
}
return out.str();
}
int main()
{
Polynomial one(3, 1, 2, 3);
Polynomial two(3, 2, 3, 4);
cout << one.str() << endl;
cout << two.str() << endl;
Polynomial three = one + two;
cout << three.str() << endl;
return 0;
}
注意,在处理不同大小的多项式时,我也要小心不要处理可能不存在的内存。访问指数小于n的多项式上的poly[n]会引起麻烦。相反,使用指数(n)函数,它将为所有高于多项式内指数的指数返回0。
- 使用C++中的模板和运算符重载执行矩阵运算
- 为什么这个运算符<重载函数对 STL 算法不可见?
- <T> 通过模板化运算符重载将 std::complex 乘以双倍
- C++20概念:需要运算符重载
- 使用赋值运算符重载从类中返回jobject
- 在运算符重载定义中使用成员函数(const错误)
- 字节到位运算符重载C++
- 为什么在运算符重载时需要参考?
- 类中 c++ 的运算符 + 重载
- 算术复合运算符重载为非成员
- 运算符重载 (+),用于添加两个具有 C++ 的数组
- 交换运算符 + 重载会导致无限递归
- 如何理解新的运算符重载?
- 向量保持复数的运算符重载
- 如何创建运算符重载?
- 链接列表运算符重载没有打印出我想要的内容
- C++:需要帮助了解运算符重载错误
- 使用模板化运算符重载 XOR 运算符失败
- 如何确保接受的C++模板类型使运算符重载?
- 运算符重载使用运算符+添加类模板