首先(万年不变的开头),最近的考试都真的让人感到无比的尴尬233,除了暴力就是爆零。所以暴力最主要的就是搜索,然后这次就很手贱的脑补一发所谓的启发式搜索,写的原因就是这个名字太有吸引力了。感觉优化非常猛(玄学)。首先贴一组图片来看看我自己的乱估价的结果:
std跑下来的结果:
我最后跑下来的结果:
好了,人生中第一次暴力c标算的记录就此生成了!
但是也着实让人很尴尬,由题目数据可以看出,复杂度应该是递增的,但是我的8, 9号点比10号点跑的还慢,
说明,不好意思,我估歪了233~
这只是一个单纯的发表感想的例子,这个估价函数也特别简单,所以把题附上,(这个绝对不是标准的启发式搜索!!注意!!)仅做纪念~
代码:
#include<cstdio>
#include<iostream>
#include<cstring>
#include<cstdlib>
#include<cmath>
#include<queue>
#include<set>
using namespace std;
struct lpl
{
int num;
int z;
int q;
int w;
bool friend operator < (lpl aaa, lpl bbb)
{
if(aaa.z > bbb.z)
{
return true;
}
if(aaa.z == bbb.z)
{
if(aaa.w < bbb.w)
return true;
}
return false;
}
}lin, qwe;
struct ld
{
int num;
int q;
bool friend operator < (ld aaa, ld bbb)
{
if(aaa.num > bbb.num) return true;
return false;
}
}asd;
int t, n, m;
inline bool check(int t)
{
int ppp = sqrt(t);
for(int i = 2; i <= ppp; ++i)
{
if(t % i == 0)
{
return false;
}
}
return true;
}
inline void putit()
{
scanf("%d%d", &n, &m);
if(check(n))
{
printf("0\n");
return;
}
priority_queue<lpl> q;
set<ld> s;
lin.num = n, lin.q = 0, lin.w = 0, lin.z = 0;
asd.num = n, asd.q = 0;
s.insert(asd);
q.push(lin);
for(;;)
{
lin = q.top(), q.pop();
qwe = lin;
if(qwe.q < m)
{
qwe.num = qwe.num / 2;
qwe.z++;
qwe.q++;
qwe.w = qwe.w + 10;
asd.q = qwe.q, asd.num = qwe.num;
if(s.count(asd) == 0)
{
if(check(qwe.num))
{
printf("%d\n", qwe.z);
return;
}
s.insert(asd);
q.push(qwe);
}
}
qwe = lin;
if(qwe.num > 2)
{
qwe.num = qwe.num--;
qwe.z++;
qwe.w = qwe.w + 3;
asd.num = qwe.num;
asd.q = qwe.q;
if(s.count(asd) == 0)
{
if(check(qwe.num))
{
printf("%d\n", qwe.z);
return;
}
s.insert(asd);
q.push(qwe);
}
}
qwe = lin;
qwe.num = qwe.num++;
qwe.z++;
qwe.w = qwe.w + 1;
asd.num = qwe.num, asd.q = qwe.q;
if(s.count(asd) == 0)
{
if(check(qwe.num))
{
printf("%d\n", qwe.z);
return;
}
s.insert(asd);
q.push(qwe);
}
}
}
int main()
{
//freopen("prime.in", "r", stdin);
//freopen("prime.out", "w", stdout);
scanf("%d", &t);
for(int i = 1; i <= t; ++i)
putit();
//fclose(stdin);
//fclose(stdout);
return 0;
}