杭电 2068(错排加组合)

来源:互联网 发布:司法行政人员 知乎 编辑:程序博客网 时间:2024/05/22 14:17

对于组合有种方法。第一种很容易超出__int64的范围.
错误代码

#include<stdio.h>__int64 nn(int n)  //n应该不能超过20{    __int64 i,s = 1;    for(i = 1;i <= n; i++)        s *= i;    return s;}int main(){    __int64 a[30];    a[1] = 0;    a[2] = 1;    int i;    for(i = 3;i < 28; i++)        a[i] = (a[i-1] + a[i-2])*(i-1);    int n;    while(scanf("%d",&n) != EOF)    {        if(n == 0)            break;        __int64 sum = 1;        for(i = 1;i <= n/2; i++)            sum = sum + nn(n)/(nn(n-i)*nn(i))*a[i];        printf("%I64d\n",sum);    }    return 0;}

法二:

正确代码

#include<stdio.h>__int64 nn(int n,int m){    int a = 1;    for(int i = 1;i <= m; i++)    {        a = a*(n-i+1); // 可以先记住,慢慢理解。        a /= i;    }    return a;}int main(){    __int64 a[30],sum;    int n,i;    a[1] = 0;    a[2] = 1;    for(i = 3;i <= 12; i++)        a[i] = (i-1)*(a[i-1] + a[i-2]);    while(scanf("%d",&n) != EOF)    {        if(n == 0)            break;        sum = 1;        for(i = 1;i <= n/2; i++)            sum = sum + nn(n,i)*a[i];        printf("%I64d\n",sum);    }    return 0;}
0 0