数据结构 - 稀疏运算器

稀疏运算器

#include<stdio.h>
#include<stdlib.h>
#include<math.h> 
#define LEN sizeof(Poly)
typedef struct term{
	float xs;		//系数 
	int zs;		//指数 
	struct term *next;
}Poly,*Link;
int LocateElem(Link p, Link s, Link &q); 
void CreatePolyn(Link &p,int m);	//创建多项式 
void PrintPolyn(Link p);			//输出多项式			
int cmp(Link a, Link b);
Link AddPolyn(Link pa, Link pb);	//多项式相加 
Link SubPolyn(Link pa, Link pb);	//多项式相减 
Link Reverse(Link p);				//逆置多项式  
int main()
{
	Link P1,P2,P3;	//多项式 
	int L1,L2;		//多项式长度 
	char ch1;
	printf("输入第一个多项式的项数:");
	scanf("%d",&L1);
	CreatePolyn(P1,L1);
	printf("第一个多项式为:");
	printf("P1(X)=");
	PrintPolyn(P1);
	printf("输入第二个多项式的项数:");
	scanf("%d",&L2);
	CreatePolyn(P2,L2);
	printf("第二个多项式为:");
	printf("P2(X)=");
	PrintPolyn(P2); 
	printf("请输入要选择的运算(+ , -): ");
	getchar();		//吞回车 
	scanf("%c",&ch1);
	getchar();		//吞回车 
 	switch(ch1)
	 {
	 	case '+':
		{
	 		printf("P1(X)+P2(X)=");
	 		P3=AddPolyn(P1, P2);
			PrintPolyn(P3);
	 	}break;
	 	case '-':
		{
	 		printf("P1(X)-P2(X)=");
	 		P3=SubPolyn(P1, P2);
			PrintPolyn(P3);
	 	}break;
	 }
	return 0;
}
int LocateElem(Link p, Link s, Link &q)//遍历链表p,每一个结点与s比较指数,若相同,q指向相同指数项的结点,返回1,若不相同,根据s所指指数大小在链表p中的位置来确定q的指向结点,返回0 
{
	Link p1 = p->next;
	Link p2 = p;
	while(p1)
	{
		if(s->zs > p1->zs)
		{
			p1 = p1->next;
			p2 = p2->next;
		}
		else if(s->zs == p1->zs)
		{
			q = p1; 
			return 1;
		}
		else
		{
			q = p2;
			return 0;
		}
	}
	if(!p1)
	{
		q = p2;
		return 0;
	}
}
void CreatePolyn(Link &p,int m) ///创建带头结点的链表, 且无论按什么顺序输入,或是有相同指数项最终在多项式中都是升幂顺序
{
	Link s,q;
	int i;
	p=(Link)malloc(LEN);
	p->next=NULL;
	for(i=0;i<m;i++)
	{
		s=(Link)malloc(LEN);
		printf("输入系数和指数(以空格隔开):");
		scanf("%f %d", &s->xs, &s->zs);
		if(!LocateElem(p, s, q))
		{	//没有相同指数项
			s->next = q->next;
			q->next = s;
		}
		else q->xs+=s->xs;					//有相同指数项						
	}	
}
void PrintPolyn(Link p)//打印显示多项式 
{
	Link s;
	s = p->next;
	while(s)
	{
	        printf(" %.2f X^%d", s->xs, s->zs);
            s = s->next;
            if(s!=NULL)  
            if(s->xs>=0) 
			printf(" +");//若下一项系数为正,则打印'+',否则不打印 
	}
	printf("\n");
}
int cmp(Link a, Link b)//比较两结点指数大小,根据情况返回不同值 
{
	if (a->zs<b->zs) return  -1;
	else if(a->zs == b->zs) return  0;
	else return 1;
}
Link AddPolyn(Link pa, Link pb)//pa,pb均指向头结点 两个多项式相加得一个新多项式,并且返回新多项式的头结点的指针   
{
	Link newp, p, q, s, pc;
	float sum;
	p = pa->next; 
	q = pb->next;
	newp=(Link)malloc(LEN); //新多项式的头结点 
	pc = newp;	//pc指向新多项式的头结点
	while(p&&q)
	{
		switch(cmp(p, q))
		{
			case -1:// //若指数:p<q,则将p所指结点链入头结点为newp的链表中,且p向后遍历   
			{
				s = (Link)malloc(LEN); 
				s->xs = p->xs;
				s->zs = p->zs;
				pc->next = s;
				pc = s;
				p = p->next;
			}break;
			case 0://若比较两项的指数相等,则将两项系数相加后得到的项放入头结点为newp的链表中 ,且p,q同时向后遍历  
			{
				sum = p->xs+q->xs; 
				if(sum!=0.0)//若两项系数相加为0,则不放入头结点为newp的链表中
				{
					s = (Link)malloc(LEN);
					s->xs = sum;
					s->zs = p->zs;
					pc->next = s;
					pc = s;
				}
				p = p->next;
				q = q->next;
			}break;
			case 1://若指数:q<p,则将q所指结点链入头结点为newp的链表中,且q向后遍历    
			{
				s = (Link)malloc(LEN);
				s->xs = q->xs;
				s->zs = q->zs;
				pc->next = s;
				pc = s;
				q = q->next;
			}break;
		}
	}
	pc->next=p?p:q;//链入pa或pb的剩余项 
	return newp;//返回新多项式的头指针 
}
Link SubPolyn(Link pa, Link pb)///两个多项式相减得一个新多项式,并且返回新多项式的头结点的指针相减就是先将减数中每一项的系数变为负,再将两个多项式相加 
{
	Link newp, p, q, s, pc;
	float sum;
	newp=(Link)malloc(LEN); 
	pc = newp;
	p = pa->next; 
	q = pb->next;
	while(q)
	{// 将pb中每一项的系数变为负 
		q->xs=0-q->xs;
		q=q->next;
	}
	q=pb->next;
	while(p&&q)
	{
		switch(cmp(p, q))
		{
			case -1: 
			{
				s = (Link)malloc(LEN); 
				s->xs = p->xs;
				s->zs = p->zs;
				pc->next = s;
				pc = s;
				p = p->next;
			}break;
			case 0: 
			{
				sum = p->xs-q->xs; 
				if(sum!=0.0)
				{
					s = (Link)malloc(LEN);
					s->xs = sum;
					s->zs = p->zs;
					pc->next = s;
					pc = s;
				}
				p = p->next;
				q = q->next;
			}break;
			case 1: 
			{
				s = (Link)malloc(LEN);
				s->xs= q->xs;
				s->zs = q->zs;
				pc->next = s;
				pc = s;
				q = q->next;
			}break;
		}
	}
	pc->next=p?p:q;
	return newp;
}
Link Reverse(Link p)///用头插法逆置链表,使多项式由降幂变成升幂顺序或使多项式由升幂变成降幂顺序
{
	Link head=p; 
	Link q1,q2;
    q2=head->next;
    head->next=NULL;//断开头结点与第一个结点 
    while(q2)
    {
        q1=q2;      
        q2=q2->next; 
		q1->next=head->next; //头插 
		head->next=q1;  
    }      
    return head;//返回链表逆置后的头结点 
}

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值