Reputation: 41
I am trying to to do a Mandelbrot plot for z′ = z^2 + c where c =x +iy on an N × N grid spanning the region where −2 ≤ x ≤ 2 and −2 ≤ y ≤ 2. and N =100. my ccom method is c =x +iy and my zcom method is for z^2 and my zprime method is for z' part i made recursive for a 100 iterations. But I am unsure why get back very large values for my zp array that zprime returns. I have tried to feed the arrays for imshow but it says invalid arguments.
My Code:
import math as mathy
import decimal as deci
import numpy as np
import pylab as plt
#z' = z**2 + c
#z=x+iy
#|z|<2
#c = x + iy
#−2 ≤ x ≤ 2,−2 ≤ y ≤ 2
#(x + iy)(u + iv)=(xu – yv) + (xu + yv)i
def zcom(u,v):
zcsq = np.zeros(2,float)
zcsq[0] = ((u)**2) - ((v)**2)
zcsq[1] = ((u)**2) + ((v)**2)
return zcsq
def ccom(x,y):
cc = np.zeros(2,float)
cc[0] = x
cc[1]= y
return cc
def zprime(u,v,x,y,n):
zp = np.zeros((n,1,2),float)
t1=np.linspace(-x,x,100)
t2=np.linspace(-y,y,100)
for i in range(0,n):
zp[i] = zcom(u,v) + ccom(t1[i],t2[i])
u= zp[i][0,0]
v= zp[i][0,1]
return zp
plt.imshow(zprime(0,0,2,2,100), cmap='hot')
plt.show()
My Error:
Warning (from warnings module):
File "Mandelbrot.py", line 25
zcsq[0] = ((u)**2) - ((v)**2)
RuntimeWarning: overflow encountered in double_scalars
Warning (from warnings module):
File "Mandelbrot.py", line 25
zcsq[0] = ((u)**2) - ((v)**2)
RuntimeWarning: invalid value encountered in double_scalars
Warning (from warnings module):
File "Mandelbrot.py", line 27
zcsq[1] = ((u)**2) + ((v)**2)
RuntimeWarning: overflow encountered in double_scalars
Warning (from warnings module):
File "Mandelbrot.py", line 27
zcsq[1] = ((u)**2) + ((v)**2)
RuntimeWarning: invalid value encountered in double_scalars
Traceback (most recent call last):
File "Mandelbrot.py", line 53, in <module>
plt.imshow(zprime(0,0,2,2,100), cmap='hot')
File "matplotlib\pyplot.py", line 2892, in imshow
imlim=imlim, resample=resample, url=url, **kwargs)
File "matplotlib\axes.py", line 7306, in imshow
im.set_data(X)
File "matplotlib\image.py", line 430, in set_data
raise TypeError("Invalid dimensions for image data")
TypeError: Invalid dimensions for image data
Upvotes: 1
Views: 1078
Reputation: 69192
The main issue is that your code seems to show a slight misunderstanding of the Mandelbrot set.
When you do the iteration to form the set, the result of the iteration is either bounded or unbounded. The Mandelbrot set is all of the iterations that are bounded, and the starting points that lead to unbounded results are not part of the set.
Usually, to yield a pretty result, the starting points that are not part of the set are plotted based on how many iterations it took to decide that the iteration was unbounded. (Hopefully, it's obvious at this point why you get the overflow, because "unbounded" can lead to very big result, in this case of 100 iterations, on the order of 22100, which is a very big number, but to know that the result will be unbounded, you can just stop when the value is greater than 2.)
Below is the result and the code I used, based on your code. The main important change was in the loop, I checked whether the iteration ever produced a result greater than 2, and if it did I noted the iteration number (just to give the color, though this point is not in the set), and if it never got greater than 2, I set the value to 0, and this point is in the set (to within the accuracy of the calculation and number of iterations). I thought it was easier to keep things in complex number notation, but you can change it back if you like. I also removed the functions for clarity.
import numpy as np
import pylab as plt
def zprime(x,y,n):
t1=np.linspace(-x,x,1000)
t2=np.linspace(-y,y,1000)
result = np.zeros((len(t1),len(t2)), np.int) # make a result array that matches the x,y grid, since you want an image of the x,y grid
for i, u0 in enumerate(t1):
for j, v0 in enumerate(t2):
z0 = u0 + 1j*v0 # initial value for iteration
zp = 1.*z0 # just a copy, ie, the value of the first iteration
for k in range(1,n): # starting from 1, since the first was a copy (I'm not saying this detail is important, just how I think of it)
zp = zp**2 + z0 # the defining calculation
if abs(zp)>2.: # >2 means unbounded, so not in the M-set
result[i, j] = k # set the result to k just to give some color
break
else: # never hit a break, so this point is in the M-set
result[i, j] = 0
return result
mset = zprime(2,2,50)
plt.imshow(mset, cmap='hot')
plt.show()
Upvotes: 2