一元多项式加减乘求导微分简单运算

主要代码

/****************************************************
  @title: 数据结构实验
  @name:<试验> 一元多项式简单计算器
  @object:
      [实验目的]
           单链表的存储结构及其基本操作的实现 
      [实验提示]
          1. 在linklist.h中实现单链表的基本操作 
          2.在Polynomial.h中实现了一元多项式的基本操作
          3.在Polynomial.h中编写代码,进行测试
          4.在MutualPlat.h中编写一交互式的运行平台
  @include:
      ds.h [*]
          单链表的实现 
  @author: wangheng
  @date: 3 / 4 / 2017
  ***************************************************/
#define  Number  2.0

#include <stdio.h>
#include <stdlib.h>
#include "MutualPlat.h"

int main()
{
    printf("是否进行运算(Y/N): ");
    char command;
    polynomial P1;
    polynomial P2;
    read(command);
    while(command == 'Y')
    {
        run();           //运行程序
        printf("是否进行运算(Y/N): ");
        readM(command);
    }
    return 0;

}
/*
   Name: LinkList.h
   Author: WangHeng
   Data: 3 / 4 / 2017 ;
   Description: 1)建立一个交互式的平台,实现创建和运行运算的功能
                2)调用一元多项式的头文件Polynomial.h,进行调用

*/

#ifndef MUTUALPLAT_H_INCLUDED
#define MUTUALPLAT_H_INCLUDED

//////////////////////////////////////////
//应用的头文件
#include <math.h>
#include <stdio.h>
#include <stdlib.h>

#include "ds.h"
#include "Polynomial.h" 
///////////////////////////////////////////

//输入函数:调用一元多项式的CreatPolyn()函数进行输入
void input (polynomial& P)
{
//1)输入第一个一元多项式各项
    printf("\n输入一个一元多项式的各项系数和指数[当输入的系数和指数为:(0 0) 时,输入结束]\n");
    CreatPolyn(P);
    //打印输出一元多项式P1
    PrintPolyn(P);
    //输出一元多项式的项数
    printf("一元多项式的项数: %d\n",PolynLength(P));
}

//运算方法清单
void CaculateMenu()
{
    printf("选择你想进行的运算方法:[A](add),[S](substract),[M](multiply),\n[D](Derivative),[C](Calculus)---");

}

//输入运算命令
Status GetCommand(char& way)
{
    printf("\n运算方法为:");
    readM(way);
    printf("\n");
    return OK;
}
//交互式运行平台
void run( )
{
    char way;
    polynomial P1;
    polynomial P2;
    //3)选择运算方法
    CaculateMenu();
    GetCommand(way);
    switch(way)
    {
    case 'A' :          //两个一元多项式的和
    case 'a':
        input(P1);          //输入一元多项式的各项
        input(P2);
        AddPolyn(P1,P2);
        //打印输出和
        printf("打印输出和:\n");
        PrintPolyn(P1);
        break;
    case  'S' :       //两个一元多项式的差
    case 's':
        input(P1);          //输入一元多项式的各项
        input(P2);

        SubtractPolyn(P1,P2);
        //打印输出差
        printf("打印输出差:\n");
        PrintPolyn(P1);
        break;
    case  'M' :        //两个一元多项式的积
    case 'm':
        input(P1);          //输入一元多项式的各项
        input(P2);

        MultiplyPolyn(P1,P2);   
        //打印输出积 
        printf("打印输出积:\n"); 
        PrintPolyn(P1);
        break;
    case 'D':
    case 'd':
        input(P1);          //输入一元多项式的各项

        Derivative(P1);
        //打印输出导数
        printf("打印输出 P1 导数: \n");
        PrintPolyn(P1);
        break;
    case 'C':
    case 'c':
        input(P1);          //输入一元多项式的各项

        Calculus (P1);
        //打印输出积分
        printf("打印输出 P1 积分: \n");
        PrintPolyn(P1);
        break;
    default:
        printf("输入的运算方法错误:");
    }
    //销毁一元多项式
    DestroyPolyn(P1);   
}

#endif  // MUTUALPLAT_H_INCLUDED
/* 
   Name: Polynomial.h
   Author: WangHeng
   Data: 3 / 4 / 2017 ;
   Description: 1)调用LinkList.h头文件,用实现链表的各种功能
                  来创建一元多项式的各种算法实现;
                2)调用ds.h来进行基本的输入输出等操作
                3)头文件Polynomial.h主要完成一元多项式的各种操作

*/

#ifndef POLYNOMIAL_H_INCLUDED
#define POLYNOMIAL_H_INCLUDED

#ifndef ElemType
#define ElemType int //数据类型默认为int
#define ELEMTYPE_TAG
#endif 

#include "ds.h"
#include "LinkList.h"

typedef LinkList polynomial;

/*************************************************************************
*  基本操作的函数原型说明
*************************************************************************/

//输入m项的系数和指数,建立表示一元多项式的有序链表P
void CreatPolyn(polynomial &P, int m);

//销毁一元多项式P
void DestroyPolyn(polynomial &P);

//打印输出一元多项式P
void PrintPolyn(polynomial P);

//返回一元多项式P中的项数
int PolynLength(polynomial P);

//完成多项式相加运算,即:Pa = Pa + Pb,并销毁一元多项式Pb
void AddPolyn(polynomial &Pa,polynomial &Pb);

//完成多项式相减运算,即:Pa = Pa - Pb,并销毁一元多项式Pb
void SubtractPolyn(polynomial &Pa,polynomial &Pb);

//完成多项式相乘运算,即:Pa = Pa * Pb,并销毁一元多项式Pb
void MultiplyPolyn(polynomial &Pa,polynomial &Pb);

//完成多项式的求导函数,即:Pa = Pa' 
void Derivative(polynomial &P);

//完成多项式的积分函数, Pa = ∫Pa' dx 
void Calculus (polynomial &P);


/*********************************************************************
* 基本操作的算法描述和实现
*********************************************************************/

//创建一元多项式P,当输入的指数和系数都为0时,输入结束。
// 一元多项式就被创建 。   
void CreatPolyn(polynomial &P)
{

    InitList(P);
    printf(" \n输入系数和指数:\n");
    read(P->coef,P->expn);     //输入系数和指数
    //-------------------TODO------------------//
    while(P->coef!=0||P->expn!=0){
        ListInsert(P, 1, P->coef, P->expn);
        printf(" \n输入系数和指数:\n");
        read(P->coef,P->expn); 
    }
    //------------初始化表达式,不断输入系数和指数,直到读到0,0为止----------//

}

//销毁一元多项式P
void DestroyPolyn(polynomial &P)
{
    DestroyList(P);   //调用LinkList.h头文件中的销毁函数

}

//打印输出一元多项式P
void PrintPolyn(polynomial P)
{
    printf("打印一员多项式的各系数和指数\n ");
    UnionList(P);   //用来合并在一元多项式计算结果中具有相同指数的项
    PrintLinkList(P);   
}

//返回一元多项式P中的项数
int PolynLength(polynomial P)
{
    return ListLength(P);    //合并后的一元多项式的项数
}

//完成多项式相加运算,即:Pa = Pa + Pb,并销毁一元多项式Pb
void AddPolyn(polynomial &Pa,polynomial &Pb)
{
    UnionList(Pa);   //合并一元多项式中具有
    UnionList(Pb);   //相同指数的项

    for (int i=1; i<=ListLength(Pb); i++)
    {
        float co;
        int ex;
        GetElem(Pb, i, co, ex);
        if(LocateElem(Pa, ex) > 0)    //判断Pa中是否具有Pb中相同指数的项,
        {                             //如果有,进行相加 
            int j = LocateElem(Pa, ex);   //记录Pa中相同项的位置
            int k = 0;
            polynomial s = Pa;
            while(k < j)     //查找这一位置
            {
        //-------------------TODO------------------//
             s=s->next;
             k++;
            }
            s->coef += co;    //系数项相加

        }
        else       //不存在相同的指数,将Pb中的该项插入Pa
            ListInsert(Pa, 1, co, ex);
    }
    DestroyList(Pb);    //销毁Pb  
}


//完成多项式相减运算,即:Pa = Pa - Pb,并销毁一元多项式Pb
void SubtractPolyn(polynomial &Pa,polynomial &Pb)
{
    UnionList(Pa);   //合并一元多项式中具有
    UnionList(Pb);   //相同指数的项

    for (int i=1; i<=ListLength(Pb); i++)
    {
        float co;
        int ex;
        GetElem(Pb, i, co, ex);
        if(LocateElem(Pa, ex) > 0)    //判断Pa中是否具有Pb中相同指数的项,
        {                             //如果有,进行相加 
            int j = LocateElem(Pa, ex);   //记录Pa中相同项的位置
            int k = 0;
            polynomial s = Pa;
            while(k < j)     //查找这一位置
            {
        //-------------------TODO------------------//
             s=s->next;
              k++;
            }
            s->coef -= co;   
                }
        else       //不存在相同的指数,将Pb中的该项插入Pa
            ListInsert(Pa, 1, co, ex);
    }
    DestroyList(Pb);    //销毁Pb
}

//完成多项式相乘运算,即:Pa = Pa * Pb,并销毁一元多项式Pb
void MultiplyPolyn(polynomial &Pa,polynomial &Pb)
{
    UnionList(Pa);   //合并一元多项式中具有
    UnionList(Pb);   //相同指数的项

    for (int i=1; i<=ListLength(Pb); i++)
    {
        float co;
        int ex;
        GetElem(Pb, i, co, ex);
        if(LocateElem(Pa, ex) > 0)    //判断Pa中是否具有Pb中相同指数的项,
        {                             //如果有,进行相加 
            int j = LocateElem(Pa, ex);   //记录Pa中相同项的位置
            int k = 0;
            polynomial s = Pa;
            while(k < j)     //查找这一位置
            {
        //-------------------TODO------------------//
             s=s->next;
              k++;
            }
            s->coef *= co;    //系数项相加

        }
        else       //不存在相同的指数,将Pb中的该项插入Pa
            ListInsert(Pa, 1, co, ex);
    }
    DestroyList(Pb);    //销毁Pb
}


//完成多项式的求导函数,即:Pa = Pa' 
void Derivative(polynomial &P)
{
    polynomial Pb=P->next;
    float co;
    int ex;
    while(Pb)
    {
        co=(Pb->coef) * (Pb->expn);
        ex=Pb->expn-1;
        Pb->coef=co;
        Pb->expn=ex;
        Pb=Pb->next;
    }
    DestroyList(Pb);    //销毁Pb
}

//完成多项式的积分函数, Pa = ∫Pa' dx 
void Calculus (polynomial &P)
{
    polynomial Pb=P->next;
    float co;
    int ex;
    while(Pb)
    {
        ex=Pb->expn+1;
        co=Pb->coef/ex;
        Pb->coef=co;
        Pb->expn=ex;
        Pb=Pb->next;
    }
    DestroyList(Pb);    
}

#ifdef ELEMTYPE_TAG
#undef ElemType
#undef ELEMTYPE_TAG
#endif

#endif  // POLYNOMIAL_H_INCLUDED
/*
   Name: LinkList.h
   Author: WangHeng
   Data: 3 / 4 / 2017 ;
   Description:    引用老师的链表结构,在此基础上进行修改,
                   使其适合一元多项式.
*/
#ifndef LINKLIST_H_INCLUDED
#define LINKLIST_H_INCLUDED

#include "ds.h"

#ifndef ElemType
#define ElemType int //数据类型默认为int
#define ELEMTYPE_TAG
#endif 

/****************************************************************
*  多项式的存储结构定义
****************************************************************/

typedef struct  LNode{
    float coef;  //系数
    int expn;  //指数
    struct  LNode *next;
} LNode,*LinkList; 

/*************************************************************************
*  基本操作的函数原型说明
*************************************************************************/

//创建并初始化为空表 
Status InitList(LinkList &L);

//销毁整个表(从此之后不再可用) 
Status DestroyList(LinkList &L);

//将表L置空 
Status ClearList(LinkList &L);

//判断表L是否为空表 
bool ListEmpty(LinkList L);

//求表L的长度 
int ListLength(LinkList L);

//取表L中的第i个元素,并用e返回. 操作成功返回OK,失败时返回ERROR 
Status GetElem(LinkList L, int i, float &co, int &ex);

template <typename T> bool equal(T a, T b)
{
    return a==b;
}
//在表L中定位元素e首次出现的位置. 操作成功返回位序,失败时返回0 
//    compare(a,b) 为比较函数,匹配时返回true,否则返回false 
//                 这里默认使用equal进行比较 
int LocateElem(LinkList L, int ex, 
      bool (*compare)(int ,int )=equal<int >);

//在表L中插入第i个元素e. 操作成功返回OK,失败时返回ERROR
Status ListInsert(LinkList &L, int i, float co , int ex);

//删除表L中第i个元素,结果用e返回. 操作成功返回OK,失败时返回ERROR 
Status ListDelete(LinkList &L, int i, float &co, int &ex);

//遍历表L,对每个元素调用visit(x). 
Status ListTraverse(LinkList L, Status (*visit)(float,int));

//合并一元多项式中相同的幂的项
void  UnionList(LinkList &L);

/**********************************************************
*  单链表的基本操作的实现
***********************************************************/

//创建并初始化为空表 
Status InitList(LinkList &L)
{
    L = (LNode*)malloc(sizeof(LNode));
    if(!L)  exit(DS_OVERFLOW);

    L->next = NULL;
    return OK;
}

//销毁整个表(从此之后不再可用) 
Status DestroyList(LinkList &L)
{
    LinkList p ;
    while (L )
    {
        p = L;
        L = L->next;
        free(p);
    }

    return OK;
}

//将表L置空 
Status ClearList(LinkList &L)
{
    LinkList p = L->next;
    LinkList s ;
    while (p )
    {
        s = p;
        p = p->next;
        free(s);
    }

    return OK;
}

//判断表L是否为空表 
bool ListEmpty(LinkList L)
{
    if(L->next == NULL)
        return TRUE;
    else 
        return FALSE;
}

//求表L的长度 
int ListLength(LinkList L)
{
    int j = 0;
    LinkList p = L;
    while (p ->next != NULL)
    {
        j++;
        p = p->next;        
    }
    return j;
}

//取表L中的第i个元素,并用返回. 操作成功返回OK,失败时返回ERROR 
Status GetElem(LinkList L, int i, float &co, int &ex)
{
    if(i > ListLength(L) || i <= 0)    return ERROR;
    int j = 0;
    LinkList p = L;
    while(p&&j < i)
    {
        p = p->next;
        j++;
    }
    if(p && j == i)
    {
        co = p->coef;
        ex = p->expn;
        return ex;
    }
    else
        return ERROR;

    //-------------------------------------
}

//在表L中定位元素e首次出现的位置. 操作成功返回位序,失败时返回0 
//    compare(a,b) 为比较函数,匹配时返回true,否则返回false 
int LocateElem(LinkList L, int ex, bool (*compare)(int , int))
{
    // TODO (#1#): 在表中定位元素ex,用compare(a,b)匹配元素
    LinkList p;
    int j;

    p = L->next; j = 0;
    while(p) {
        j++;
        if( compare(p->expn,ex) )  return j;
        p=p->next;
    }
    return 0;
    //-------------------------------------
}

//在表L中插入第i个元素e. 操作成功返回OK,失败时返回ERROR
Status ListInsert(LinkList &L, int i, float co, int ex)
{
    // TODO (#1#): 在链表中插入元素
    LinkList p = L;
    int j = 0;    
    while(p && j < i - 1)   //注意判断条件
    {
        p = p->next ;
        j++;
    }

    if(p && j == i-1)
    {
        LinkList s = (LNode *)malloc(sizeof(LNode));   //分配插入的结点
        if(!s)  exit(DS_OVERFLOW);

    //-------------------TODO------------------//
       s->coef=co;
       s->expn=ex;
        s->next = p->next;
        p->next  = s;
        return OK;
    }
    else 
        return ERROR;
    //-------------------------------------

}

//删除表L中第i个元素,结果用e返回. 操作成功返回OK,失败时返回ERROR 
Status ListDelete(LinkList &L, int i, float &co, int &ex)
{
    // TODO (#1#): 在链表中删除元素
    LinkList p = L;
    int j = 0;    
    while(p && j < i-1 )   //注意判断条件
    {
        p = p->next ;
        j++;
    }
    if(p && j == i-1)
    {
        LinkList s = p->next;
        p->next = s->next;
    //-------------------TODO------------------//
        co= s->coef;
        ex= s->expn;
        free(s);
        return OK;
    }
    else 
        return ERROR;   
    //-------------------------------------
}

//遍历表L,对每个元素调用visit(x). 
Status ListTraverse(LinkList L, Status (*visit)(float,int))
{
    LinkList p = L->next;
    while ( p ) {
        if ( visit(p->coef,p->expn)==ERROR )  return ERROR;
        p = p->next;
        printf("+\t");
    }
    return OK;
    //--------------------------------------
}


//合并一元多项式中相同的幂的项
void  UnionList(LinkList &L)
{
    int ex1,ex2;
    float co0,co1,co2;
    LinkList p = L;
    for(int i = 1; i < ListLength(L); i++)
    {
        GetElem(L, i, co1, ex1);
        if(co1 == 0)
            ListDelete(L, i, co1, ex1);
        for (int j = i+1; j < ListLength(L)+1; j++)
        {
            GetElem(L, j, co2, ex2);
            if(co2 == 0)
                ListDelete(L, j, co2, ex2);
            else if(ex2 == ex1)
            {
                co0 = co1 + co2;      //解决在同一一元多项式中有相同系数的情况
                ListDelete(L, j, co2, ex2);
                ListDelete(L, i, co1, ex1);
                ListInsert(L, i, co0, ex1);
            }                
        }
    }
}
/******************************************************
*  在程序设计时,所需的小型函数
*****************************************************/
// 打印数据元素的方法 
Status print(float co,int ex )
{
    printf("%.2f X^%2d  \t",co,ex);
    return OK;
}

//打印链表内容 
void PrintLinkList(LinkList L)
{
    ListTraverse(L,print); //遍历链表并print()每个元素 
    printf("\n");
}

bool equal(int a, int b)
{
    return a==b;
}

#ifdef ELEMTYPE_TAG
#undef ElemType
#undef ELEMTYPE_TAG
#endif

#endif  // LINKLIST_H_INCLUDED

演示效果:

这里写图片描述
这里写图片描述
这里写图片描述
这里写图片描述
这里写图片描述

项目下载链接https://pan.baidu.com/s/1kUUEqph

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章