Julia Sets in Julia
Subtitle: Completely invariant iterations of the holomorphic function
# Gaston Julia
Gaston Julia was born on the 3rd of February, 1893 in Sidi bel Abbès, Algeria to Delorès Delavent and Joseph Julia, a mechanic. Gaston became interested in music and mathematics at an early age, and excelled in both, settling on the violin as his favorite instrument.
In 1901, the family moved to Oran on the coast of Algeria where he enrolled in the Lycée, eventually graduating with distinction in the baccalaureate examinations of science, modern languages, philosophy, and mathematics. He left Algeria for Paris and received a scholarship to the École Normale Supériore in 1911. In 1914 Germany declared war on France and Julia was called up for service with the 57th Infantry Regiment at Libourne.
Deployed to the Western Front, the following is a report of the action, and Julia’s injury that cost him his nose.
January 25, 1915, showed complete contempt for danger. Under an extremely violent bombardment, he succeeded despite his youth (22 years) to give a real example to his men. Struck by a bullet in the middle of his face causing a terrible injury, he could no longer speak but wrote on a ticket that he would not be evacuated. He only went to the ambulance when the attack had been driven back. It was the first time this officer had come under fire.
For the remainder of his life, Julia wore a leather strap to cover the missing nose.
Julia married Marianne Chausson in 1918. She was the nurse who attended to him after his injury, and the daughter of composer Ernest Chausson. He had completed his Ph.D. in mathematics the year before, under Émile Picard, Henri Lebesgue, and Pierre Humbert.
At age 25, he published a 199-page manuscript, Mémoire sur l’iteration des fonctions rationelles, (Memoir on the iteration of rational functions) which brought him instant fame in mathematical circles and earned him the Grand Prix des Sciences Mathématiques of the French Academy of Sciences.
An iterated function is applied repeatedly to the previous solution, and a rational function is one like
where and are polynomial functions. can’t be zero, but it can be , meaning that .
# Function Iterations
Iterating a function is pretty simple. Suppose
If you start with , then . Now put into the function to get . This goes on forever, A more interesting function is
In other words, if is even, divide it by , but if it’s odd, multiply by and add . Any number that’s a power of immediately collapses down to , for example, . Then you get stuck in the loop If you start with you get the sequence .
Can you find a starting number that doesn’t wind up at ? Nobody knows for sure, but it’s thought that every sequence eventually winds down to . This is known as the Collatz conjecture, named for mathematician Lothar Collatz who first proposed the conjecture in 1937. It’s also called the Hailstone Problem because of the way the number sequence jumps up and down.
# Curses, FOILed Again!
Remember the FOIL method from high school algebra? If you want to expand using the FOIL method, you multiply the First two terms, , then the Outer terms, , the Inner ones, , and finally the Last two, to get
Snidely Whiplash often said, “Curses, foiled again!” on the Rocky and Bullwinkle show, but he may not have been referring to algebra. Here’s a picture of Rocky, Bullwinkle, and Captain Peachfuzz. Because reasons.
What’s the square root of negative one ? For a long time, mathematicians thought there was no solution to this problem because when you multiply two positive numbers together you get a positive number, and when you multiply two negative numbers together you also get a positive number, so there can’t be an such that . But, in the 17th century, René Descartes named the solution to as , an imaginary, fictitious, and useless number.
Since then, we’ve found plenty of uses for these otherwise useless numbers. Combine them with real numbers, the kind we’re used to, and you get complex numbers like which is parts real and parts imaginary. You can plot complex numbers as points, using the axis for the real part, and the axis for the imaginary part. Here’s a plot of :
Suppose you wanted to multiply by another complex number . Just use the FOIL method but with the complex numbers,
Remember that , so multiplying the two imaginary parts together gives the negative of the product, ignoring the ’s. It might make more sense to do the first and last together to get the new real part, and then the inner and outer parts for the new imaginary. You could call it the FLIO method.
In the plot, the real part of is , which is drawn as the vector , and the imaginary part is , drawn as the vector . These two vectors form the adjacent and opposite sides of a right triangle with angle . Using the Pythagorean Theorem, we can calculate the length of the hypotenuse, . The sides and can be written in terms of and as
# A Most Beautiful Equation
Leonard Euler (see our previous post, “Seven Bridges for Seven Truckers”) discovered an amazing property of complex numbers,
where is the base of the natural logarithm. The proof is pretty simple. Define as
The reason for choosing this particular function is that we will show that for every , meaning that the numerator and denominator are the same everywhere. Using the product rule of differentiation,
Since the derivative of for every , then is a constant. The derivative of a function gives the slope of the function at every point, so a derivative of zero means the function has zero slope, in other words, it’s a straight line parallel to the axis at some constant distance from the axis.
We can calculate the value of this constant at any , and the easiest one is , where since , , and . In other words, for every , which completes the proof.
The angle is measured from the axis, so is along the positive real number line, is the positive imaginary axis, represents negative real numbers and points along the negative imaginary axis.
Looking at , we see that when , , which gives the most beautiful equation,
Physicist Richard Feynman said that this is “the most remarkable formula in mathematics” because it contains , the base of natural logarithms, the imaginary number , , the constant relating the radius of a circle to its circumference and area, the first natural number, and the center of the mathematical universe.
# Iterations on a Complex Number
Julia wondered what would happen if he iterated a function like where both and could be complex. If and , then the first few iterations become
If you start with a smaller , say , the values of jump around, but they stay relatively small. Another way to look at the iterations is to plot several steps of the iterations at different starting points and additive constant .
Since the first iterate squares the initial value of and adds , then and will meet at after the first step. The same thing happens for .
In this plot, for degrees, and .
Adding shifts the starting points a little bit to prevent overlapping trajectories, and dividing by is equivalent to setting in the and vectors except for the slight shift of the starting point. If you set , eventually all of the trajectories escape towards infinity.
What is it that keeps some points from getting away, while others escape? The norm of a vector is the length of the vector and as we saw above, the length is easily calculated using the Pythagorean theorem. A shorthand notation for the norm is a pair of vertical lines around the vector or complex number,
After a single iteration, becomes , and the length or norm is . One way to check if the iterates are tending towards infinity is to calculate the length of each iterate. In the case (without dividing by ), the norm of the iterates is
Using the same starting point, and now dividing by , the iterates are
Not only do the iterates remain small, but they get closer to (after rounding).
What happens if you write and want to find ? This is very easy because
How long is the new vector ? The part measures the angle so it doesn’t contribute to the length, which means that the length of is simply .
If we choose such that , then will be greater than if . If then will grow at each step. If you think of and as vectors, then the smallest value for is when and point in opposite directions.
In most cases, and won’t point in opposite directions, so will be even larger and the trajectory will escape faster, but we can check to see if and stop iterating when we get to that value.
Vectors are added together by connecting the point of to the tail of to get . Subtracting from turns the direction of around.
Using the FOIL method, we can calculate for combinations of positive and negative vectors and .
In the picture above, you can see that the red vectors have the same , as do the green vectors. After a single iteration, the new value of is the same as the new value of , just as the green vectors coincide. If results in an escaping trajectory, then so does .
# Julia Sets
Gaston Julia wanted to find the boundary between the points that escaped and those that didn’t. The boundary is now called the Julia Set. The points are taken from all points in the complex plane, and the set changes depending on the initial choice of the parameter .
In this image, , and the complex numbers range over . The image is composed of 1281 points in each dimension, and for each point , the number of iterations needed to exceed is stored in a matrix. The black regions are where starts greater than , and the colored points are counts. On the right side, the color bar indicates the number of iterations, up to 1000, before the norm of becomes large.
Another example shows that for , the points either are clearly in the set or outside. At the top of this post is a plot of the Julia set for values of from to , taken from Benjamin Badger’s Julia Sets page.
The code (on Github) to generate these images is very straightforward. An
iterCounts array is initialized to zero, and for each , the value of is computed. The iteration is repeated until either or the number of iterations reaches 1000. The array
iterCounts is displayed as a heatmap to make the image.
The code is written in the Julia language because Julia is easy to learn and extremely fast. In fact, Julia is so fast that I didn’t bother to take advantage of symmetry.
In the figure above, there are 1.6 million points and each point requires one multiplication and one addition to get , and two more multiplications and an addition followed by a square root to get the norm of . Even if only a quarter of the points got to the limit of 1000 iterations, somewhere near one billion calculations were required. In Julia, the whole process completed in just a little over 10 seconds even with inefficient code.
function plotJulia(c,xRng = [-1.6,1.6], yRng = [-1.6, 1.6])
# Array of iteration counts
nx = 1281
ny = 1281
iterCounts = zeros(nx,ny)
xLocs = range(minimum(xRng),stop = maximum(xRng),length = nx)
yLocs = range(minimum(yRng),stop = maximum(yRng),length = ny)
# Loop over x,y locations iterating until maxIter reached, or |z|² > 4
maxIters = 1000
for j = 1:nx
for k = 1:ny
z = xLocs[j] + yLocs[k]im
while iterCounts[j,k] < maxIters && norm(z) < 2
z = z^2 + c
iterCounts[j,k] += 1
# Display Julia set as a heatmap
# Return array of iteratations
Gaston Julia never saw the images that we can now quickly produce in the Julia language, but he was able to work out many of the details and provide great insight into the structure of Julia sets.
- “Mémoire sur l’itération des fonctions rationnelles”, Gaston Julia
- Gaston Julia, MacTutor History of Mathematics Archive
- “Computers, Fractals and Dynamics: Computer Experiments in Mathematics”, Robert L. Devaney
- “Chaos, Fractals and Dynamics: Computer Experiments in Mathematics”, Robert L. Devaney (YouTube Video)
- “An Introduction to Julia and Fatou Sets”, Scott Sutherland.
- “Fractal Geometry: The Mandelbrot and Julia Sets”, Stephanie Avalos-Bock
- “Complex Dynamics, the Julia Set.”, Eric Kuennen
- “Understanding Julia and Mandelbrot Sets”, Karl Sims
- Julia Sets
- Julia Language Plots.jl and plot attributes
- Wikipedia page on Julia sets
- The Julia Programming Language
- Timing in Julia
- Collatz Conjecture