计算多项式

本文详细介绍了如何使用链表实现一元多项式的计算,并针对特定情况进行了优化,包括处理系数为-1的项、所有输入为0的情况以及避免在阶数较高的多项式剩余项系数为0时不建立新结点的问题。

http://acm.buaa.edu.cn/contest/185/problem/B/

一元多项式的计算用链表实现,本题需要注意的是:

1.系数为-1的项只输出负号,例如1-x^4+2x^8-3x^10+15x^14+4x^18

2.当所有输入均为0时,输出结果0

3.如果阶数较多的那个多项式剩下的项的系数为0不要建立新的结点

否则会输出0x^160x^17

#include <cstdio>
#include <cstdlib>
#define MAX 502

typedef struct array
{
	double coef;
	int exp;
} PolyArray[MAX];

typedef struct pnode
{
	double coef;
	int exp;
	struct pnode *next;
}  PolyNode;
void DispPoly(PolyNode *L)
{
	bool first=true;
	PolyNode *p=L->next;
	while (p!=NULL)
	{
		if (first)
			first=false;
		else if (p->coef>0)
			printf("+");
		if (p->exp==0)
			printf("%g",p->coef);
		else if (p->exp==1)
		{
		    if (p->coef==1)
                printf("x");
                else if (p->coef==-1)
                printf("-x");
                else
                printf("%gx",p->coef);
		}
                else
		{
		    if (p->coef==1)
                printf("x^%d",p->exp);
                else if (p->coef==-1)
                printf("-x^%d",p->exp);
                else
                printf("%gx^%d",p->coef,p->exp);
		}

		p=p->next;
	}
	printf("\n");
}
void DestroyList(PolyNode *&L)
{
	PolyNode *p=L,*q=p->next;
	while (q!=NULL)
	{
		free(p);
		p=q;
		q=p->next;
	}
	free(p);
}
void CreateListR(PolyNode *&L,PolyArray a,int n)
{
	PolyNode *s,*r;int i;
	L=(PolyNode *)malloc(sizeof(PolyNode));
	L->next=NULL;
	r=L;
	for (i=0;i<n;i++)
	{
		s=(PolyNode *)malloc(sizeof(PolyNode));
		s->coef=a[i].coef;
		s->exp=a[i].exp;
		r->next=s;
		r=s;
	}
	r->next=NULL;
}

void Sort(PolyNode *&head)
{
	PolyNode *p=head->next,*q,*r;
	if (p!=NULL)
	{
		r=p->next;
		p->next=NULL;
		p=r;
		while (p!=NULL)
		{
			r=p->next;
			q=head;
			while (q->next!=NULL && q->next->exp<p->exp)
				q=q->next;
			p->next=q->next;
			q->next=p;
			p=r;
		}
	}
}
void Add(PolyNode *ha,PolyNode *hb,PolyNode *&hc)
{
	PolyNode *pa=ha->next,*pb=hb->next,*s,*tc;
	double c;
	hc=(PolyNode *)malloc(sizeof(PolyNode));
	tc=hc;
	while (pa!=NULL && pb!=NULL)
	{
	        if     (pa->exp>pb->exp)
		{
			s=(PolyNode *)malloc(sizeof(PolyNode));
			s->exp=pa->exp;s->coef=pa->coef;
			tc->next=s;tc=s;
			pa=pa->next;
		}
		else if (pa->exp<pb->exp)
		{
			s=(PolyNode *)malloc(sizeof(PolyNode));
			s->exp=pb->exp;s->coef=pb->coef;
			tc->next=s;tc=s;
			pb=pb->next;
		}
		else
		{
			c=pa->coef+pb->coef;
			if (c!=0)
			{
				s=(PolyNode *)malloc(sizeof(PolyNode));
				s->exp=pa->exp;s->coef=c;
				tc->next=s;tc=s;
			}
			pa=pa->next;
			pb=pb->next;
		}
	}
	if (pb!=NULL) pa=pb;//将阶数较多的那个多项式赋给pa
	while (pa!=NULL)
	{
		        c=pa->coef;
			if (c!=0)//如果剩下的项的系数为0就不建立新的结点
			{
			    s=(PolyNode *)malloc(sizeof(PolyNode));
		            s->exp=pa->exp;s->coef=pa->coef;
                            tc->next=s;tc=s;
			}

		        pa=pa->next;
	}
	tc->next=NULL;
}

int main()
{
    int n,m,i,j;
    while (~scanf("%d%d",&n,&m))
    {
        int g,h;
        g=n+1;
        h=m+1;
        PolyNode *ha,*hb,*hc;
        PolyArray a,b;
    for(i =0; i<MAX;i++ )
    {
        a[i].exp=0;
        a[i].coef=0;
    }
    for(j =0; j<MAX;j++ )
    {
        b[j].exp=0;
        b[j].coef=0;
    }
    for(i =0; i<n+1;i++ )
    {
        scanf("%lf",&a[i].coef);
    }
    for(j=0; j<m+1;j++ )
    {
        scanf("%lf",&b[j].coef);
    }
    for(i =0; i<n+1;i++ )
    {
        a[i].exp=i;
    }
    for(j =0; j<m+1;j++ )
    {
        b[j].exp=j;
    }
        CreateListR(ha,a,g);
	CreateListR(hb,b,h);
	Sort(ha);
	Sort(hb);
	Add(ha,hb,hc);
	if(hc->next!=NULL)
	{
	    DispPoly(hc);
	}
	else
	 printf("0\n");
	DestroyList(ha);//要实现多次输入输出必须在每轮结束后销毁链表
	DestroyList(hb);
	DestroyList(hc);
    }
}



### 多项式曲线长度的数学方法 计算多项式曲线的长度通常涉及积分计算,其基本思想是利用微分几何中的弧长公式。对于给定多项式函数 $ y = f(x) $,其在区间 $[a, b]$ 上的弧长 $ L $ 可以通过以下公式计算: $$ L = \int_a^b \sqrt{1 + \left( \frac{dy}{dx} \right)^2} \, dx $$ 其中,$\frac{dy}{dx}$ 是多项式函数的导数,表示曲线在任意点处的斜率。对于多项式函数,导数可以通过常规的微分运算求得,而积分则可以通过解析方法或数值积分方法计算。 ### 线性多项式的情况 以线性多项式 $ y = mx + c $ 为例,其导数为常数 $ m $,因此弧长公式可以简化为: $$ L = \int_a^b \sqrt{1 + m^2} \, dx = \sqrt{1 + m^2} \cdot (b - a) $$ 这种情况下,可以直接通过公式计算出曲线的长度。 ### 高次多项式的情况 对于高次多项式,例如二次多项式 $ y = ax^2 + bx + c $,其导数为 $ \frac{dy}{dx} = 2ax + b $,代入弧长公式后,积分可能无法用初等函数表示,这时需要采用数值积分方法进行计算。常用的数值积分方法包括梯形法则、辛普森法则等。 #### 示例代码:数值积分计算二次多项式曲线长度 以下是一个使用 MATLAB 进行数值积分的示例代码,计算二次多项式 $ y = ax^2 + bx + c $ 在区间 $[x_1, x_2]$ 上的弧长: ```matlab % 定义多项式系数 a = 1; b = 2; c = 3; % 定义导数函数 dy_dx = @(x) 2*a*x + b; % 定义被积函数 integrand = @(x) sqrt(1 + (dy_dx(x)).^2); % 定义积分区间 x1 = 0; x2 = 1; % 使用数值积分计算弧长 L = integral(integrand, x1, x2); % 输出结果 disp(['The length of the polynomial curve is: ', num2str(L)]); ``` ### 非解析解的处理 对于某些高次多项式,其导数的平方可能导致积分无法用解析形式表示。在这种情况下,必须依赖数值积分工具来求解。MATLAB 提供了 `integral` 函数,可以高效地处理这类问题。 ### 多项式曲线的参数化表示 在某些应用中,多项式曲线可能以参数化形式给出,例如 $ x(t) $ 和 $ y(t) $。此时,弧长公式变为: $$ L = \int_{t_1}^{t_2} \sqrt{\left( \frac{dx}{dt} \right)^2 + \left( \frac{dy}{dt} \right)^2} \, dt $$ 这种方法适用于更复杂的曲线表示,如贝塞尔曲线或样条插值。 ### 结论 综上所述,计算多项式曲线长度的核心在于应用弧长公式,并根据多项式的具体形式选择合适的积分方法。对于低次多项式,可以尝试解析积分;而对于高次多项式或复杂形式的曲线,则推荐使用数值积分方法。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值