|
楼主 |
发表于 2019-12-25 15:54:11
|
显示全部楼层
本帖最后由 bin554385863 于 2019-12-25 17:48 编辑
lnum.h
2019年12月25日15:51:11#ifndef LNUM_H
#define LNUM_H
#include <iostream>
#include <string>
#include <vector>
using std::istream;
using std::ostream;
using std::string;
using std::vector;
class lnum
{
typedef vector<int> vecint;
struct Num
{
int sign;
vecint vec;
size_t nlen;
size_t dplen;
string str;
};
struct align
{
vecint shrter;
vecint longer;
};
private:
Num num;
//0:STR to lnum
const Num STRtoNUM(const string &s) const;
//1:vec to str
const string VECtoSTR(const vecint &v, const int sign, const size_t dplen) const;
//2:clear zero
void ClearZero(vecint &v) const;
//3:满十进1
void Carry(vecint &v) const;
//4:借1退10
const vecint Borrow(const vecint &v) const;
//5:vec小数位对齐
const vecint vecAlign(const vecint &m, const size_t mdpl, const vecint &n, size_t ndpl) const;
//6:小数对齐
const align Align(const vecint &m, const size_t mdpl, const vecint &n, size_t ndpl) const;
//7:大于比较
const bool GreaterThan(const vecint &m, const size_t mdpl, int msign, const vecint &n, size_t ndpl, int nsign) const;
//8:小于比较
const bool LessThan(const vecint &m, const size_t mdpl, int msign, const vecint &n, size_t ndpl, int nsign) const;
//9:相等比较
const bool Equal(const vecint &m, const size_t mdpl, int msign, const vecint &n, size_t ndpl, int nsign) const;
public:
lnum(const string &s):num(STRtoNUM(s)){}
lnum(const char *cstr = "0"):num(STRtoNUM(cstr)){}
lnum(const lnum &l) : num(l.num) {}
//?
void showinfo() const;
//?:overload >
const bool operator>(lnum &l) const;
//?:overload <
const bool operator<(lnum &l) const;
//?:overload ==
const bool operator==(lnum &l) const;
//over load >>
friend istream &operator>>(istream &is, lnum &n);
//overload <<
friend ostream &operator<<(ostream &os, const lnum &l);
~lnum() {}
};
#endif
lnum.cpp#include "E:\Users\admin\Documents\VScode\Code\My Class\shape.cpp\lnum\lnum.h"
//0:STR to lnum
const lnum::Num lnum::STRtoNUM(const string &s) const
{
Num n = {1, {0}, 1, 0, s};
string t = s;
if (t[0] == '-')
{
n.sign = -1;
t.erase(0, 1);
}
if (int(t.find('.')) != -1)
{
n.dplen = t.size() - t.find('.') - 1;
t.erase(t.find('.'), 1);
}
n.vec.clear();
for (char c : t)
{
n.vec.push_back(c - 48);
}
n.nlen = n.vec.size();
return n;
}
//1:vec to str
const string lnum::VECtoSTR(const vecint &v, const int sign, const size_t dplen) const
{
string s;
for(int i: v)
{
s.push_back(48 + i);
}
if (dplen != 0)
{
s.insert(s.size() - dplen, 1, '.');
}
if (sign == -1)
{
s.insert(0, 1, '-');
}
return s;
}
//2:clear zero
void lnum::ClearZero(vecint &v) const
{
size_t i = 0, s = v.size();
if (v[0] == 0)
{
for (; i < s; i++)
{
if (v[i] != 0)
{
break;
}
}
v.erase(v.begin(), v.begin() + i);
}
}
//3:满十进1
void lnum::Carry(vecint &v) const
{
v.insert(v.begin(), 1, 0);
size_t s = v.size();
for (size_t i = s-1; i > 0; i--)
{
int n = v[i];
v[i] = n % 10;
v[i - 1] += n / 10;
}
ClearZero(v);
}
//4:借1退10
const lnum::vecint lnum::Borrow(const vecint &v) const
{
size_t s = v.size();
vecint r = v;
for (size_t i = 1; i < s; i++)
{
r[i - 1] -= 1;
r[i] += 10;
}
return r;
}
//5vec对齐
const lnum::vecint lnum::vecAlign(const vecint &m, const size_t mdpl, const vecint &n, size_t ndpl) const
{
vecint r;
if (mdpl != ndpl)
{
r = mdpl < ndpl ? m : n;
size_t s = (mdpl > ndpl ? mdpl : ndpl) - (mdpl < ndpl ? mdpl : ndpl);
r.insert(r.end(), s, 0);
}
return r;
}
//6:小数对齐
const lnum::align lnum::Align(const vecint &m, const size_t mdpl, const vecint &n, size_t ndpl) const
{
align agn;
if (mdpl == ndpl)
{
agn.shrter = m.size() <= n.size() ? m : n;
agn.longer = n.size() >= m.size() ? n : m;
}
else
{
const vecint &sdpl = vecAlign(m, mdpl, n, ndpl);
const vecint &ldpl = mdpl > ndpl ? m : n;
agn.shrter = sdpl.size() <= ldpl.size() ? sdpl : ldpl;
agn.longer = ldpl.size() >= sdpl.size() ? ldpl : sdpl;
}
return agn;
}
//7:大于比较
const bool lnum::GreaterThan(const vecint &m, const size_t mdpl, int msign, const vecint &n, size_t ndpl, int nsign) const
{
bool f = true;
if (msign < nsign)
{
f = false;
}
else if (msign == nsign)
{
if (mdpl == ndpl)
{
if (m.size() != n.size())
{
f = m.size() > n.size();
if (msign = -1)
{
f = m.size() < n.size();
}
}
else
{
f = m > n;
if (msign == -1)
{
f = m < n;
}
}
}
else
{
if (mdpl < ndpl)
{
const vecint &tm = vecAlign(m, mdpl, n, ndpl);
if (tm.size() != n.size())
{
f = tm.size() > n.size();
if (msign = -1)
{
f = tm.size() < n.size();
}
}
else
{
f = tm > n;
if (msign == -1)
{
f = tm < n;
}
}
}
else if (ndpl < mdpl)
{
const vecint &tn = vecAlign(m, mdpl, n, ndpl);
if (m.size() != tn.size())
{
f = m.size() > tn.size();
if (msign == -1)
{
f = m.size() < tn.size();
}
}
else
{
f = m > tn;
if (msign == -1)
{
f = m < tn;
}
}
}
}
}
return f;
}
//8:小于比较
const bool lnum::LessThan(const vecint &m, const size_t mdpl, int msign, const vecint &n, size_t ndpl, int nsign) const
{
bool f = true;
if (GreaterThan(m, mdpl, msign, n, ndpl, nsign) || Equal(m, mdpl, msign, n, ndpl, nsign))
{
f = false;
}
return f;
}
//9:相等比较
const bool lnum::Equal(const vecint &m, const size_t mdpl, int msign, const vecint &n, size_t ndpl, int nsign) const
{
bool f = true;
if ((msign != nsign) || (mdpl != ndpl) || m.size() != n.size() || m != n)
{
f = false;
}
return f;
}
//?
void lnum::showinfo() const
{
std::cout << "正/负: " << num.sign << "\n"
<< "原数字: " << num.str << "\n"
<< "数字组成: ";
for (int i : num.vec)
{
std::cout << i << " ";
}
std::cout << "\n有效位数: " << num.nlen << "\n"
<< "小数位数: " << num.dplen;
}
//?:overload >
const bool lnum::operator>(lnum &l) const
{
return GreaterThan(num.vec, num.dplen, num.sign, l.num.vec, l.num.dplen, l.num.sign);
}
//?:overload <
const bool lnum::operator<(lnum &l) const
{
return LessThan(num.vec, num.dplen, num.sign, l.num.vec, l.num.dplen, l.num.sign);
}
//?:overload ==
const bool lnum::operator==(lnum &l) const
{
return Equal(num.vec, num.dplen, num.sign, l.num.vec, l.num.dplen, l.num.sign);
}
//over load >>
istream &operator>>(istream &is, lnum &n)
{
string str;
is >> str;
n = str;
return is;
}
//overload <<
ostream &operator<<(ostream &os, const lnum &l)
{
os << l.num.str;
return os;
}
int main(int argc, char const *argv[])
{
lnum a, b;
int i = 0;
while (i != 5)
{
std::cout << std::endl;
std::cout << "input data" << std::endl;
std::cin >> a >> b;
std::cout << "a = " << a << "\n"
<< "b = " << b << "\n"
<< "a > b: " << (a > b) << "\n"
<< "a == b: " << (a == b) << "\n"
<< "a < b: " << (a < b) << std::endl;
i++;
};
return 0;
}
================================================================
Microsoft Windows [版本 10.0.18363.535]
(c) 2019 Microsoft Corporation。保留所有权利。
E:\Users\admin\Documents\VScode\Code>c:\Users\admin\.vscode\extensions\ms-vscode.cpptools-0.26.2\debugAdapters\bin\WindowsDebugLauncher.exe --stdin=Microsoft-MIEngine-In-ex4w2dlu.upv --stdout=Microsoft-MIEngine-Out-pyje5tvg.zas --stderr=Microsoft-MIEngine-Error-ot1h5uhy.d0z --pid=Microsoft-MIEngine-Pid-01azs4my.aje --dbgExe=D:\MinGW\bin\gdb.exe --interpreter=mi
input data
-13.12 -12
a = -13.12
b = -12
a > b: 0
a == b: 0
a < b: 1
input data
123 123
a = 123
b = 123
a > b: 0
a == b: 1
a < b: 0
input data
-987.256 -987.256
a = -987.256
b = -987.256
a > b: 0
a == b: 1
a < b: 0
input data
12345678999999 888888888888
a = 12345678999999
b = 888888888888
a > b: 1
a == b: 0
a < b: 0
input data
-123456789 -987654321
a = -123456789
b = -987654321
a > b: 1
a == b: 0
a < b: 0
input data
987654321 654321
a = 987654321
b = 654321
a > b: 1
a == b: 0
a < b: 0
input data
22222222222 9999999999
a = 22222222222
b = 9999999999
a > b: 1
a == b: 0
a < b: 0
input data
1.23456789 1.02345678
a = 1.23456789
b = 1.02345678
a > b: 1
a == b: 0
a < b: 0
input data
-1.123654 12
a = -1.123654
b = 12
a > b: 0
a == b: 0
a < b: 1
input data
-7 9
a = -7
b = 9
a > b: 0
a == b: 0
a < b: 1
E:\Users\admin\Documents\VScode\Code> |
|