C++ 大数运算(整型加法乘法),类+运算符重载实现

提示:文章写完后,目录可以自动生成,如何生成可参考右边的帮助文档


前言

在蓝桥杯备赛中遇到大数的乘法,兴致一来,构建一个大数类练练手
在学习加法器和乘法器之后,利用相似的原理,利用数组构建了无符号大数类,支持加法和乘法的基本操作。
主要用到运算符重载、输入输出重载的知识。

一、类的头文件Numorous.h

//Numorous.h
#pragma once
#include <iostream>
#define int_dec_length 200
//在这里定义十进制数最大长度
using namespace std;

class Int
{
public:
	//各种构造函数
	Int();
	Int(int arr[],int length);
	Int(long long num);
	Int(int num);
	~Int();
	
	//打印输出大数,统计长度
	void show()const;
	
	//单目移位
	void operator<<=(int num);
	void operator>>=(int num);

	//双目移位
	Int operator>>(int num);
	Int operator<<(int num);
	
	//输入输出重载
	friend ostream& operator<< (ostream& out, Int A);
	friend istream& operator>> (istream& in, Int& A);

	//单目加法
	void operator+=(long long num);
	void operator+=(int  num);
	void operator+=(Int B);

	//双目加法
	Int operator+(long long num);
	Int operator+(int num);
	Int operator+(Int B);

	//单目乘法
	void operator*= (long long num);
	void operator*=(int num);
	void operator*=(Int B);
	
	//双目乘法
	Int operator*(long long num);
	Int operator*(int num);
	Int operator*(Int B);

	static Int factor(int num);	//静态函数,可以算num的阶乘
private:
	int len;					//长度
	int A[int_dec_length];		//记录数据的数组
};

二、类的实现文件Numorous.cpp

#include "Numorous.h"

Int::Int(){
	len = 0;
	for (int i = 0; i < int_dec_length; ++i) A[i] = 0;
}
Int::Int(int arr[],int length){
	if (length > 0) {
		for (int i = 0; i < length; i++) A[length - 1 - i] = arr[i];
		len = length;
	}
	if (len < 0) {
		for (int i = 0; i < -length; i++)A[i] = arr[i];
		len = -length;
	}
	for (int i = len; i < int_dec_length; ++i)A[i] = 0;
}
Int::Int(long long num){
	int i = 0;
	while (num) {
		A[i++] = num % 10;
		num /= 10;
	}
	len = i;
	for (int i = len; i < int_dec_length; ++i)A[i] = 0;
	
}
Int::Int(int num){
	int i = 0;
	while (num) {
		A[i++] = num % 10;
		num /= 10;
	}
	len = i;
	for (int i = len; i < int_dec_length; ++i)A[i] = 0;
}
Int::~Int(){
}

void Int::show()const{
	if (len == 0) { cout << "NULL" << endl; return; }
	for (int i = len-1; i >= 0; --i) {
		cout << A[i];
	}
	cout << "  "<<"len: " << len << endl;
}

void Int::operator<<=(int num) {
	for (int i = int_dec_length - 1; i >= num; --i) {
		A[i] = A[i - num];
	}
	for (int i = 0; i < num; ++i) {
		A[i] = 0;
	}
	len += num;
}
void Int::operator>>=(int num) {
	for (int i = 0; i <= int_dec_length - num - 1; ++i) {
		A[i] = A[i + num];
	}
	len -= num;
}

Int Int::operator>>(int num){
	Int B = *this;
	B >>= num;
	return B;
}
Int Int::operator<<(int num){
	Int B = *this;
	B <<= num;
	return B;
}

ostream& operator<< (ostream& out, Int A) {
	A.show();
	return out;
}
istream& operator>> (istream& in, Int& A) {
	long long tmp = 0;
	in >> tmp;
	A = tmp;
	return in;
}

void Int::operator+=(long long num){
	long long s = 0, c = num;
	for (int i = 0; i < int_dec_length; ++i) {
		s = A[i] + c;
		A[i] = s % 10;
		c = s / 10;
	}
	for (int i = 0; i < int_dec_length; ++i) {
		if (A[i] != 0)len = i + 1;
	}
}
void Int::operator+=(int num){
	int s = 0, c = num;

	for (int i = 0; i < int_dec_length; ++i) {
		s = A[i] + c;
		A[i] = s % 10;
		c = s / 10;
	}

	for (int i = 0; i < int_dec_length; ++i) {
		if (A[i] != 0)len = i + 1;
	}
}
void Int::operator+=(Int B){
	int s = 0, c = 0;
	for (int i = 0; i < int_dec_length; ++i) {
		s = A[i] + B.A[i] + c;
		A[i] = s % 10;
		c = s / 10;
	}
	for (int i = 0; i < int_dec_length; ++i) {
		if (A[i] != 0)len = i + 1;
	}
}

Int Int::operator+(long long num){
	Int B = Int(A, -len);
	B += num;
	return B;
}
Int Int::operator+(int num){
	Int B = Int(A, -len);
	B += num;
	return B;
}
Int Int::operator+(Int B){
	Int C = B;
	C += *this;
	return C;
}

void Int::operator*=(long long num){
	long long s = 0, c = 0;
	for (int i = 0; i < int_dec_length; ++i) {
		s = A[i] * num + c;
		A[i] = s % 10;
		c = s / 10;
	}
	for (int i = 0; i < int_dec_length; ++i) {
		if (A[i] != 0)len = i + 1;
	}
}
void Int::operator*=(int num) {
	long long s = 0, c = 0;
	for (int i = 0; i < int_dec_length; ++i) {
		s = A[i] * num + c;
		A[i] = s % 10;
		c = s / 10;
	}
	for (int i = 0; i < int_dec_length; ++i) {
		if (A[i] != 0)len = i + 1;
	}
}
void Int::operator*=(Int B) {
	Int C = *this;
	*this = 0;
	for (int i = B.len - 1; i >= 0; --i) {
		this->operator+=(C * B.A[i]);
		this->operator<<=(1);
	}
	this->operator>>=(1);
}

Int Int::operator*(long long num) {
	Int C = *this;
	C *= num;
	return C;
}
Int Int::operator*(int num) {
	Int C = *this;
	C *= num;
	return C;
}
Int Int::operator*(Int B) {
	Int C = B;
	C *= *this;
	return C;
}

Int Int::factor(int num){
	Int A = 1;
	if (num <= 0) {
		cout << "Error!" << endl;
		return A;
	}
	for (int i = 1; i <= num; ++i) {
		A *= num;
	}
	return A;
}

源文件main.cpp内的调用示例

1、整数初始化,乘法,阶乘

Int a = 54321;
Int b = 10000100001;
Int c = a * b;
a.show();	//54321
cout << c;	//5432154321
cout << Int::factor(22);	//很长的一个30位数字
//341427877364219557396646723584 len:16

2、数组初始化,加法,移位

int arr[16] = { 1,2,3,4,5,6,7,6,5,4,3,2,1,1,1,1 };
Int a(arr, 16);		//1234567654321111 len:16
Int b;
cin >> b;			//999999	len:6
cout << a << b;
Int c = a + b;
cout << c;			//1234567655321110	len:16
c >>= 3;
c.show();			//1234567655321  len: 13

总结

整体逻辑不是很复杂,只要明确A[i]各个位之间的进位关系无脑for循环,个人感觉某些循环设计太冗余,但也想不到更好的方法去解决。
入门小白第一次尝试写博客,如有不足,还请批评指正。

  • 16
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 1
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值