HDU 5943-Kingdom of Obsession 二分匹配模板

Kingdom of Obsession

Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 65536/32768 K (Java/Others)
Total Submission(s): 2567    Accepted Submission(s): 757


 

Problem Description

There is a kindom of obsession, so people in this kingdom do things very strictly.

They name themselves in integer, and there are n people with their id continuous (s+1,s+2,⋯,s+n) standing in a line in arbitrary order, be more obsessively, people with id x wants to stand at yth position which satisfy
 

xmody=0



Is there any way to satisfy everyone's requirement?  

Input

First line contains an integer T , which indicates the number of test cases.

Every test case contains one line with two integers n , s .

Limits
1≤T≤100 .
1≤n≤109 .
0≤s≤109 .

 

Output

For every test case, you should output 'Case #x: y', where x indicates the case number and counts from 1 and y is the result string.

If there is any way to satisfy everyone's requirement, y equals 'Yes', otherwise y equals 'No'.

 

Sample Input

 

2

5 14

4 11

 

Sample Output

 

Case #1: No

Case #2: Yes


题意:

      给你一个n和s,问你能不能完成这样的操作:将s+1,s+2,s+3.....s+n进行排序,使得排序后,第一个可以整除1,第二个可以整除2....第n个可以整除n。

做法:

     我们知道,素数只能被1整除,所以连续的区间之内最多只能有1个素数,但是又因为1e9的范围之内任意两个相邻素数之间的距离不会超过100,所以当数很大的时候我们可以直接筛去很多情况。剩下的只要暴力枚举每个数能与哪个相匹配,再连边跑一边匈牙利就好啦


代码如下:

#include<vector>
#include<iostream>
#include<cstdio>
#include<cstring>
#include<algorithm>
#include<cmath>

using namespace std;
const int inf=0x3f3f3f3f;
const int maxn=2505;
int obj[maxn],vis[maxn],n,s;
vector<int> ve[maxn];
int match(int x){
    for(int i=0;i<ve[x].size();i++){
        int v=ve[x][i];
        if(!vis[v]){
            vis[v]=1;
            if(obj[v]==0||match(obj[v])){
                obj[v]=x; return 1;
            }
        }
    }
    return 0;
}
void init(){
    memset(obj,0,sizeof(obj));
    for(int i=1;i<=2450;i++)
        ve[i].clear();
}
int main(){
    int t,cas=0;
    cin>>t;
    while(t--){
        int now=0,flag=0;
        scanf("%d%d",&n,&s);
        init();
        if(s<n) swap(s,n);
        if(n>300) {
            printf("Case #%d: No\n",++cas);
            continue;
        }
        for(int i=1;i<=n;i++){
            for(int j=1;j<=n;j++){
                if((s+i)%j==0) ve[i].push_back(j);
            }
        }
        int sum=0;
        for(int i=1;i<=n;i++){
            memset(vis,0,sizeof(vis));
            if(match(i)) sum++;
        }
        if(sum==n) printf("Case #%d: Yes\n",++cas);
        else printf("Case #%d: No\n",++cas);
    }

	return 0;
}

猜你喜欢

转载自blog.csdn.net/qq_41955236/article/details/81739010