Barnsley fern

Barnsley's fern uses four affine transformations. The formula for one transformation is the following:

f(x,y)={\begin{bmatrix}a&b\\c&d\end{bmatrix}}{\begin{bmatrix}x\\y\end{bmatrix}}+{\begin{bmatrix}e\\f\end{bmatrix}}

Barnsley shows the IFS code for his Black Spleenwort fern fractal as a matrix of values shown in a table. In the table, the columns "a" through "f" are the coefficients of the equation, and "p" represents the probability factor.

w a b c d e f p Portion generated
ƒ1 0 0 0 0.16 0 0 0.01 Stem
ƒ2 0.85 0.04 −0.04 0.85 0 1.60 0.85 Successively smaller leaflets
ƒ3 0.20 −0.26 0.23 0.22 0 1.60 0.07 Largest left-hand leaflet
ƒ4 −0.15 0.28 0.26 0.24 0 0.44 0.07 Largest right-hand leaflet

 

 

 

 

 

<출처: https://en.wikipedia.org/wiki/Barnsley_fern>

import random
import matplotlib.pyplot as plt

def transformation_1(p):
    x=p[0]
    y=p[1]
    x1=0.85*x +0.04*y
    y1=-0.04*x +0.85*y+1.6
    return x1,y1

def transformation_2(p):
    x=p[0]
    y=p[1]
    x1 = 0.2 * x - 0.26 * y
    y1 = 0.23 * x + 0.22 * y + 1.6
    return x1,y1

def transformation_3(p):
    x=p[0]
    y=p[1]
    x1 = -0.15 * x + 0.28 * y
    y1 = 0.26 * x + 0.24 * y + 0.44
    return x1,y1

def transformation_4(p):
    x=p[0]
    y=p[1]
    x1 = 0
    y1 = 0.16*y
    return x1,y1

def get_index(probability):
    r=random.random()
    c_probability=0
    sum_probability=[]
    for p in probability:
        c_probability += p
        sum_probability.append(c_probability)
    for item,sp in enumerate(sum_probability):
        if r<=sp:
            return item
    return len(probability)-1

def transform(p):
    transformations=[transformation_1,transformation_2,transformation_3,transformation_4]
    probability=[0.85,0.07,0.07,0.01]
    tindex=get_index(probability)
    t=transformations[tindex]
    x,y=t(p)
    return x,y

def draw_fern(n):
    x=[0]
    y=[0]

    x1,y1=0,0
    for i in range(n):
        x1,y1=transform((x1,y1))
        x.append(x1)
        y.append(y1)
    return x,y

n=int(input("Enter the number of points in the Fern:"))

x,y=draw_fern(n)
plt.plot(x,y,'o')
plt.title('Fern with {0} points'.format(n))
plt.show()

결과를 실행시켜보면 아래와 같다.

barnsley