今天写LV算法,就是我之前的那个blog,产生了困扰我很久的问题。
使用回溯法计算八皇后,只需要访问114个节点就可以找到一个解。用随机算法理论上,效果比回溯法好,大概只需要访问50几次就可以得到一个解。但是我的随机算法却跑了很久,十几秒。searchNode数在几千到几十万不等。
出现这种问题的原因是,随机算法设置的种子time(0)是一个秒级的数,计算机执行随机算法很快,大概是微秒级,所以用秒级的随机数就会产生很多重复的。这就造成了LV算法特别慢。
这是当时的随机算法
int uniform(int x) {
uniform_int_distribution<int> u(1, x);
default_random_engine e(time(0));
return u(e);
}
不能直接使用time(0)而应该使用微秒级的种子。
这里插曲一下:
c++获取毫秒的方式
#include <sys/timeb.h>
struct timeb tp;
ftime(&tp);
结构体timeb是库文件sys/timeb.h中定义的
struct timeb{
time_t time; /* 为1970-01-01至今的秒数*/
unsigned short millitm; /* 千分之一秒即毫秒 */
short timezonel; /* 为目前时区和Greenwich相差的时间,单位为分钟 */
short dstflag; /* 为日光节约时间的修正状态,如果为非0代表启用日光节约时间修正 */
};
这样使用tp.millitm就是一个小于1000的按毫秒变化的数字。
将tp.time/1000+tp.millitm作为种子就得到一个毫秒级的随机数。
但是LV算法即使用毫秒也不行!用微秒级的随机数才行!
微妙和纳秒级太麻烦,不想去研究
所以想到了一个办法,设置一个全局变量seeds,给初始值为一个毫秒时间戳,然后每次的种子都是seeds+1这样每次调用都不会有相同的数字。