两个长数字串全乘双向链表实现
来源:互联网 发布:python hangman游戏 编辑:程序博客网 时间:2024/05/17 01:59
//两个长数字串全乘双向链表实现
#include <iostream>
#include <cmath>
#include <stdlib.h>
using namespace std;
class DblList;
class DblNode{//双向链表结点类定义;
friend class DblList;
private:
int data;
DblNode *lLink , *rLink ;
public:
DblNode(int value,DblNode* left,DblNode *right):data(value),lLink(left),rLink(right){}
DblNode(int value):data(value),lLink(NULL),rLink(NULL){}
};
//
class DblList{
public :
DblList (int unique_Val) ;
~DblList () ;
void input () ;//P 从键盘输入一串长整数构造双向循环链表
int Length ( ) const ;//P 求链表中有效结点个数 ,即链表长度
void Insertfront (const int & value) ;//P 将新元素插入到链表头
void Insertrear (const int &value) ;//P 将新元素插入到链表尾
void print () ;//P 打印输出链表表示的长整数
void convolution (DblList&la ,DblList &lb) ;//P 求两数卷积运算
void multiplication (DblList& ld) ;// P 卷积结果分离成商数;
private :
DblNode *first;
};
//
DblList::DblList(int unique_Val){
first = new DblNode (unique_Val) ;
first->rLink = first->lLink = first ;
}
DblList::~DblList{
DblNode * p , * q ;
p =first - > rLink ;
while (p ! =first) {
q = p ;p = p - > rLink ;
delete q ;
}
delete first ;
}
int DblLst ∷ Length () const{//P 求链表的长度(结点个数)
DblNode * p =first - > rLink ;
int count = 0 ;
while (p ! =first) {p = p - > rLink ;count + + ;}
return count ;
}
void DblList ∷Insertrear (const int & value)//插入元素到链表尾
{ DblNode * p ;
p = new DblNode (value) ;
p - > rLink =first ;
p - > lLink =first - > lLink ;
first - > lLink - > rLink = p ;
first - > lLink = p ;
}
void DblList ∷Insertfront (const int & value)// 插入元素到链表头
{
DblNode * p ;
p = new DblNode (value) ;
if (first - > rLink = =first
{ p - > rLink =first ;
p - > lLink =first ;
first - > lLink =first - > lLink = p ;
}
else
{
p - > lLink =first - > lLink ;
p - > rLink =first ;
first - > lLink - > rLink = p ;
first - > lLink = p ;
}
}
void DblList ∷ input () {//从键盘输入一串长数字串建立其对应的双向循环链表;
char ch ;
int chint ;
int i = 0 ,k = 0 ;
cout < <“请输入长数字串 ,按回车键或 Ctrl+ C结束:” ;
while ( ! cin. eof () )
{
ch = cin. get () ;//接收从键盘输入的长数字串中的一个字符;
if (ch = =‘P n’ ) break ;
if (ch = =‘- ’ ) first - > data = - 1 ;
else
if (ch > =‘0’ &&ch < =‘9’ )
{
chint = ch -‘0’ ;
Insertrear (chint) ;
k + + ;
}
else if (ch = =‘.’ ) i = k ;
else{
cerr < <“输入错误 !”< < endl ;
exit (1) ;
}
}
if (i = = 0) i = k ;
first - > data = (first - > data) * i ;
}
void DblList ∷ print () {//打印输出链表所对应的长整数
DblNode * p ;
int ij ,k ;
p =first ;
i = abs (first -> data) ;
k =Length () ;
cout < <“\ n长整数为:” ;
if (p - > data < 0)
cout<<‘- ’ ;
j = 0 ;
while (p - > rLink ! =first) {
p = p - > rLink ;
cout < < p - > data ;
j + + ;
if (j = = i&& i ! = k) cout < <‘.’ ;
}
cout < <‘\ n’ ;
}
void DblList ∷conv olution (DblList& la , DblList &lb)//求两数的卷积结果
{
DblNode * p1 , * p2 , * pp1 , * pp2 ;
int c1 ,c2 ,c* ;
c1 = la. first - > data ;
c1 = la.Length () - abs (c1) ;
c2 = lb. first - > data ;
c2 = lb.Length () - abs (c2) ;
c* = abs (c1) + abs (c2) ;
if ( (la. first - > data) * (1b. first - > data) < 0)
c* = c* * ( - 1) ;
first - > data = c* ;
p1 = la. first - > lLink ;p2 = lb. first - > lLink ;
while (p2 ! = lb. first)
{ pp2 = p2 ;
int k = 0 ;
pp1 = p1 ;
while (pp2 ! = 1b. first & &pp1 ! = la. first)
{
k = k + (pp1 - > data) * (pp2 - > data) ;
pp2 = pp2 - > rLink ;
pp1 = pp1 - > lLink ;
}
Insertfront (k) ;
p2 = p2 - > lLink ;
}
p1 = p1 - > lLink ; p2 = lb. first - > rLink ;
while (pl ! = la. first)
{
pp1 = p1 ;
pp2 = p2 ;
int k = 0 ;
while (pp1 ! = la. first &&pp2 ! = lb. first)
{
k = k + (pp1 - > data) * (pp2 - > data) ;
pp1 = pp1 - > lLink ;
pp2 = pp2 - > rLink ;
}
Insertfront (k)
p1 - p1 - > lLink ;
}
}
void DblList ∷ multiplication (DblList&ld)//卷积结果分离成商数;
{
DblNode * p ;
int k ,ij = 0 ,c = 0 ;
p = 1d. first - > lLink ;
while (p ! = ld. first)
{ k = c + p - > data ;
i = k %10 ;
c = kP 10 ;
Insertfront (i) ;
j + + ;
p = p - > lLink ;
}
while (c ! = 0)
{
i = c %10 ;
c = cP 10 ;
Insertfront (i) ;
j + + ;
}
k = ld. first - > data ;
i = j - abs (k) ;
first - > data = i ;
if (k < 0)
first->data = (first->data)*(-1) ;
}
void main () {
DblList pa (1) ;//构造初始双向循环链表pa
DblList pb (1) ;//构造初始双向循环链表pb
DblList pc (1) ;//构造初始双向循环链表pc
DblList pd (1) ;//构造初始双向循环链表pd
pa. input () ;//从键盘输入待计算的长整数串1并建立其对应的双向循环链表pa
pb. input () ;//从键盘输入待计算的长整数串2并建立其对应的双向循环链表pb
pc. conv olution (pa ,pb)//进行卷积运算并将其结果放在链表pc 中;
pd. multiplication (pc)// 将卷积结果转化为两数相乘的结果值放在双向链表pd中;
pd. print () ;// 输出结果值
}
/*运行结果示例
示例1 :
请输入长数字串 ,按回车键或 Ctrl + C结束:
12. 3456789012
请输入长数字串 ,按回车键或 Ctrl + C结束:
- 4567. 891234
12. 3456789012 3 - 4567. 891234 = - 56393.
7184305702320808
示例2 :
请输入长数字串 ,按回车键或 Ctrl + C结束:
1234567890
请输入长数字串 ,按回车键或 Ctrl + C结束:
23. 123456789
1234567890 3 23. 123456789 = 2854477257.
501905210
PS:
加法、 减法和除法等运算又如何实现呢 ? 用
带表头结点的双向循环链表表示的长数字串 ,对
于加、 减法运算 ,主要要处理好小数点对齐和进
位、 借位等问题 ,然后按位相加减即可实现;而对
于除法运算可以看成是除数的倒数乘以被除数 ,
即除法运算转化成乘法运算实现。如要求 x
y
的
值 ,我们可以把它看成是 x ×1
y
,而 1
y
可以用牛顿
法则的迭代计算公式: Ui+1 = Ui ×(2 - y ×Ui
) 进
行若干次迭代,根据精度要求精确到小数点后若
干位再与 x 相乘即可得到结果;迭代计算需要一
个初值 ,它必须满足大于0且小于1
y
的2倍 ,可通
过一个函数来实现。 限于篇幅,在此没有给出全部
程序。
*/
#include <iostream>
#include <cmath>
#include <stdlib.h>
using namespace std;
class DblList;
class DblNode{//双向链表结点类定义;
friend class DblList;
private:
int data;
DblNode *lLink , *rLink ;
public:
DblNode(int value,DblNode* left,DblNode *right):data(value),lLink(left),rLink(right){}
DblNode(int value):data(value),lLink(NULL),rLink(NULL){}
};
//
class DblList{
public :
DblList (int unique_Val) ;
~DblList () ;
void input () ;//P 从键盘输入一串长整数构造双向循环链表
int Length ( ) const ;//P 求链表中有效结点个数 ,即链表长度
void Insertfront (const int & value) ;//P 将新元素插入到链表头
void Insertrear (const int &value) ;//P 将新元素插入到链表尾
void print () ;//P 打印输出链表表示的长整数
void convolution (DblList&la ,DblList &lb) ;//P 求两数卷积运算
void multiplication (DblList& ld) ;// P 卷积结果分离成商数;
private :
DblNode *first;
};
//
DblList::DblList(int unique_Val){
first = new DblNode (unique_Val) ;
first->rLink = first->lLink = first ;
}
DblList::~DblList{
DblNode * p , * q ;
p =first - > rLink ;
while (p ! =first) {
q = p ;p = p - > rLink ;
delete q ;
}
delete first ;
}
int DblLst ∷ Length () const{//P 求链表的长度(结点个数)
DblNode * p =first - > rLink ;
int count = 0 ;
while (p ! =first) {p = p - > rLink ;count + + ;}
return count ;
}
void DblList ∷Insertrear (const int & value)//插入元素到链表尾
{ DblNode * p ;
p = new DblNode (value) ;
p - > rLink =first ;
p - > lLink =first - > lLink ;
first - > lLink - > rLink = p ;
first - > lLink = p ;
}
void DblList ∷Insertfront (const int & value)// 插入元素到链表头
{
DblNode * p ;
p = new DblNode (value) ;
if (first - > rLink = =first
{ p - > rLink =first ;
p - > lLink =first ;
first - > lLink =first - > lLink = p ;
}
else
{
p - > lLink =first - > lLink ;
p - > rLink =first ;
first - > lLink - > rLink = p ;
first - > lLink = p ;
}
}
void DblList ∷ input () {//从键盘输入一串长数字串建立其对应的双向循环链表;
char ch ;
int chint ;
int i = 0 ,k = 0 ;
cout < <“请输入长数字串 ,按回车键或 Ctrl+ C结束:” ;
while ( ! cin. eof () )
{
ch = cin. get () ;//接收从键盘输入的长数字串中的一个字符;
if (ch = =‘P n’ ) break ;
if (ch = =‘- ’ ) first - > data = - 1 ;
else
if (ch > =‘0’ &&ch < =‘9’ )
{
chint = ch -‘0’ ;
Insertrear (chint) ;
k + + ;
}
else if (ch = =‘.’ ) i = k ;
else{
cerr < <“输入错误 !”< < endl ;
exit (1) ;
}
}
if (i = = 0) i = k ;
first - > data = (first - > data) * i ;
}
void DblList ∷ print () {//打印输出链表所对应的长整数
DblNode * p ;
int ij ,k ;
p =first ;
i = abs (first -> data) ;
k =Length () ;
cout < <“\ n长整数为:” ;
if (p - > data < 0)
cout<<‘- ’ ;
j = 0 ;
while (p - > rLink ! =first) {
p = p - > rLink ;
cout < < p - > data ;
j + + ;
if (j = = i&& i ! = k) cout < <‘.’ ;
}
cout < <‘\ n’ ;
}
void DblList ∷conv olution (DblList& la , DblList &lb)//求两数的卷积结果
{
DblNode * p1 , * p2 , * pp1 , * pp2 ;
int c1 ,c2 ,c* ;
c1 = la. first - > data ;
c1 = la.Length () - abs (c1) ;
c2 = lb. first - > data ;
c2 = lb.Length () - abs (c2) ;
c* = abs (c1) + abs (c2) ;
if ( (la. first - > data) * (1b. first - > data) < 0)
c* = c* * ( - 1) ;
first - > data = c* ;
p1 = la. first - > lLink ;p2 = lb. first - > lLink ;
while (p2 ! = lb. first)
{ pp2 = p2 ;
int k = 0 ;
pp1 = p1 ;
while (pp2 ! = 1b. first & &pp1 ! = la. first)
{
k = k + (pp1 - > data) * (pp2 - > data) ;
pp2 = pp2 - > rLink ;
pp1 = pp1 - > lLink ;
}
Insertfront (k) ;
p2 = p2 - > lLink ;
}
p1 = p1 - > lLink ; p2 = lb. first - > rLink ;
while (pl ! = la. first)
{
pp1 = p1 ;
pp2 = p2 ;
int k = 0 ;
while (pp1 ! = la. first &&pp2 ! = lb. first)
{
k = k + (pp1 - > data) * (pp2 - > data) ;
pp1 = pp1 - > lLink ;
pp2 = pp2 - > rLink ;
}
Insertfront (k)
p1 - p1 - > lLink ;
}
}
void DblList ∷ multiplication (DblList&ld)//卷积结果分离成商数;
{
DblNode * p ;
int k ,ij = 0 ,c = 0 ;
p = 1d. first - > lLink ;
while (p ! = ld. first)
{ k = c + p - > data ;
i = k %10 ;
c = kP 10 ;
Insertfront (i) ;
j + + ;
p = p - > lLink ;
}
while (c ! = 0)
{
i = c %10 ;
c = cP 10 ;
Insertfront (i) ;
j + + ;
}
k = ld. first - > data ;
i = j - abs (k) ;
first - > data = i ;
if (k < 0)
first->data = (first->data)*(-1) ;
}
void main () {
DblList pa (1) ;//构造初始双向循环链表pa
DblList pb (1) ;//构造初始双向循环链表pb
DblList pc (1) ;//构造初始双向循环链表pc
DblList pd (1) ;//构造初始双向循环链表pd
pa. input () ;//从键盘输入待计算的长整数串1并建立其对应的双向循环链表pa
pb. input () ;//从键盘输入待计算的长整数串2并建立其对应的双向循环链表pb
pc. conv olution (pa ,pb)//进行卷积运算并将其结果放在链表pc 中;
pd. multiplication (pc)// 将卷积结果转化为两数相乘的结果值放在双向链表pd中;
pd. print () ;// 输出结果值
}
/*运行结果示例
示例1 :
请输入长数字串 ,按回车键或 Ctrl + C结束:
12. 3456789012
请输入长数字串 ,按回车键或 Ctrl + C结束:
- 4567. 891234
12. 3456789012 3 - 4567. 891234 = - 56393.
7184305702320808
示例2 :
请输入长数字串 ,按回车键或 Ctrl + C结束:
1234567890
请输入长数字串 ,按回车键或 Ctrl + C结束:
23. 123456789
1234567890 3 23. 123456789 = 2854477257.
501905210
PS:
加法、 减法和除法等运算又如何实现呢 ? 用
带表头结点的双向循环链表表示的长数字串 ,对
于加、 减法运算 ,主要要处理好小数点对齐和进
位、 借位等问题 ,然后按位相加减即可实现;而对
于除法运算可以看成是除数的倒数乘以被除数 ,
即除法运算转化成乘法运算实现。如要求 x
y
的
值 ,我们可以把它看成是 x ×1
y
,而 1
y
可以用牛顿
法则的迭代计算公式: Ui+1 = Ui ×(2 - y ×Ui
) 进
行若干次迭代,根据精度要求精确到小数点后若
干位再与 x 相乘即可得到结果;迭代计算需要一
个初值 ,它必须满足大于0且小于1
y
的2倍 ,可通
过一个函数来实现。 限于篇幅,在此没有给出全部
程序。
*/
- 两个长数字串全乘双向链表实现
- 双向链表实现长整数运算
- 两个数乘运算
- 两个任意长度的长整数相乘(C语言、双向链表方法)
- HDU1261字串数(全排列)
- 字符串或数字串全排列问题
- 链表实现两个数相加
- 实现双向链表的创建、测长、打印、插入、删除
- 利用双向循环链表实现任意长的整数进行加法运算
- c# 抽象方法:实现两个数的加、减、乘操作运算
- 解决 PHPExcel 长数字串显示为科学计数
- poi的 excel 身份证等长数字串 问题
- 解决 PHPExcel 长数字串显示为科学计数
- 解决 PHPExcel 长数字串显示为科学计数
- tf22: ocr识别——不定长数字串识别
- hdu1261字串数(组合数--大数问题--包括加 ,乘,除)
- 实现双向链表
- 双向链表实现
- 4个Android Chart开源免费的图表插件项目
- 内存池的实现(2)
- 引起Iphone应用被App Store拒绝的原因
- 写文章之前先测试一下
- Ubuntu下acer-wmi模块Inter Wireless-N 1000网卡无法上网解决办法
- 两个长数字串全乘双向链表实现
- 自己编的计算器,能连续计算
- 图形用户界面设计——CardLayout布局管理器
- linux opensuse ssh联通
- ACE中网络通讯编程基本架构
- VC读写XML文件
- omap android 的资料链接
- 【这篇文章我找了好久啊。。。。用RGB像素画图!!!!!!!!!!!!!!!】使用SetDIBitsToDevice显示RGB数组
- 软中断和硬中断的区别