您的位置:首页 > 其它

神庙逃亡的无限钻石

2016-10-18 19:42 190 查看
2014年8月,我基本上就是在神庙逃亡中度过的。

我截下了4种bug的图:



花了很久才知道这个任务到底是什么意思,miser是吝啬鬼的意思,就是说跑的时候不能碰到金币。

但是没有说细节,后来才知道,指的就是在矿洞里面不能碰到金币。

说实话,这个真的很难!

不过,我还是完成了,然而,完成了之后,就变成了:



真心无语MDZZ



据说这里叫云端,如果不小心触发了bug到了这里,就完全失去了对身体的掌控了。

刚开始的时候感觉很爽,什么都不用做,他会自己跑,没有障碍,距离一直在增加。

但是没过多久就之间挂了。。。



这运气。。。死的时候刚好钱币占了整个屏幕。

可以清晰的看到,钱居然是破的。。。

与此类似,我还收藏了一个钻石的图片:



好了,言归正传,本文的标题叫神庙逃亡的无限钻石。

在神庙逃亡已经没什么好玩的时候,我开始借助外挂看能冲到多远。

在网上下载的外挂,说是有无限钻石,但是其实也只有8亿多而已。

具体多少我忘了,不如就用图片里面的数字814778622

这么多钻石,最多能复活多少次呢?

(本文不考虑中途获得钻石)

第一次复活需要1个钻石,第二次需要2个,第三次需要4个。。。。。。

所以,复活n次一共需要2^n-1个钻石

2^29=536870912

所以,这么多钻石可以复活29次。

然后,这一局结束之后,就只剩下277907711个钻石了。

要多少局才能把钻石全部用完呢?

代码:

#include<iostream>
using namespace std;

int f(int n)
{
cout << n << endl;
int k = 1;
while (k * 2 < n)k = k * 2 + 1;
return n - k;
}

int main()
{
int n = 814778622;
while (n)n = f(n);
return 0;
}


输出:

814778622

277907711

9472256

1083649

35074

2307

260

5

2

1

每运行一次n=f(n)刚好就是一局玩完了,f(n)就是剩下多少钻石。

如果用二进制表示的话:



显然,不断运行n=f(n)的话,n会严格单调递减,而且最后一定会变成0,于是循环结束。

现在,新的问题来了,对于任意的自然数n,运行多少次n=f(n)之后才会变成0呢?

我们用l
来表示答案,l是length的意思。

那么,根据f(n)的特点,可以得到关于l
的递推式,见代码。

代码:

#include<iostream>
using namespace std;

int l[100000];

int f(int n)
{
int k = 1;
while (k * 2 < n)k = k * 2 + 1;
return n - k;
}

int main()
{
l[0] = 0;
for (int i = 1; i < 100000; i++)l[i] = l[f(i)]+1;
return 0;
}

结果很有意思:

l[100000]={0, 1, 2, 1, 2, 3, 2, 1, 2, 3, 2, 3, 4, 3, 2, 1, 2, 3, 2, 3, 4, 3, 2, 3, 4, 3, 4, 5, 4, 3, ...}

随着i的增大,每次l要不就是增大1,要不就是减小1。

其实,这个只要用数学归纳法就可以证明。

但是不是对i进行归纳,而是对i的2进制的位数进行归纳,详情略。

如果不限于计算机,l是一个无限的数列,那么l将包含所有的正整数。

对于任意n,存在一个最小的m=2^n-n使得,l[m]=n
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: