You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

类中operator*运算符实现报错求助:float*x^int类型类乘法问题

usuario类operator*运算符实现导致程序崩溃

实现表示float*x^int类型的usuario类时,在实现operator*运算符后,执行两个类对象相乘、类对象与float类型相乘操作时程序终止报错。以下是完整代码:

主文件

#include <iostream>
#include "usuario.h"
usuario& operator*(usuario& u1,usuario& u2);
usuario& operator*(usuario& u1,float num);

int main()
{
    usuario u1;
    usuario u2;
    std::cout<<"Monomio 1:";
    std::cin>>u1;
    std::cout<<std::endl<<"Monomio 2:";
    std::cin>>u2;
    float alfa = 3.2;
    usuario u3 = u1*u2;
    usuario u4 = u1;
    std::cout<<u1<<"*"<<u2<<"="<<u3<<std::endl;
    std::cout<<u1<<"*"<<alfa<<"="<<u4;

    return 0;
}

usuario& operator*(usuario& u1,usuario u2)
{
    u1*=u2;
    return u1;

}
usuario& operator*(usuario& u1,float num)
{
    usuario u2(num,0);
    u1*=u2;
    return u1;
}

类头文件(usuario.h)

#ifndef USUARIO_H
#define USUARIO_H
#include <iostream>

class usuario
{
    public:
        usuario();
        usuario(float numero, int exponente);
        usuario(const usuario& u);
        usuario& operator=(const usuario& u);
        usuario& operator*=(const usuario& u);
        float num() const;
         int exp() const ;



    private:
        float numero;
         int exponente;

};
std::istream& operator>>(std::istream& in, usuario& u);
std::ostream& operator<<(std::ostream& out,const usuario& u);



#endif // USUARIO_H

实现文件

#include "usuario.h"

usuario::usuario():numero(1),exponente(1)
{

}
usuario::usuario(float numero, int exponente):numero(numero),exponente(exponente)
{

}
usuario::usuario(const usuario& u):numero(u.numero),exponente(u.exponente)
{

}
usuario& usuario::operator*=(const usuario& u)
{
    numero*=u.numero;
    exponente+=u.exponente;
    return *this;
}
std::istream& operator>>(std::istream& in ,usuario& u)
{
    char ch;
    float numero;
    int exponente;
    in>>numero;
    in>>ch;
    in>>ch;
    in>>exponente;
    u = usuario(numero,exponente);
    return in;

}
std::ostream& operator<<(std::ostream& out,const usuario& u)
{
    out<<u.num();
    out<<"x";
    out<<"^";
    out<<u.exp();
    return out;
}
float usuario::num()const
{
    return numero;
}
 int usuario::exp()const
{
    return exponente;
}

usuario& usuario::operator=(const usuario& u)
{
    numero = u.numero;
    exponente = u.exponente;
    return *this;
}

问题根源

  1. operator*设计错误:当前实现的operator*直接修改左操作数(u1)并返回其引用,违背乘法运算语义——乘法不应改变原操作数,而是生成新的结果对象。这种设计会导致原对象被意外修改,若操作数为临时对象还可能引发悬垂引用问题。
  2. 声明与定义不匹配:主文件中operator*(usuario& u1, usuario& u2)的声明与定义usuario& operator*(usuario& u1, usuario u2)的第二个参数类型不一致(声明为引用,定义为值传递),会引发编译或链接错误。
  3. 缺少const修饰:参数未使用const引用,既无法接受临时对象作为操作数,也无法保证原对象不被修改。
  4. 缺少反向重载:未实现float * usuario的重载,无法支持3.2 * u1这类右操作数为类对象的乘法。

修复方案

1. 修改operator*的实现,返回新对象而非引用

在usuario.h中补充正确的声明:

// 两个usuario对象相乘
usuario operator*(const usuario& u1, const usuario& u2);
// usuario与float相乘
usuario operator*(const usuario& u, float num);
// float与usuario相乘(反向重载)
usuario operator*(float num, const usuario& u);

在实现文件中添加这些重载的实现:

usuario operator*(const usuario& u1, const usuario& u2)
{
    usuario result = u1;
    result *= u2;
    return result;
}

usuario operator*(const usuario& u, float num)
{
    usuario result(u.num() * num, u.exp());
    return result;
}

usuario operator*(float num, const usuario& u)
{
    return u * num;
}

2. 移除主文件中原错误的operator*声明与定义

删除主文件中以下内容:

usuario& operator*(usuario& u1,usuario& u2);
usuario& operator*(usuario& u1,float num);

// 对应的错误实现
usuario& operator*(usuario& u1,usuario u2)
{
    u1*=u2;
    return u1;

}
usuario& operator*(usuario& u1,float num)
{
    usuario u2(num,0);
    u1*=u2;
    return u1;
}

3. 输入逻辑优化(可选)

若输入格式不符合系数x^指数,operator>>会读取失败导致对象状态异常,可添加校验:

std::istream& operator>>(std::istream& in ,usuario& u)
{
    char ch1, ch2;
    float numero;
    int exponente;
    if (!(in >> numero >> ch1 >> ch2 >> exponente) || ch1 != 'x' || ch2 != '^') {
        in.setstate(std::ios::failbit);
        return in;
    }
    u = usuario(numero, exponente);
    return in;
}

修复后效果

修改后,u1*u2会生成新的usuario对象赋值给u3,u1和u2的原值保持不变;u1*alfa也会生成新对象,不会修改u1,完全符合乘法运算的预期。

内容的提问来源于stack exchange,提问作者Alvaro Suarez Menendez

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.11 12:40:22