版权声明:转载请注明出处。 https://blog.csdn.net/baidu_38304645/article/details/82933191
稀疏多项式:如P(x)=1+3x1000+x20000; Q(x)=x+x50000
R(x)=1+x+3x1000+x20000+x50000。
数学模型:
P=((1,0),(3,1000),(1,20000)) Q=((1,1),(1,50000)) R=((1,0),(1,1),(3,1000),(1,20000),(1,50000))
一个基础元素称为一个小项,可定义类型Term
typedef struct{
float coef;int expn;
}Term;
一个多项式实际可看做元素类型为term的线性结构的数据对象,可在线性表的基础上实现具体操作。
首先定义辅助宏:
#define OK 1
#define LIST_INIT_SIZE 100
#define LISTINCREMENT 10
#define ERROR 0
#define TRUE 1
#define FALSE 0
#define NULL 0
#define OVERFLOW -1
typedef int Status;
多项式的存储结构定义:
//多项式的存储结构定义
typedef struct{
float coef; //系数
int expn; //指数
}term,ElemType;
typedef struct LNode{
ElemType data;
struct LNode *next;
}*LinkList;
typedef LinkList Polynomial;
插入一个结点,使之按照指数大小从大到小排序。
Status Insert(Polynomial &P,Polynomial &q){
//插入一个结点
if(q->data.coef==0)
return OK;
LNode *prep,*p;
prep=P;
p=P->next;
while(p&&p->data.expn>q->data.expn){ //有序插入
prep=p;
p=p->next;
}
if(!p) //没找到插入队尾
prep->next=q;
else{
if(p->data.expn==q->data.expn) { //指数相等
if(p->data.coef==q->data.coef*(-1)){ //系数和为0则销毁
prep->next=p->next;
free(p);
}
else //否则系数改变
p->data.coef+=q->data.coef;
}
else{ //指数不相等,插入这一项
prep->next=q;
q->next=p;
}
}
return OK;
}
输入n项指数与系数,创建一元多项式.
Status InputElem(ElemType &e){
//输入一个项
scanf("%f %d",&e.coef,&e.expn);
return OK;
}
Status CreatePolyn(Polynomial &P,int n){
//输入n项指数与系数,创建一元多项式
printf("请输入多项式的项数: ");
scanf("%d",&n);
if(n<0)
return ERROR;
LNode *p;
P=(LNode *)malloc(sizeof(LNode));
if(!P) //创建失败
exit(OVERFLOW);
P->next=NULL;
for(int i=0;i<n;i++){
p=(LNode *)malloc(sizeof(LNode));
p->next=NULL;
if(!p)
exit(OVERFLOW);
printf("请输入第 %d 项的系数与指数 :",i+1);
InputElem(p->data);
Insert(P,p); //插入这个项,要求幂递增,乘法等也可用
}
}
输出多项式.
Status PrintPolyn(Polynomial &P){
//输出多项式
if(!P->next)
printf("空多项式\n");
else{
LNode *p=P->next;
while(p){
if(p->data.coef>0&&p!=P->next)
printf("+");
if(p->data.coef==-1&&p->data.expn!=0)
printf("-");
if(p->data.coef!=1&&p->data.coef!=-1)
printf("%.f",p->data.coef);
else if((p->data.coef==1||p->data.coef==-1)&&p->data.expn==0)
printf("%.f",p->data.coef);
if(p->data.expn!=0)
printf("x");
if(p->data.expn!=1&&p->data.expn!=0)
printf("^%d",p->data.expn);
p=p->next;
}
printf("\n");
}
return OK;
}
销毁一元多项式.
Status DestroyPolyn(Polynomial &P){
//销毁一元多项式
LNode *p=P,*q;
while(p){
q=p->next;
free(p);
p=NULL;
p=q;
}
return OK;
}
计算Pa=Pa+Pb 并销毁Pb。
Status AddPolyn(Polynomial &Pa,Polynomial &Pb){
//计算Pa=Pa+Pb 并销毁Pb。
//如果pa指数等于pb的指数 一种情况两者系数和为0,此时
//销毁pa项并且释放pb当前项。反之pa系数加上pb的系数并且释放pb当前项
LNode *pa=Pa->next,*pb=Pb->next;
LNode *prea=Pa,*preb=Pb;
while(pa&&pb) { //用两个指针遍历整个链表
if(pa->data.expn==pb->data.expn){
if(pa->data.coef==pb->data.coef*(-1)){
prea->next=pa->next;
free(pa);
pa=prea->next;
preb->next=pb->next;
free(pb);
pb=preb->next;
}
else{
pa->data.coef+=pb->data.coef;
prea=pa;
pa=pa->next;
preb->next=pb->next;
free(pb);
pb=preb->next;
}
}
else if(pa->data.expn<pb->data.expn){ //如果pa指数小,将pb这个结点插入pa前面 并且释放pb当前项
preb->next=pb->next;
pb->next=pa;
prea->next=pb;
pb=preb->next;
}
else { // 比较当前两项 如果pa指数大 pa后移一位
prea=pa;
pa=pa->next;
}
}
if(pb)
prea->next=pb;
free(Pb);
Pb = NULL;
return OK;
}
计算Pa=Pa-Pb 并销毁Pb。
Status DecreasePolyn(Polynomial &Pa,Polynomial &Pb){
//计算Pa=Pa-Pb 并销毁Pb。
LNode *pa=Pa->next,*pb=Pb->next,*q;
LNode *prea=Pa,*preb=Pb;
while(pa&&pb){//用两个指针遍历整个链表
if(pa->data.expn==pb->data.expn){//如果pa指数等于pb的指数 一种情况两者系数相等,此时销毁pa项并且释放pb当前项。反之pa系数加上pb的系数并且释放pb当前项
if(pa->data.coef==pb->data.coef) {
prea->next=pa->next;
free(pa);
pa=prea->next;
preb->next=pb->next;
free(pb);
pb=preb->next;
}
else{
pa->data.coef-=pb->data.coef;
prea=pa;
pa=pa->next;
preb->next=pb->next;
free(pb);
pb=preb->next;
}
}
else if(pa->data.expn<pb->data.expn){//如果pa指数小,将pb这个结点插入pa前面 并且释放pb当前项
pb->data.coef*=(-1);
preb->next=pb->next;
pb->next=pa;
prea->next=pb;
pb=preb->next;
}
else{//比较当前两项 如果pa指数大 pa后移一位
prea=pa;
pa=pa->next;
}
}
q=pb;
while(pb){
pb->data.coef*=(-1);
pb=pb->next;
}
if(q)
prea->next=q;
free(Pb);
return OK;
}
计算Pc=Pa*Pb 。
Status RidePolyn(Polynomial &Pa,Polynomial &Pb,Polynomial &Pc){
//计算Pc=Pa*Pb 。
Pc=(LNode *)malloc(sizeof(LNode));
if(!Pc)
exit(OVERFLOW);
Pc->next=NULL;
LNode *pa=Pa->next,*pb=Pb->next,*p; //设两个指针遍历Pa Pb
while(pa) { //循环Pa与Pb 将每一项相乘,得到一个新的结点插入Pc中
while(pb) {
p=(LNode *)malloc(sizeof(LNode)); //设立一个新结点
p->next=NULL;
if(!p)
exit(OVERFLOW);
p->data.coef=pa->data.coef*pb->data.coef;
p->data.expn=pa->data.expn+pb->data.expn;
Insert(Pc,p);//插入新结点
pb=pb->next;
}
pa=pa->next;
pb=Pb->next;
}
return OK;
}
计算Pc=Pa/Pb 。商存入Pc,余数存入Pa.
Status RemovePolyn(Polynomial &Pa,Polynomial &Pb,Polynomial &Pc){
//计算Pc=Pa/Pb 。商存入Pc,余数存入Pa
//算法思路:首先整除一下,然后计算得到的余数,然后再用余数除Pb,
//不断循环直到余数的首项指数小于Pb的首项指数为止,即余数为0
Polynomial P; //设立一个临时多项式
Pc=(LNode *)malloc(sizeof(LNode));
if(!Pc)
exit(OVERFLOW);
Pc->next=NULL;
float a;
int b;
LNode *pa=Pa->next,*pb=Pb->next,*p,*q;
while(pa&&pb&&pa->data.expn>=pb->data.expn){ //当Pa首项的指数大于等于Pb首项的指数
p=(LNode *)malloc(sizeof(LNode)); //设立新节点保存Pa与Pb首项之商
if(!p)
exit(OVERFLOW);
p->next=NULL;
a=pa->data.coef/pb->data.coef;
b=pa->data.expn-pb->data.expn;
p->data.coef=a;
p->data.expn=b;
Insert(Pc,p); //将得到的商结点插入Pc中
P=(LNode *)malloc(sizeof(LNode)); //创建临时多项式
if(!P)
exit(OVERFLOW);
P->next=NULL;
while(pb) {//遍历Pb中的每一项
q=(LNode *)malloc(sizeof(LNode)); //设立新节点,保存pb中项与得到的商结点相乘的项
if(!q)
exit(OVERFLOW);
q->next=NULL;
q->data.coef=a*pb->data.coef;
q->data.expn=b+pb->data.expn;
Insert(P,q); //将得到结点插入临时多项式中
pb=pb->next;
}
DecreasePolyn(Pa,P);//将Pa与临时多项式相减 得到一个新的Pa
pa=Pa->next; //获得首项
pb=Pb->next;
}
return OK;
}
进行多项式的求导.
Status PolynDerivative(Polynomial &P){
//进行多项式的求导
LNode *p=P->next,*prep=P;
while(p){ //遍历每一个项
if(p->data.expn==0){//若指数为零,删除这个项
prep->next=p->next;
free(p);
p=prep->next;
}
else{ //指数不为零 修改系数与指数
p->data.coef*=p->data.expn;
p->data.expn--;
prep=p;
p=p->next;
}
}
return OK;
}