题解:CF788C The Great Mixing
__vector__ · · 题解
我不理解为什么题解区所有做法都需要枚举
我实际测试,
这篇题解将主要说明为什么
做法
首先,令
令
但是,可能的总和范围在
而每个点最多有
但是,事实上,只有编号
首先,枚举的总和范围在
证明:已知最后总和为
接着,上界可以降低到
证明:如果有某一步,总和超过了
#include <bits/stdc++.h>
using namespace std;
#define FOR(i,a,b) for(auto i=(a);i<=(b);i++)
#define REP(i,a,b) for(auto i=(a);i>=(b);i--)
#define FORK(i,a,b,k) for(auto i=(a);i<=(b);i+=(k))
#define REPK(i,a,b,k) for(auto i=(a);i>=(b);i-=(k))
#define pb push_back
#define mkpr make_pair
typedef long long ll;
typedef pair<int,int> pii;
typedef pair<ll,ll> pll;
typedef vector<int> vi;
template<class T>
void ckmx(T& a,T b){
a=max(a,b);
}
template<class T>
void ckmn(T& a,T b){
a=min(a,b);
}
template<class T>
T gcd(T a,T b){
return !b?a:gcd(b,a%b);
}
template<class T>
T lcm(T a,T b){
return a/gcd(a,b)*b;
}
#define gc getchar()
#define eb emplace_back
#define pc putchar
#define ep empty()
#define fi first
#define se second
#define pln pc('\n');
#define islower(ch) (ch>='a'&&ch<='z')
#define isupper(ch) (ch>='A'&&ch<='Z')
#define isalpha(ch) (islower(ch)||isupper(ch))
template<class T>
void wrint(T x){
if(x<0){
x=-x;
pc('-');
}
if(x>=10){
wrint(x/10);
}
pc(x%10^48);
}
template<class T>
void wrintln(T x){
wrint(x);
pln
}
template<class T>
void read(T& x){
x=0;
int f=1;
char ch=gc;
while(!isdigit(ch)){
if(ch=='-')f=-1;
ch=gc;
}
while(isdigit(ch)){
x=(x<<1)+(x<<3)+(ch^48);
ch=gc;
}
x*=f;
}
const int maxn=1005;
int n,k;
bitset<maxn> ok;
int dis[maxn];
void bfs(){
memset(dis,0x3f,sizeof dis);
int inf=dis[0];
queue<int> q;
FOR(i,n,1000){
if(ok[i])dis[i-n]=1,q.push(i-n);
}
while(!q.empty()){
int u=q.front();
q.pop();
FOR(i,0,1000){
if(ok[i]){
int to=u+i-n;
if(to>=0&&to<=1000){
if(dis[to]>dis[u]+1){
dis[to]=dis[u]+1;
q.push(to);
}
}
}
}
}
if(dis[0]==inf)puts("-1");
else printf("%d\n",dis[0]);
}
void solve(int id_of_test){
read(n);
read(k);
FOR(i,1,k){
int a;
read(a);
ok[a]=1;
}
bfs();
}
int main()
{
int T;
T=1;
FOR(_,1,T){
solve(_);
}
return 0;
}