多项式相乘求组合数RC(n,r)——链表实现

来源:互联网 发布:淘宝假冒伪劣产品 编辑:程序博客网 时间:2024/05/16 15:56

设集合S={n1*e1, n2*e2, ... nt*et}, n1 + n2 +...+nt = n, 从S中任取r个,求其组合数RC(n, r)。

设多项式

 

则RC(n,r)就是多项式中xr的系数, 即  RC(n, r) = ar。

根据上述方法,编程实现:求任意的从S中任取r个的组合数RC(n,r),且输出ai(i = 1, 2...r)。

解决思路:

1. 每个多项式用一个链表表示。多项式的系数和幂用链表的节点表示。

2. 多项式相乘即为对链表每个节点的遍历和计算。

编程实现如下:

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

typedef int datatype;

typedef struct node
{
    datatype coe; //多项式的系数 
    datatype power; //多项式幂 
    struct node *next;    
}listnode, *linklist; 

linklist linklist_create()
{
    linklist L;
    if ((L = (linklist)malloc(sizeof(listnode))) == NULL)
    {
        printf("malloc error \n");
        return NULL;   
    }
    L->next = NULL;
    return L;
}
int linklist_insert(linklist L, datatype x, datatype y)
{
    linklist p, q = L;
    
    while (q->next != NULL)
    {
        q = q->next;  
    }
    p = (linklist)malloc(sizeof(listnode));
    p->coe = x;  //系数 
    p->power = y;   //幂 
    p->next = q->next;
    q->next = p;   
    return 0;
}
int linklist_is_empty(linklist L)
{
    linklist p = L;
    
    if (p->next == NULL)
       return 1;
    else
       return 0;   
}
int linklist_show(linklist L)
{
    linklist p = L->next;  
    while (p != NULL)
    {
          printf("%d*x<%d>  ", p->coe, p->power);
          p = p->next;
    }
    printf("\n\n");
    return 0;
}
int linklist_show_r(linklist L, int k)
{
    linklist p = L->next;
    int i = 0;
    for (i = 0; i < k; i++)
    {
        p = p->next;
    }   
    printf("%d\n", p->coe);
    return 0;
}
int linklist_clear(linklist L)
{
    linklist p = L;
    while (L->next)
    {
        p = L->next;
        L->next = p->next;
        free(p);
        p = NULL; 
    }
    return 0;
}
int linklist_length(linklist L)
{
    linklist p = L->next;
    int len = 0;   
    while (p != NULL)
    {
        len ++;
        p = p->next;
    }
    return --len;
}
int multinomial_multipty(linklist L, linklist MUL)
{
    int len = 0;
    len = linklist_length(L) + linklist_length(MUL);
    int tempcoe[100] = {0}, temppower[100] = {0};     
    linklist p = MUL->next, q = L->next;
    int temp = 0;
    int i = 0;
      
    i = 0;
    while (i <= len)
    {
        tempcoe[i] = 0;
        temppower[i] = i; 
        i++;
    }
    while (p != NULL)    //多项式相乘 
    {
        q = L->next;
        while (q != NULL)     
        {
           temp = q->power + p->power;
           tempcoe[temp] += q->coe * p->coe;
           
           q = q->next;
        } 
        p = p->next;
    }
    p = q = NULL;
    linklist_clear(L);
    for (i = 0; i <= len; i++)  //重新赋值给链表L 
    {
        linklist_insert(L, tempcoe[i], temppower[i]);
    } 
    return 0;
}

#define N 100

int main(void)
{
    int t = 0; //元素类型数 
    int x[N] = {0};     //元素 
    int m[N] = {0};     //元素个数 
    int i = 0, j = 0;
    int r = 0, n = 0;
    linklist L, TL;
    L = linklist_create();
    TL = linklist_create();
    linklist_insert(L, 1, 0);
    printf("           程序计算结果如下       \n\n\n");
    printf("请输入元素类型数:");
    scanf("%d", &t); 
    printf("\n请输入各元素:");  
    for (i = 0; i < t; i++)
    {
        scanf("%d", &x[i]);
    }
    printf("\n请输入相应的元素个数:");
    for (i = 0; i < t; i++)
    {
        scanf("%d", &m[i]);
        n += m[i];
    } 
    printf("\n请输入r: ");
    scanf("%d", &r);
    printf("\n输入的多项式为: \n"); 
    for (i = 0; i < t; i++)
    {
       for (j = 0; j <= m[i]; j++)
       {
           linklist_insert(TL, 1, j);              
       }
       linklist_show(TL);
       multinomial_multipty(L, TL);
       linklist_clear(TL);      
    }
    printf("\n相乘后的多项式为: ");
    linklist_show(L);
    printf("组合数RC(n, r) = RC(%d, %d) = ", n, r);
    linklist_show_r(L, r);
    printf("\n");
    system("pause()");
    return 0;
}