您的位置:首页 > 运维架构

UVa 861 Little Bishops(棋盘放棋)

2016-07-14 17:07 651 查看
UVa 861



题意

国际象棋棋盘上象只能走对角线,如果两只象位于同一对角线上,它们将互相攻击。现在,给出n和k,在一个n*n的棋盘上放k个互不攻击的象有多少种方法?





另有题解

#include <iostream>
#include <cstdio>
#include <algorithm>
#include <cmath>
#include <cstring>
#define mst(a,b) memset(a,b,sizeof(a))
typedef long long LL;
using namespace std;
const int N = 9;
int Cb
,Cw
,Rb
[65],Rw
[65];
//C[]-旋转45°后黑白棋每行格子数(白色多一行)、R[i][j]-前i行放j个棋子的方法数

void Init(int n){
mst(Cb,0);
mst(Cw,0);
Cw[1]=1;
for(int i=1;i<=n;i++){
if(i<=n/2){
Cw[i]=2*i-1;
Cb[i]=2*i;
}
else{
if(!Cw[n+1-i])
Cw[i]=Cw[i-1]+2;
else Cw[i]=Cw[n+1-i];
Cb[i]=Cb[n-i];
}
//cout<<"第"<<i<<"行白棋:"<<Cw[i]<<endl;
//cout<<"第"<<i<<"行黑棋:"<<Cb[i]<<endl;
}
}

void init(int n){
mst(Cb,0);
mst(Cw,0);
for(int i=1;i<=n;i++){
for(int j=1;j<=n;j++){
if((i+j)&1) Cb[(i+j)>>1]++;
else Cw[(i+j)>>1]++;
}

}
/*for(int i=1;i<=n;i++){
cout<<"第"<<i<<"行白棋:"<<Cw[i]<<endl;
cout<<"第"<<i<<"行黑棋:"<<Cb[i]<<endl;
}*/
}

void Bishop(int n,int k,int C[],int R[][65]){
for(int i=0;i<=n;i++)   R[i][0]=1;
for(int i=1;i<=k;i++)   R[0][i]=0;
for(int i=1;i<=n;i++)
for(int j=1;j<=C[i];j++)
R[i][j]=R[i-1][j]+R[i-1][j-1]*(C[i]-j+1);
}

int main()
{
int n,k;
while(scanf("%d%d",&n,&k)&&(n||k)){
Init(n);            //两个init作用相同,初始化Cb、Cw数组
sort(Cb+1,Cb+n);
sort(Cw+1,Cw+n+1);

Bishop(n-1,k,Cb,Rb);
Bishop(n,k,Cw,Rw);
LL ans=0;
for(int i=0;i<=k;i++)
ans+=Rb[n-1][i]*Rw
[k-i];
printf("%lld\n",ans);

}

return 0;
}
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: