【二进制枚举】阶乘之和

​题目链接​

题目

【二进制枚举】阶乘之和_i++

思路

阶乘增长很快,10!就已经超过1e6了。
原本想背包存在性DP整一波,写了一半发现不用,直接二进制枚举选与不选即可即可。
比较一下01背包和二进制枚举
【二进制枚举】阶乘之和_二进制枚举_02
【二进制枚举】阶乘之和_01背包_03
这里n很小,所以二进制枚举更好一些

代码

#include<bits/stdc++.h>
using namespace std;
typedef long long LL;
const int N=15,M=5e6+10;
LL w[N]={1};
bool exist[M];
LL fac=1,cnt=1;
int main(){
for(int i=1;i<=10;i++){
fac*=i;
w[cnt++]=fac;
}
for(int i=0;i<(1<<cnt);i++){
LL tmp=0;
for(int j=0;j<cnt;j++){
if(i&(1<<j))tmp+=w[j];
}
if(tmp>0&&tmp<=1e6)exist[tmp]=1;
}

LL n;
while(cin>>n){
if(n<0)break;
if(exist[n])puts("YES");
else puts("NO");
}
return 0;
}