您的位置:首页 > 理论基础 > 计算机网络

C - Binary Stirling Numbers解题报告(来自网络)

2012-04-17 19:40 393 查看
C - Binary Stirling Numbers
Time Limit:1000MS Memory Limit:10000KB 64bit IO Format:%I64d
& %I64u
Submit Status Practice POJ
1430

Description

The Stirling number of the second kind S(n, m) stands for the number of ways to partition a set of n things into m nonempty subsets. For example, there are seven ways to split a four-element set into two parts:

{1, 2, 3} U {4}, {1, 2, 4} U {3}, {1, 3, 4} U {2}, {2, 3, 4} U {1}

{1, 2} U {3, 4}, {1, 3} U {2, 4}, {1, 4} U {2, 3}.


There is a recurrence which allows to compute S(n, m) for all m and n.

S(0, 0) = 1; S(n, 0) = 0 for n > 0; S(0, m) = 0 for m > 0;

S(n, m) = m S(n - 1, m) + S(n - 1, m - 1), for n, m > 0.


Your task is much "easier". Given integers n and m satisfying 1 <= m <= n, compute the parity of S(n, m), i.e. S(n, m) mod 2.

Example

S(4, 2) mod 2 = 1.


Task

Write a program which for each data set:

reads two positive integers n and m,

computes S(n, m) mod 2,

writes the result.

Input

The first line of the input contains exactly one positive integer d equal to the number of data sets, 1 <= d <= 200. The data sets follow.

Line i + 1 contains the i-th data set - exactly two integers ni and mi separated by a single space, 1 <= mi <= ni <= 10^9.

Output

The output should consist of exactly d lines, one line for each data set. Line i, 1 <= i <= d, should contain 0 or 1, the value of S(ni, mi) mod 2.

Sample Input

1
4 2


Sample Output

1


过了这题,我很兴奋,很久都没有这种感觉了。真的很舒服,不过这题我想了很久,数论的类型,的确有些难想。

好了,不多说了,说说这题到底怎么个解法吧!此题解法都是自己一步一步推过来的,希望对大家有启发。

首先由于%2的操作,我想到了f(n,m) = s(n,m)%2,假设一个f函数。于是s(n,m) = m * s(n-1,m)+ s(n-1,m-1) ==>

f(n,m) = s(n-1,m-1) (m为偶数); f(n,m) = f(n-1,m) + f(n-1,m-1)(m为奇数)。这样就可以将m给去掉,最后就是计算f(n,m)%2即可,必须想到怎么样得到f(n,m)。

怎么得到呢?这一步是比较难想的。我用递推,推了很久都不行,因为n,m实在太大了。于是我想到了先画个图,希望通过图形来表示它们的递推关系,果真很管用,我找到了。x轴表示n方向,y轴表示m方向,那么我可以看出其实就找从(0,0)点到(n,m)点有多少条路径,就是f(n,m) 的值了。如果大家将图画出来后,然后通过上式去找,我相信会找到公式了,最后其实得到的是一个组合 求出 f(n,m) = C(n-m, (m-1)/2)。不会很难找,大家就画画吧。

简化就是求C(n,m)%2 ,就是求C(n,m)的奇偶了。怎么求呢,这又是一个难点。C(n,m) = m!/(n!*(m-n)!){这个大家都知道的},这里就是要靠数学感觉了,我直接就想到了肯定和2因子有关,于是就得到这样一个结论,如果分子2因子的个数= 分母2因子的个数,那么就为奇数;否则就为偶数.。大家多想想,如果有些疑问,给我留言,现在就不在这里多说了。

相信大家如果看来上面且明白后,这个题AC就是2分钟内了。

#include <iostream>
using namespace std;

__int64 f(__int64 x)//计算x! 2的因子数目
{
__int64 t =0;
while(x)
{
x /= 2;
t += x;
}
return t;
}
int main()
{
int cas;
__int64 n,m;
scanf("%d",&cas);
while(cas)
{
cas --;
cin>>n>>m;
n -= m;
m = (m-1)/2;
if(f(n+m) == f(n)+ f(m))
printf("1\n");
else
printf("0\n");
}
return 0;
}
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: