10_21
大数加减:
bignum.h
#pragma once
#ifndef BIG_NUM_H
#define BIG_NUM_H
#include<iostream>
#include<string>
using namespace std;
class BigNum
{
public:
BigNum(int num = 0);//空的构造函数
BigNum(const string& str);//string构造
BigNum(const BigNum& src);//拷贝构造
BigNum& operator=(const BigNum& src);//等号运算符重载,不用析构,系统会自动调用析构函数
BigNum operator+(const BigNum& src);//加法运算符重载
BigNum operator-(const BigNum& src);//减法运算符重载
BigNum& operator++();//前置++
BigNum operator++(int);//后置++
bool operator&&(const BigNum& bignum);
friend ostream& operator<<(ostream& out, const BigNum& src);
private:
char int_to_char(int num)
{
char err[] = {
'0','1','2','3','4','5','6','7','8','9' };
return err[num];
}
int char_to_int(char c)
{
char err[] = {
'0','1','2','3','4','5','6','7','8','9' };
for (int i = 0; i < sizeof(err) / sizeof(err[0]); i++)
{
if (err[i] == c)
{
return i;
}
}
return -1;
}
string _num;
};
#endif
bignum.cpp
#include"bignum.h"
BigNum::BigNum(int num)
{
char c;
int val;
while (num != 0)
{
val = num % 10;//最低位
c = int_to_char(val);
_num.push_back(c);//尾插法插入
num /= 10;//最高位
}
}
BigNum::BigNum(const string& str)
{
for (int i = str.size() - 1; i >= 0; i--)
{
_num.push_back(str[i]);
}
}
BigNum::BigNum(const BigNum& src)//string的底层是一个字符串,所以不用clear
{
_num = src._num;
}
BigNum& BigNum::operator=(const BigNum& src)
{
_num = src._num;
return *this;
}
BigNum BigNum::operator+(const BigNum& src)
{
int sum = 0;
int val = 0;
int flag = 0;
BigNum tmp;
int i = 0;
//将长度相同的部分先加起来
for (; i < _num.size() && i < src._num.size(); i++)
{
sum = char_to_int(_num[i]) + char_to_int(src._num[i]) + flag;
val = sum % 10;
flag = sum / 10;
tmp._num.push_back(int_to_char(val));
}
//找出当前还没有计算完的是哪个大数
const string* p = NULL;
if (i < _num.size())
{
p = &_num;
}
else if (i < src._num.size())
{
p = &src._num;
}
else
{
//如果都走完了,看一下是否还有进位没有放进去
if (flag != 0)
{
tmp._num.push_back(int_to_char(flag));
}
}
//将没有走完的大数继续进行运算
for (; NULL != p && i < p->size(); i++)
{
sum = char_to_int((*p)[i]) + flag;
val = sum % 10;
flag = sum / 10;
tmp._num.push_back(int_to_char(val));
}
//走完了之后,看一下是否还有进位没有放进去
if (flag != 0)
{
tmp._num.push_back(int_to_char(flag));
}
return tmp;
}
BigNum BigNum::operator-(const BigNum& src)
{
return *this;
}
BigNum& BigNum::operator++()//前置++
{
int sum = 0;
int flag = 0;
int val = 0;
if (_num.empty())
{
_num.push_back('0');
}
//将个位的数字+1
sum = char_to_int(_num[0]) + 1;
val = sum % 10;
flag = sum / 10;
_num[0] = int_to_char(val);
//如果存在进位的情况
int i = 1;
while (flag != 0 && i < _num.size())
{
sum = char_to_int(_num[i]) + flag;
val = sum % 10;
flag = sum / 10;
_num[i] = int_to_char(val);
i++;
}
//如果到最后依然存在进位
if (flag != 0)
{
_num.push_back(int_to_char(flag));
}
return *this;
}
BigNum BigNum::operator++(int)//后置++
{
BigNum tmp = *this;
int sum = 0;
int flag = 0;
int val = 0;
if (_num.empty())
{
_num.push_back('0');
}
//将个位的数字+1
sum = char_to_int(_num[0]) + 1;
val = sum % 10;
flag = sum / 10;
_num[0] = int_to_char(val);
//如果存在进位的情况
int i = 1;
while (flag != 0 && i < _num.size())
{
sum = char_to_int(_num[i]) + flag;
val = sum % 10;
flag = sum / 10;
_num[i] = int_to_char(val);
i++;
}
//如果到最后依然存在进位
if (flag != 0)
{
_num.push_back(int_to_char(flag));
}
return tmp;
}
// 0 && 0 1&&0 1 && 1
bool BigNum::operator&&(const BigNum& bignum)
{
//两个中有一个空的或者全为空
if (_num.empty() || bignum._num.empty())
{
return false;
}
//"0" 有一个数字不为空,但是只有一个0在里面
if (_num.size() == 1 && _num[0] == '0')
{
return false;
}
//有一个不为空,但是只有一个0在里面
if (bignum._num.size() == 1 && bignum._num[0] == '0')
{
return false;
}
return true;
}
ostream& operator<<(ostream& out, const BigNum& src)
{
for (int i = src._num.size() - 1; i >= 0; i--)
{
cout << src._num[i];
}
cout << endl;
return out;
}
main(bignum):测试用例
#include<iostream>
#include"bignum.h"
using namespace std;
/*
* 刷题
* 要求每周两道 ---- 发到邮箱 --- word ----- 每周周一交
*
*
* 1.BigNum 代码实现
* 2.Mstring 仿写string
*/
int main()
{
BigNum b1(8789);
BigNum b2("95779");
BigNum b3 = b1 + b2;
cout << b3 << endl;
return 0;
}
仿写库中的Mstring类
mstring.h
#ifndef MSTRING_H
#define MSTRING_H
#include<iostream>
using namespace std;
#define DEFEALT_LEN 10
class Mstring
{
public:
Mstring(const char* str = NULL);
Mstring(const Mstring& src);
Mstring& operator=(const Mstring& src);
~Mstring();
void push_back(char c);
void pop_back();
char back()const;//获取最后一个元素
char front()const;//获取第一个元素
bool empty()const;//是否为空
int size()const;//计算长度
Mstring operator+(const Mstring& str)const;
char& operator[](int pos);//中括号运算符重载
char operator[](int pos)const;
friend ostream& operator<<(ostream& out, const Mstring& src);
friend istream& operator>>(istream& in, Mstring& src);
private:
bool full()const;
void revert();
char* _str;
int _len;//当前空间总长度
int _val_len;//已经占用的长度,试即数据数量
};
#endif#pragma once
mstring.cpp
#include"mstring.h"
Mstring::Mstring(const char* str)
{
//当为空的时候,置为0
if (NULL == str)
{
_len = DEFEALT_LEN;
_val_len = 0;
_str = new char[_len];
memset(_str, 0, _len);
return;
}
//当不为空的时候,
_val_len = strlen(str);
_len = _val_len + 1;//有\0,所以长度+1
_str = new char[_len];//申请空间
memset(_str, 0, _len);//全部设置为0
//数据依次拷贝进去
for (int i = 0; i < _val_len; i++)
{
_str[i] = str[i];
}
}
//拷贝构造
Mstring::Mstring(const Mstring& src)
{
_val_len = strlen(src._str);
_len = _val_len + 1;
_str = new char[_len];
memset(_str, 0, _len);
for (int i = 0; i < _val_len; i++)
{
_str[i] = src._str[i];
}
}
Mstring& Mstring::operator=(const Mstring& src)
{
//防止自赋值
if (&src == this)
{
return *this;
}
delete[]_str;//删除原来的值,防止内存泄漏
//防止浅拷贝
_val_len = strlen(src._str);
_len = _val_len + 1;
_str = new char[_len];
memset(_str, 0, _len);
for (int i = 0; i < _val_len; i++)
{
_str[i] = src._str[i];
}
return *this;
}
Mstring::~Mstring()
{
delete[]_str;
}
void Mstring::push_back(char c)
{
//判断当前空间是否占满
if (full())
{
revert();//扩容
}
_str[_val_len] = c;
_val_len++;
}
void Mstring::pop_back()
{
if (empty())
{
return;
}
_val_len--;
}
char Mstring::back()const
{
if (empty())
{
return 0;
}
return _str[_val_len - 1];
}
char Mstring::front()const
{
if (empty())
{
return 0;
}
return _str[0];
}
bool Mstring::empty()const//判空
{
return _val_len == 0;
}
Mstring Mstring::operator+(const Mstring& str)const
{
char* p;
int len = _val_len + str._val_len + 1;
p = new char[len];
memset(p, 0, len);
//进行数据拷贝-----将两个字符串的数据拼接起来
int i = 0;
for (; i < _val_len; i++)
{
p[i] = _str[i];
}
for (int j = 0; j < str._val_len; j++, i++)
{
p[i] = str._str[j];
}
return p;
}
char& Mstring::operator[](int pos)
{
return _str[pos];
}
char Mstring::operator[](int pos)const
{
return _str[pos];
}
bool Mstring::full()const
{
return _val_len == _len - 1;
}
void Mstring::revert()
{
_len = _len << 1;
char* p = new char[_len];
memset(p, 0, _len);
for (int i = 0; i < _val_len; i++)
{
p[i] = _str[i];
}
delete[]_str;
_str = p;
}
int Mstring::size()const
{
return _val_len;
}
ostream& operator<<(ostream& out, const Mstring& src)//常对象只能调用常方法
{
for (int i = 0; i < src.size(); i++)
{
out << src[i];
}
out << endl;
return out;
}
istream& operator>>(istream& in, Mstring& src)
{
char tmp[1024];
in >> tmp;
src = tmp;
return in;
}
main(mstring).cpp
#include<iostream>
#include"bignum.h"
#include"mstring.h"
using namespace std;
/*
* 刷题
* 要求每周两道 ---- 发到邮箱 --- word ----- 每周周一交
*
* 1.BigNum 代码实现
* 2.Mstring 仿写string
*
*
*/
int main()
{
BigNum b1(8789);
BigNum b2("95779");
BigNum b3 = b1 + b2;
cout << b3 << endl;
string s = "qqqq";
string s1 = "eee";
string s3 = s1 + s;
s.push_back('o');
for (int i = 0; i < s.size(); i++)
{
cout << s[i] << " ";
//s[i] = 'y';
//cout << endl;
}
s.pop_back();
s.empty();
s.back();
s.front();
cout << endl;
cout << "================================" << endl;
Mstring str1;
cout << str1 << endl;
Mstring str2("1234567");
cout << str2 << endl;
str2.push_back('9');
cout << str2 << endl;
cin >> str1;
cout << str1 << endl;
return 0;
}