十几行python代码,带你画一个漂亮的Mandelbrot集
想必大多对数学感兴趣的人都对Mandelbrot集有所耳闻。
虽然每个做这个程序的都要说,但是我还是以我的语言再解释一次吧。
对于复平面上任意一个复数C,从X0=0开始,Xn=Xn-1^2+C反复迭代 ,如果结果始终不会发散,则C属于曼德布洛特集。
所以绘制曼德布洛特集其实很简单,按照定义把这些点找出来就可以啦。
用python实现一下:
import numpy as np
from matplotlib import pyplot as plt
n=1000
Y, X = np.mgrid[-1.5:1.5:3/n, -2:1:3/n]
C = X+1j*Y
#做出复平面C,每一个元素,都是复平面上该点的坐标。
#下面来检查一下这些点,哪些满足Mandelbrot集定义
pic = np.zeros((n,n)) #定义一个平面,用来保存定义要求的每一次迭代的结果。
ans = np.zeros((n,n)) #用来绘制最终曼德布洛特集的平面。
for i in range(20):
pic=pic**2+C #按照曼德布洛特集的定义进行迭代。
ans = np.float32(np.abs(pic)<100)
#检查多次迭代后,最终结果模值小于100的点都认为收敛,从而得到每一点的收敛情况
# 把收敛结果然后转化成浮点类型,放在ans中。
plt.imshow(ans,cmap="rainbow")
plt.show() #把ans画出来
怎么样,是不是很简单? 我们来看看结果如何。

总共13行就实现了这样的效果。
现在修改一下程序,我们把迭代过程中的每一步满足的点集都绘制在一张图上。修改的方法很简单,让保存最终结果的ans是每一步结果的和,看下修改后的代码
import numpy as np
from matplotlib import pyplot as plt
n=1000
Y, X = np.mgrid[-1.5:1.5:3/n, -2:1:3/n]
C = X+1j*Y
pic = np.zeros((n,n))
ans = np.zeros((n,n))
for i in range(20):
pic=pic**2+C
ans += np.float32(np.abs(pic)<100)
#这里ans放入循环体中,对每一步求和,从而展示出逐渐收敛的过程。
plt.imshow(ans,cmap="rainbow")
plt.show()
看看结果:

效果是不是挺惊艳。
如果想绘制局部图形,还是老程序,但是需要修改对应的参数:
import numpy as np
from matplotlib import pyplot as plt
n=1000
Y, X = np.mgrid[-0.05:0.05:0.1/n, 0.2:0.3:0.1/n]
#在这里只选择平面上自己想绘制的部分区间。
C = X+1j*Y
pic = np.zeros((n,n))
ans = np.zeros((n,n))
for i in range(200):
#由于绘制范围变小,为了在局部依然明确的区分出收敛情况,则需要相应提高迭代次数。
pic=pic**2+C
ans += np.float32(np.abs(pic)<100)
plt.imshow(ans,cmap="rainbow")
plt.show()

怎么样,没有疑问了吧。