问题:平面内一个物体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的结果图示,和以上数学分析结果一致。