1/16
一元多项式的加法、减法、乘法和求导
一、【实验构思(Conceive)】(10%)
(本部分应包括:描述实验实现的基本思路,包括所用到的离散数学、工程数学、程
序设计、算法等相关知识)
1、一元稀疏多项式的加法、减法、乘法和求导法则:
假设:f(x)=3x^8+9x^5
g(x)=7x^9+3x
则:f(x)+g(x)=7x^9+3x^8+9x^5+3x
f(x)-g(x)=-7x^9+3x^8+9x^5-3x
f(x)*g(x)=21x^17+63x^14+9x^9+27x^6
f'(x)=24x^7+45x^4
2、基本思路:
首先定义一个结构体,其中定义一元多项式中的两个参数:系数和指数和链表中结点
的指针域;然后一一罗列每个在主程序中用到的函数,并一一实现;最后在主程序中
主要完成用户的输入和相关函数的调用。
二、【实验设计(Design)】(20%)
voidinrt(PLOYList*head,PLOYList*input)
//查找位置插入新链节的函数,且让输入的多项式呈降序排列
PLOYList*creat(charch)
//输入多项式
PLOYList*add(PLOYList*head,PLOYList*pre)
//多项式相加,head为第一个多项式建立的链表表头,pre为第二个多项式建立的链
表表头
PLOYList*sub(PLOYList*head,PLOYList*pre)
//多项式相减
PLOYList*mul(PLOYList*head,PLOYList*pre)
2/16
//多项式相乘
PLOYList*der(PLOYList*head)
//多项式求导
voidprint(PLOYList*fun)
//输出多项式,fun指要输出的多项式链表的表头
voidstart()
//用户选择界面
主程序:
voidmain()
{
PLOYList*f,*g,*pf,*hf,*p;
intsign=-1;
start();
while(sign!=0)
{
scanf("%d",&sign);
switch(sign)
{
ca0:
break;
ca1://多项式相加
{
printf("你选择的操作是多项式相加:n");
printf("请输入第一个多项式f(x):");
f=creat('f');
printf("第一个多项式为:f(x)=");
print(f);
printf("请输入第二个多项式g(x):");
g=creat('g');
printf("第二个多项式为:g(x)=");
print(g);
printf("结果为:F(x)=f(x)+g(x)=");
f=add(f,g);
print(f);
printf("nn");
printf("继续请选择相应操作,退出请按0.");
break;
}
ca2://多项式相减
{
printf("你选择的操作是多项式相减:n");
printf("请输入第一个多项式f(x):");
f=creat('f');
printf("第一个多项式为:f(x)=");
print(f);
printf("请输入第二个多项式g(x):");
3/16
g=creat('g');
printf("第二个多项式为:g(x)=");
print(g);
printf("结果为:F(x)=f(x)-g(x)=");
f=sub(f,g);
print(f);
printf("nn");
printf("继续请选择相应操作,退出请按0.");
break;
}
ca3://多项式相乘
{
printf("你选择的操作是多项式相乘:n");
printf("请输入第一个多项式f(x):");
f=creat('f');
printf("第一个多项式为:f(x)=");
print(f);
printf("请输入第二个多项式g(x):");
g=creat('g');
printf("第二个多项式为:g(x)=");
print(g);
printf("结果为:F(x)=f(x)*g(x)=");
pf=mul(f,g);
print(pf);
printf("nn");
printf("继续请选择相应操作,退出请按0.");
break;
}
ca4://多项式求导
{
printf("您选择的是对一个一元多项式求导:n");
printf("请输入一个一元多项式:");
f=creat('f');
printf("这个多项式为:f(x)=");
print(f);
printf("求导结果为:F(x)=f'(x)=");
f=der(f);
print(f);
printf("nn");
printf("继续请选择相应操作,退出请按0.");
break;
}
ca5://帮助用户理解输入规则
{
printf("---------------------------帮助------------------------------n");
printf("n");
printf("1.输入时只输入多项式的系数与指数n");
printf("2.输入多项式形式:系数1指数1系数2指数2……,以00结束n");
printf("3.例如输入"112200"表示"1*X^1+2*X^2"n");
printf("n");
printf("---------------------------帮助------------------------------n");
printf("nn");
break;
}
4/16
default:
{
printf("看完帮助信息后请重新选择操作n");
break;
}
}//swith
}//while
}//void
三、【实现描述(Implement)】(30%)
1.插入函数,用来对根据用户输入的项建立的单个结点进行排序,使其按照指数降序
排列,此函数也可以用在多项式的加减法里,因为加减法实质上也是插入的过程。
voidinrt(PLOYList*head,PLOYList*input)//查找位置插入新链节的函数,且让输入的多项式呈降序排列
{
PLOYList*pre,*now;
intsignal=0;
pre=head;
if(pre->next==NULL){pre->next=input;}//如果只有一个头结点,则把新结点直接连在后面
el
{
now=pre->next;//如果不是只有一个头结点,则设置now指针
while(signal==0)
{
if(input->expn
{
if(now->next==NULL)
{
now->next=input;
signal=1;
}
el
{
pre=now;
now=pre->next;//始终让新输入的数的指数与最后一个结点中的数的指数比较,小于则插在其后
面
}
}
elif(input->expn>now->expn)
{
input->next=now;
pre->next=input;
signal=1;
}//若新结点中指数比最后一个结点即now中的指数大,则插入now之前
el//若指数相等则需合并为一个结点,若相加后指数为0则释放该结点
{
now->coef=now->coef+input->coef;
signal=1;
free(input);
if(now->coef==0)
{
pre->next=now->next;
5/16
free(now);
}
}//el
}//while
}//el
}//void
2.输入函数,用来实现用户对多项式的输入,且根据用户的输入,输入一个项则建立
一个结点并调用inrt函数进行排序,此函数满足用户随便输入多项式的项数,以0
结束输入。
PLOYList*creat(charch)//输入多项式
{
PLOYList*head,*input;
floatx;
inty;
head=(PLOYList*)malloc(sizeof(PLOYList));//创建链表头
head->next=NULL;
scanf("%f%d",&x,&y);//实现用户输入的第一个项,包括其指数和系数
while(x!=0)//当用户没有输入结束标志0时可一直输入多项式的项,且输入一个创建一个结点
{
input=(PLOYList*)malloc(sizeof(PLOYList));//创建新链节
input->coef=x;
input->expn=y;
input->next=NULL;
inrt(head,input);//每输入一项就将其排序,是的链表中多项式呈降序排列
scanf("%f%d",&x,&y);
}
returnhead;
}
3.实现多项式的加法的函数,运用插入函数,若实现f(x)+g(x),即将g(x)中的每项
一个一个查找位置并插入到f(x)中,即最后加法的结果保存在f(x)中。
PLOYList*add(PLOYList*head,PLOYList*pre)//多项式相加,head为第一个多项式建立的链表表头,pre
为第二个多项式建立的链表表头
{
PLOYList*input;
intflag=0;
while(flag==0)
{
if(pre->next==NULL)
flag=1;//若该链表为空,则无需进行加法运算,跳出循环
el
{
pre=pre->next;
input=(PLOYList*)malloc(sizeof(PLOYList));//申请空间
input->coef=pre->coef;
input->expn=pre->expn;
input->next=NULL;
inrt(head,input);//把g(x)插入到f(x)中,相当于两者相加,结果保存于f(x)
}
}
returnhead;
}
4.实现多项式的减法的函数,运用插入函数,若实现f(x)-g(x),则将g(x)中的每项
的系数变为其相反数,再用和加法实现一样的过程实现。
6/16
PLOYList*sub(PLOYList*head,PLOYList*pre)//多项式相减
{
PLOYList*input;
intflag=0;
while(flag==0)
{
if(pre->next==NULL)
flag=1;
el
{
pre=pre->next;
input=(PLOYList*)malloc(sizeof(PLOYList));
input->coef=0-pre->coef;//将第二个多项式里的数变为其相反数,再用和加法一样的方法实现减法
input->expn=pre->expn;
input->next=NULL;
inrt(head,input);
}
}
returnhead;
}
4.实现多项式的乘法的函数,也运用插入函数,若实现f(x)*g(x),则运用二重循环
将g(x)中的每项与f(x)中的每项相乘,再运用插入函数对其进行排序和合并。
PLOYList*mul(PLOYList*head,PLOYList*pre)//多项式项乘
{
PLOYList*hf,*pf,*qa,*qb;
qa=head->next;
qb=pre->next;//定义指针指向表头后一个元素,即链表中第一个元素
hf=(PLOYList*)malloc(sizeof(PLOYList));//新创建一个结点,当做表头
hf->next=NULL;
for(;qa;qa=qa->next)
{
for(qb=pre->next;qb;qb=qb->next)//用两个循环,实现两个多项式之间每个项相乘,结果用inrt
函数进行排序与合并
{
pf=(PLOYList*)malloc(sizeof(PLOYList));
pf->coef=qa->coef*qb->coef;
pf->expn=qa->expn+qb->expn;
pf->next=NULL;
inrt(hf,pf);
}
}
returnhf;
}
5.实现多项式的求导的函数,将多项式的每项系数和指数相乘得到新的系数,指数减
一得到新的指数即完成求导。
PLOYList*der(PLOYList*head)//多项式求导
{
PLOYList*p;
p=head->next;
while(p)
{
p->coef=p->coef*p->expn;
7/16
p->expn=p->expn--;
p=p->next;
}
returnhead;
}//将多项式的每项系数和指数相乘得到新的系数,指数减一得到新的指数即完成求导
6.输出函数,满足判断多项式输出,根据是用户的输入选择我调用算法来实现用户想要计
算的功能,与此同时他其实也在调用上面的功能函数
voidprint(PLOYList*fun)//输出多项式,fun指要输出的多项式链表的表头
{
PLOYList*printing;
intflag=0;
printing=fun->next;
if(fun->next==NULL)//若为空表,则无需输出
{
printf("0n");
return;
}
while(flag==0)
{
if(printing->coef>0&&fun->next!=printing)
printf("+");
if(printing->coef==1);
elif(printing->coef==-1)
printf("-");
el
printf("%f",printing->coef);
if(printing->expn!=0)printf("x^%d",printing->expn);
elif((printing->coef==1)||(printing->coef==-1))
printf("1");
if(printing->next==NULL)
flag=1;
el
printing=printing->next;
}
printf("n");
}
7.用户输入界面,提供用户输入的提示。
voidstart()//用户选择界面
{
printf("************************************n");
printf("用户选择界面n");
printf("************************************n");
printf("**n");
printf("*1.两个一元多项式相加*n");
printf("*2.两个一元多项式相减*n");
printf("*3.两个一元多项式相乘*n");
printf("*4.对一个一个一元多项式求导*n");
printf("*5.帮助*n");
printf("*0.退出系统*n");
printf("**n");
printf("************************************n");
printf("n");
printf("注:输入多项式格式为:系数1指数1系数2指数2……,并以00结束:n");
printf("n");
8/16
printf("请选择操作:");
}
四、【测试结果(Testing)】(10%)
************************************
用户选择界面
************************************
**
*1.两个一元多项式相加*
*2.两个一元多项式相减*
*3.两个一元多项式相乘*
*4.对一个一个一元多项式求导*
*5.帮助*
*0.退出系统*
**
************************************
注:输入多项式格式为:系数1指数1系数2指数2……,并以00结束:
请选择操作:1
你选择的操作是多项式相加:
请输入第一个多项式f(x):23456700
第一个多项式为:f(x)=6.000000x^7+4.000000x^5+2.000000x^3
请输入第二个多项式g(x):13567500
第二个多项式为:g(x)=5.000000x^6+7.000000x^5+x^3
结果为:F(x)=f(x)+g(x)=6.000000x^7+5.000000x^6+11.000000x^5+3.000000x^3
9/16
继续请选择相应操作,退出请按0.2
你选择的操作是多项式相减:
请输入第一个多项式f(x):23456700
第一个多项式为:f(x)=6.000000x^7+4.000000x^5+2.000000x^3
请输入第二个多项式g(x):13567500
第二个多项式为:g(x)=5.000000x^6+7.000000x^5+x^3
结果为:F(x)=f(x)-g(x)=6.000000x^7-5.000000x^6-3.000000x^5+x^3
继续请选择相应操作,退出请按0.3
你选择的操作是多项式相乘:
请输入第一个多项式f(x):234500
第一个多项式为:f(x)=4.000000x^5+2.000000x^3
请输入第二个多项式g(x):135600
第二个多项式为:g(x)=5.000000x^6+x^3
结果为:F(x)=f(x)*
g(x)=20.000000x^11+10.000000x^9+4.000000x^8+2.000000x^6
继续请选择相应操作,退出请按0.4
您选择的是对一个一元多项式求导:
请输入一个一元多项式:23456500
这个多项式为:f(x)=10.000000x^5+2.000000x^3
求导结果为:F(x)=f'(x)=50.000000x^4+6.000000x^2
继续请选择相应操作,退出请按0.5
---------------------------帮助------------------------------
1.输入时只输入多项式的系数与指数
2.输入多项式形式:系数1指数1系数2指数2……,以00结束
3.例如输入"112200"表示"1*X^1+2*X^2"
---------------------------帮助------------------------------
10/16
1(帮助后可重新输入想要进行的操作,这里选1,进行加法运算)
你选择的操作是多项式相加:
请输入第一个多项式f(x):123400
第一个多项式为:f(x)=3.000000x^4+x^2
请输入第二个多项式g(x):324500
第二个多项式为:g(x)=4.000000x^5+3.000000x^2
结果为:F(x)=f(x)+g(x)=4.000000x^5+3.000000x^4+4.000000x^2
继续请选择相应操作,退出请按0.
四、【实验总结】(10%)
通过本次试验,更加规范了我使用数据结构来编写相关程序的格式和方法。且增强了
寻找错误位置的能力。在实验过程中,出现过很多各种各样的错误,如函数的参数设
定不对或调用时的参数不对、循环时的某些初始化的遗忘,以及指针的运用出错。通
过解决问题,还增加了很多以前不懂得知识,但仍然还有很多方面需要更正和改进,
以使自己编写的程序的出错率减少。
五、【项目运作描述(Operate)】(10%)
通过用户输入界面,让用户省掉了笔算的麻烦,并使处理一元稀疏多项式运算的速率
提高。
六、【代码】(10%)
(本部分应包括:完整的代码及充分的注释。注意纸质的实验报告无需包括此部分。
格式统一为,字体:Georgia,行距:固定行距12,字号:小五)
#include
#include
typedefstructnode//定义节点类型
{
floatcoef;//多项式的系数
intexpn;//多项式的指数
structnode*next;//结点指针域
}PLOYList;
voidinrt(PLOYList*head,PLOYList*input)//查找位置插入新链节的函数,且让输入的多项式呈降序排列
{
11/16
PLOYList*pre,*now;
intsignal=0;
pre=head;
if(pre->next==NULL){pre->next=input;}//如果只有一个头结点,则把新结点直接连在后面
el
{
now=pre->next;//如果不是只有一个头结点,则设置now指针
while(signal==0)
{
if(input->expn
{
if(now->next==NULL)
{
now->next=input;
signal=1;
}
el
{
pre=now;
now=pre->next;//始终让新输入的数的指数与最后一个结点中的数的指数比较,小于则插在其后
面
}
}
elif(input->expn>now->expn)
{
input->next=now;
pre->next=input;
signal=1;
}//若新结点中指数比最后一个结点即now中的指数大,则插入now之前
el//若指数相等则需合并为一个结点,若相加后指数为0则释放该结点
{
now->coef=now->coef+input->coef;
signal=1;
free(input);
if(now->coef==0)
{
pre->next=now->next;
free(now);
}
}//el
}//while
}//el
}//void
PLOYList*creat(charch)//输入多项式
{
PLOYList*head,*input;
floatx;
inty;
head=(PLOYList*)malloc(sizeof(PLOYList));//创建链表头
head->next=NULL;
scanf("%f%d",&x,&y);//实现用户输入的第一个项,包括其指数和系数
while(x!=0)//当用户没有输入结束标志0时可一直输入多项式的项,且输入一个创建一个结点
{
input=(PLOYList*)malloc(sizeof(PLOYList));//创建新链节
12/16
input->coef=x;
input->expn=y;
input->next=NULL;
inrt(head,input);//每输入一项就将其排序,是的链表中多项式呈降序排列
scanf("%f%d",&x,&y);
}
returnhead;
}
PLOYList*add(PLOYList*head,PLOYList*pre)//多项式相加,head为第一个多项式建立的链表表头,pre
为第二个多项式建立的链表表头
{
PLOYList*input;
intflag=0;
while(flag==0)
{
if(pre->next==NULL)
flag=1;//若该链表为空,则无需进行加法运算,跳出循环
el
{
pre=pre->next;
input=(PLOYList*)malloc(sizeof(PLOYList));//申请空间
input->coef=pre->coef;
input->expn=pre->expn;
input->next=NULL;
inrt(head,input);//把g(x)插入到f(x)中,相当于两者相加,结果保存于f(x)
}
}
returnhead;
}
PLOYList*sub(PLOYList*head,PLOYList*pre)//多项式相减
{
PLOYList*input;
intflag=0;
while(flag==0)
{
if(pre->next==NULL)
flag=1;
el
{
pre=pre->next;
input=(PLOYList*)malloc(sizeof(PLOYList));
input->coef=0-pre->coef;//将第二个多项式里的数变为其相反数,再用和加法一样的方法实现减法
input->expn=pre->expn;
input->next=NULL;
inrt(head,input);
}
}
returnhead;
}
PLOYList*mul(PLOYList*head,PLOYList*pre)//多项式项乘
13/16
{
PLOYList*hf,*pf,*qa,*qb;
qa=head->next;
qb=pre->next;//定义指针指向表头后一个元素,即链表中第一个元素
hf=(PLOYList*)malloc(sizeof(PLOYList));//新创建一个结点,当做表头
hf->next=NULL;
for(;qa;qa=qa->next)
{
for(qb=pre->next;qb;qb=qb->next)//用两个循环,实现两个多项式之间每个项相乘,结果用inrt
函数进行排序与合并
{
pf=(PLOYList*)malloc(sizeof(PLOYList));
pf->coef=qa->coef*qb->coef;
pf->expn=qa->expn+qb->expn;
pf->next=NULL;
inrt(hf,pf);
}
}
returnhf;
}
PLOYList*der(PLOYList*head)//多项式求导
{
PLOYList*p;
p=head->next;
while(p)
{
p->coef=p->coef*p->expn;
p->expn=p->expn--;
p=p->next;
}
returnhead;
}//将多项式的每项系数和指数相乘得到新的系数,指数减一得到新的指数即完成求导
voidprint(PLOYList*fun)//输出多项式,fun指要输出的多项式链表的表头
{
PLOYList*printing;
intflag=0;
printing=fun->next;
if(fun->next==NULL)//若为空表,则无需输出
{
printf("0n");
return;
}
while(flag==0)
{
if(printing->coef>0&&fun->next!=printing)
printf("+");
if(printing->coef==1);
elif(printing->coef==-1)
printf("-");
el
printf("%f",printing->coef);
if(printing->expn!=0)printf("x^%d",printing->expn);
14/16
elif((printing->coef==1)||(printing->coef==-1))
printf("1");
if(printing->next==NULL)
flag=1;
el
printing=printing->next;
}
printf("n");
}
voidstart()//用户选择界面
{
printf("************************************n");
printf("用户选择界面n");
printf("************************************n");
printf("**n");
printf("*1.两个一元多项式相加*n");
printf("*2.两个一元多项式相减*n");
printf("*3.两个一元多项式相乘*n");
printf("*4.对一个一个一元多项式求导*n");
printf("*5.帮助*n");
printf("*0.退出系统*n");
printf("**n");
printf("************************************n");
printf("n");
printf("注:输入多项式格式为:系数1指数1系数2指数2……,并以00结束:n");
printf("n");
printf("请选择操作:");
}
voidmain()
{
PLOYList*f,*g,*pf,*hf,*p;
intsign=-1;
start();
while(sign!=0)
{
scanf("%d",&sign);
switch(sign)
{
ca0:
break;
ca1://多项式相加
{
printf("你选择的操作是多项式相加:n");
printf("请输入第一个多项式f(x):");
f=creat('f');
printf("第一个多项式为:f(x)=");
print(f);
printf("请输入第二个多项式g(x):");
g=creat('g');
printf("第二个多项式为:g(x)=");
print(g);
printf("结果为:F(x)=f(x)+g(x)=");
f=add(f,g);
15/16
print(f);
printf("nn");
printf("继续请选择相应操作,退出请按0.");
break;
}
ca2://多项式相减
{
printf("你选择的操作是多项式相减:n");
printf("请输入第一个多项式f(x):");
f=creat('f');
printf("第一个多项式为:f(x)=");
print(f);
printf("请输入第二个多项式g(x):");
g=creat('g');
printf("第二个多项式为:g(x)=");
print(g);
printf("结果为:F(x)=f(x)-g(x)=");
f=sub(f,g);
print(f);
printf("nn");
printf("继续请选择相应操作,退出请按0.");
break;
}
ca3://多项式相乘
{
printf("你选择的操作是多项式相乘:n");
printf("请输入第一个多项式f(x):");
f=creat('f');
printf("第一个多项式为:f(x)=");
print(f);
printf("请输入第二个多项式g(x):");
g=creat('g');
printf("第二个多项式为:g(x)=");
print(g);
printf("结果为:F(x)=f(x)*g(x)=");
pf=mul(f,g);
print(pf);
printf("nn");
printf("继续请选择相应操作,退出请按0.");
break;
}
ca4://多项式求导
{
printf("您选择的是对一个一元多项式求导:n");
printf("请输入一个一元多项式:");
f=creat('f');
printf("这个多项式为:f(x)=");
print(f);
printf("求导结果为:F(x)=f'(x)=");
f=der(f);
print(f);
printf("nn");
printf("继续请选择相应操作,退出请按0.");
break;
16/16
}
ca5://帮助用户理解输入规则
{
printf("---------------------------帮助------------------------------n");
printf("n");
printf("1.输入时只输入多项式的系数与指数n");
printf("2.输入多项式形式:系数1指数1系数2指数2……,以00结束n");
printf("3.例如输入"112200"表示"1*X^1+2*X^2"n");
printf("n");
printf("---------------------------帮助------------------------------n");
printf("nn");
break;
}
default:
{
printf("看完帮助信息后请重新选择操作n");
break;
}
}//swith
}//while
}//void
本文发布于:2022-11-12 18:52:06,感谢您对本站的认可!
本文链接:http://www.wtabcd.cn/fanwen/fan/88/6060.html
版权声明:本站内容均来自互联网,仅供演示用,请勿用于商业和其他非法用途。如果侵犯了您的权益请与我们联系,我们将在24小时内删除。
留言与评论(共有 0 条评论) |