题目链接
在某kerin的带领下,成功开始做每日一题
放个大佬的链接kerin的博客
好了,今天这个题一看数据范围:15
!!!
是不是瞬间想到打表!
不不不,打表也得能算出来呀~~
第一思路,先想到的就是next_permutation(不得不说,全排列yyds)
冒着会超时的风险,我写下了代码,
//头文件省略掉了
// int num[30];
// cin>>n;
// for (int i = 1; i <= n; ++i) {
// num[i]=i;
// }
// int men[30]={0};
// int count=0;
// do{
// int flag=0;
// for (int i = 1; i <= n; ++i) {
// if(num[i]==men[i]){
// flag=1;
// break;
// }
// if(num[i]%i!=0 && i%num[i]!=0){
// men[i]=i;
// flag=1;
// break;
// }
// }
// if(flag==0){
// count++;
// }
// }while(next_permutation(num+1,num+n+1));
// cout<<count<<endl;
// return 0;
不得不说,这代码在本地跑12就跑不出来了,甚至以为加了一个剪枝发现根本没用???为什么?人家函数都给你生成好数了,你再拦能拦住什么呢??
于是,dfs
其实看了看不加剪枝应该也还可以
其实还是加剪枝了,第count位不可以是mem[count]
记录下来了
int num=0;
int n;
vector<int> v;
int mem[25]={0};
int all_num[25]={0};
void dfs(int count){
if(!v.empty()) {
if (v[count - 1] % count != 0 && count % v[count - 1] != 0) {
mem[count] = v[count - 1];//第count位不可以是mem[count]
return;
}
}
if(n==count){
num++;
return ;
}
for (int i = 1; i <= n ; ++i) {
if(all_num[i]==0 && mem[count+1]!=i){
all_num[i]=1;
v.push_back(i);
dfs(count+1);
all_num[i]=0;
v.pop_back();
}
}
}
int main(){
//
cin>>n;
dfs(0);
cout<<num;
}
不过实际上最后的代码完美迎合了一开始的想法QAQ
db[20]={0,1,2,3,8,10,36,41,132,250,700,750,4010,4237,10680,24679};
就,这样了