問題:平面內一個物體Object的初始座標(0,0),此後,每秒進行一個移動,每次移動1,方向是上下左右。即,newLocation = oldLocation + (x, y),其中(x,y) = (0,1) or (0, -1) or (1, 0) or (-1, 0)。那麼,N秒後,Object離初始座標的距離,會不會隨着N的增長而增長?python
分析:問題的本質是求N秒後的指望距離。這裏有一點要注意,N秒後的指望距離和N秒後object最有可能出現的位置是兩個該問題!搞清了這一點以後,咱們就知道E(dist) = sigma(dist[i] * p[i]),其中dist[i]是離(0,0)的距離,p[i]是此距離的機率。由此,咱們能夠獲得一個直觀的概念,指望距離會隨着N的增長而增長。(實際上,用數學的機率分佈能夠證實)app
如下,用python來仿真這一過程,證實這一結論dom
代碼spa
#!/usr/bin/python import pylab import random import math def distance(location): return math.sqrt( location[0]**2 + location[1]**2 ) def simulate(count): location = [0, 0] countLeft = 0 countRight = 0 countUp = 0 countDown = 0 for i in range(0, count): direction = random.choice(["left", "right", "up", "down"]) # print "direction = ", direction if (direction == "left"): location[0] -= 1 countLeft += 1 if (direction == "right"): location[0] += 1 countRight += 1 if (direction == "up"): location[1] += 1 countUp += 1 if (direction == "down"): location[1] -= 1 countDown += 1 # print "location = ", location dist = distance(location) result.append(dist) print countLeft, countRight, countDown, countUp return result = [] simulate(10000) pylab.title('random walk simulation') pylab.xlabel('time/s') pylab.ylabel('distance/m') pylab.plot(result) pylab.show()
運行結果:code
改進:orm
咱們看到,一次試驗只能給人一個直觀映像,即,隨着step的增長,與原點的距離也在增長。可是,一次試驗的隨機性比較高,這致使結果的振動幅度比較大,沒法很好的看出dist和step的關係。如何改進這一點呢?數學
用取平均的方法來消除隨機偏差。這裏,咱們對500次試驗取平均。it
如下是改進後的試驗結果:io
如下是改進後的代碼:form
#!/usr/bin/python import pylab import random import math def distance(location): return math.sqrt( location[0]**2 + location[1]**2 ) def simulate(count): location = [0, 0] countLeft = 0 countRight = 0 countUp = 0 countDown = 0 result = [] for i in range(0, count): direction = random.choice(["left", "right", "up", "down"]) # print "direction = ", direction if (direction == "left"): location[0] -= 1 countLeft += 1 if (direction == "right"): location[0] += 1 countRight += 1 if (direction == "up"): location[1] += 1 countUp += 1 if (direction == "down"): location[1] -= 1 countDown += 1 # print "location = ", location dist = distance(location) result.append(dist) return result def performTrial(steps, tries): distLists = [] for i in range(0, tries): result = simulate(steps) distLists.append(result) return distLists def main(): steps = 3 tries = 500 distLists = performTrial(steps, tries) averageList = [0] for i in range(0, steps): total = 0 for j in range(0, tries): total += distLists[j][i] average = total/tries averageList.append(average) # print 'total=', total # print 'average=', average # print averageList pylab.plot(averageList) pylab.title('random walk simulation') pylab.xlabel('time/s') pylab.ylabel('distance/m') pylab.show() return if __name__ == '__main__': main()
最後用簡單的例子來證實正確性:
steps = 0 dist = 0
steps = 1 dist = 1
steps = 2 dist = (2+0+sqrt(2)+sqrt(2))/4 = 1.21
step3 = 3 dist = (3+1+sqrt(5)+sqrt(5)+...+...)/16 = 1.59
以下是steps=3, tries=500的結果圖示,和以上數學分析結果一致。