Coding Challenge #21: Mandelbrot Set with p5.js

Video Statistics and Information

Video
Captions Word Cloud
Reddit Comments

I love this guy. Pretty much taught me all the java I know. His lessons make it really easy.

👍︎︎ 1 👤︎︎ u/sdonaghy 📅︎︎ Jan 12 2017 🗫︎ replies
Captions
hello welcome to another coding challenge in this coding challenge I'm going to with great trepidation but excitement and energy I'm going to program from scratch the Mandelbrot set show you how to do it talk about the math behind it and make it happen in javascript in the browser problems will come up but I'm gonna do my best so why why do you care about this it's a fractal pattern you can make some beautiful images with it you might also just sort of learn a bit about programming and pixels and arrays but but yeah so know you're here you probably want to do the Mandelbrot set if you don't you can go outside and play frisbee um so let's see now let's look at least and let's read this definition which you know it's gonna cause a small like a slight pain in my side here to read it but I'm gonna do it anyway and try to unpack and understand it as best we can in the context of a short YouTube coding challenge video ok the Mandelbrot set is the set of complex numbers see it what does it mean for something to be a complex number and then to have a set of complex numbers that's the question we need to answer which the function f of Z equals Z squared plus C ok what does that function mean exactly does not diverge what does it mean for something to not diverge when iterated from Z equals 0 okay so there's a lot of stuff in there and the first thing the first thing I want to do before I start writing the code is just talk about the math and the first thing I want to do is talk about what is a complex number ok so you might be familiar with an operation in math called square roots I could say oh I think I have the wrong end of this pen I could say the square root of 4 by the way I forgot this whole thing I was practicing pronunciation and I completely forgot to do it the Mandelbrot set is named for the French mathematician Benoit Mandelbrot okay but all the time practice things like Benoit okay the square root of 4 is 2 the square root of 16 is 4 the square root of negative 1 is what well in fact you might say to yourself there is no such thing as the square root of negative 1 it's impossible any number squared positive or negative results in a positive number so the square root of a negative number inherently does not exist is not exactly the case in fact there is an answer to this and it's called I and I is an imaginary number it's imaginary because it's not a real number it doesn't actually exist but if we consider the square root of negative 1 actually be something that does exist and call it I all sorts of magic can happen but of which by the way is the Mandelbrot set so this is what's known so this is a real number and this is an imaginary number if I put those two things together 3 plus I this is a complex number a complex number has both a real component and an imaginary component and it is typically written in the form a plus bi a is the quote-unquote real component B is the quote/unquote imaginary component I personally love imaginary numbers because I could just imagine that then use my creative imagination to think about imaginary numbers ok so so this is what a complex number is now let's go back to that definition the set of complex numbers ok what does it mean for something to be a set of complex numbers well this actually relates to you can think about a canvas right a canvas or canvas the thing that lives in the browser in HTML or processing or Java or whatever graphics environment you're using has an x-axis and a y-axis it's a two dimensional plane well what if a I don't know which one should be which I'll just pick one and hopefully the Mandelbrot set won't be upside down hey let's say a is the x-axis and B is the y axis the plane of complex numbers the set of complex numbers is all the number that appears here might have an a value of 7 and a B value of 3 meaning 7 plus 3i so this plane this set of complex numbers is all the complex numbers for all of all a possibilities and all B possibilities so we have to do something for every single a set of complex numbers within this sort of downs of this canvas okay so that's good which the function f of Z equals Z squared plus C does not diverge when iterating from Z equals zero okay this is probably the hardest part for us to understand but once we understand it we're done and we can actually start to program the code so let me come back over here and let's write that so f of Z equals Z I I wrote the wrong thing down I might need some more space let's see Z squared plus C now C is a complex is a complex number A plus bi any number from this spot and we want to iterate this function starting with Z equals zero so if we start with Z equal to zero what do we get well Z the next Z like F Z like we're z1 e if this is Z index you know Z sub 0 Z of the 0 generation Z of the first generation equals Z squared plus C which is by the way just C so now Z sub 2 equals what C squared plus C and Z sub 3 is going to be C squared plus Z squared plus C so one of the things we need to look at how to do here is how do we get C squared this is where I need a little bit more room C squared what is C squared C squared is a plus B I times a plus B I right because C is a complex number and has a real component and imaginary component a plus bi well let's multiply these two things together a times a is a squared plus a times B I plus a bi now bi times a plus a bi again be AI times bi now this is a crazy one bi times bi is what B squared I squared what I I is the square root of negative 1 I mean it's imaginary but it is the square root of negative 1 so if you square it what do you get negative 1 so this actually turns out to be a squared plus this is a bi plus a bi plus 2 a VI plus oh no not plus minus because I squared is negative 1 minus B squared or we could look at this another way a squared minus B squared plus 2 a bi well guess what this is a complex number it has a real component a squared minus B squared and it has an imaginary component to a B so this is all the math that we need because what we're going to do is actually in our code just calculate these values over and over and over again generation to generation we're going to iterate iterate iterate and as we calculate those values over and over again we need to see do they remain bounded and absolute value so the question is are they tending to go towards infinity or they actually just like staying around some reasonable number and the Mandelbrot set is the set of numbers for which the function remains bounded so it's all the top for all of the possibilities it's all of the ones that don't tend towards infinity whoo that was a lot to think about maybe pause this video go outside do so take a break for a little while but now if you're back I'm going to start you're writing the code for that I'm going to refer back to this math a couple times probably I don't know if you're following this I'm having a good time ok so let's go to the code now I have a sort of empty p5.js sketch here and this is some JavaScript code it's just like a basic skeleton here the only thing that it's doing is it's looking at every single x value at every single Y value and setting its pixel to a grayscale value of 51 so I'm going to go take a look at that it's right here you can see here there we go there's my gray window if I were to you know change this component to 255 you can see it's like a redder window because I added more red so what I need to do altum Utley is UPS is I need to inside this code for every one of these x and y values I need to run this Mandelbrot set F of Z Z squared plus C math thing and I need to see them are my numbers getting bigger or are they not getting bigger and then I'm going to set a color based on that okay so now we have an interesting question though to ask which is hmm if this is my pixel window which goes from 0 to 360 and 0 to 240 well do I really want and at complex numbers a plus bi what do I really want to deal with complex numbers like 2 357 plus 212 I know I really want my range I don't know what it should be but I'm going to just go between negative 2 & 2 and then let's try that top to bottom and probably get something's going to be squished but it'll be fine so what one thing the first thing I need to do is I need to figure out what are my a and B values relative to X and y so I want to map X which goes from 0 to with to maybe between negative 2 & 2 let's make this a square and then I don't have to worry about any of this nonsense and then I'm going to map B and this is really which goes from Y which goes from 0 to height also between negative 2 & 2 so I'm looking for all the complex numbers that go between negative 2a plus plus negative 2b no no sorry negative 2 minus 2i all the way to 2 plus 2i that's the full range okay so I want to use those numbers now I need to start doing that iterating okay so the first thing I need to do is say oh I know how to do this I've done this before okay let's look at this we need to over and over again so we need to over and over we can have we need an operation that's going to happen over and over again so let's keep track of how one thing we should do is keep track of how often are we doing this let's have a variable n because I want to just make sure like as long as n is less than I don't know some arbitrary amount 100 like I don't want to iterate more than 100 times I can keep doing what I'm doing and I want to have Z start with something so I'm going to have a Z start with zero I'm sure I'm getting something wrong here because I'm it's like thinking about this as I'm doing and I'm gonna fix it as I go but let's let's figure out some things I need to calculate I kind of want to like pause recording to go look at my code for before okay but it's okay I'm fine I'm fine it's going to be okay okay did I get something wrong in the chat everybody put like rainbow emojis or something if I did something horribly wrong maybe rainbow maybe that's not right it should be rainbow if it's correct okay so the first thing I want to do is I want to calculate a squared minus B squared okay so I'm going to call that a a is a or let's that's going to be my new a is a times a minus B times B and then I also need to calculate to a B so I'm going to call that B B is two times a times B so I have now calculated the real components the real and the complex components for the next generation and then what do I need to say C say a equals a a and B equals B B and do it again so this is just my iterative process because I start with I think this is right write the number while yeah oh and then I need to say n plus plus okay now another thing I could do here is I could say like what does it mean for this tooten to be unbounded to tend towards infinity what if I just say something like I could be really lazy what if a a plus B B is greater than I don't know 16 or I made up that number that means maybe and not and I want to take the absolute value of that what if the absolute value of those two the real and the imaginary component added together goes toward infinity ah greater than 16 that's my infinity then I want to break out of it so the question is did I get to 100 or did I not so look so this is how a picture thought about look I'm gonna come back maybe we'll talk about this again let's see let's see how far I've gotten why not use a for-loop well I could use a fourth don't make a lot of sense but I'm just using a while loop for no good reason okay so now let's just do something I'm just going to say like now if n let's equals if N equals 100 right if we got to the max iterations and I should probably make that a variable then let's make a brightness value brightness value equals zero and then a brightness value equals 255 so let's just see what happens now if I basically with this simple little algorithm figure out whether n kept going and remained bounded or if it went to infinity let's see we should get we should get something well I got a nice like circle that's promising so now let's be a little bit more thoughtful about this maybe we can do some sort of coloring based on the value of n maybe that will get us something better so let's actually say now map n which could go from 0 to 100 between 0 and 255 thank you rob time out okay welcome back there was a critical error in what I had written here which I just didn't notice and thankfully the Internet chat came to the rescue and it's right here in these lines a equals a a plus a B equals B B plus B now let's go let's think about what's going on here if you recall the idea of what we're doing is we're saying Z the new Z e equals the previous Z squared plus C and all of the math that I did here all of this right here this is me figuring out what Z squared is Z squared is a a plus B bi that's what Z squared is so what do I need to do I need to then add to that C but C is always the core original real and imaginary component of where we are in this complex plane so even though I want the new a and B that's then going to get squared for the next iteration the next iteration to get updated right I want the new a and B that's going to get squared over and over to get updated this that's getting added to it see this is really what's standing in for C right here this has to be those original values so I'm going to I'm going to just do this I'm going to say C a equals a and maybe somebody on the internet here can oh I'm gonna post this code to github can submit a pull request with nice variable leanings for all this stuff because I feel like boy this is like I I I have a pet peeve and I'm really doing my own pet peeve which is like all these cryptic variable names that would never make any sense if you were just coming to look at it but it is what it is right now so I need to store those original values and keep that as CA and C B so let's take a look now and see what we get ah this is starting to look like that Mandelbrot set you can see it there now you can see like oh I kind of like it's not exactly centered I've been sort of the wrong place so you know we can fudge with that one we could fund static say like oh let's uh let's kind of like have a little bit of a wider range or you can see I kind of like squished it so I'm gonna make Y the same there you go but it's also still doesn't really look exactly like what you think of when you think of the Mandelbrot set um you know if i zoom in you can see there's some level of greyscale there what I'm doing is I'm essentially saying let me just take the number of iterations that got to right if it got to 100 it's done the number of iterations before it breaks out and gets to before if it goes to infinity how many iterations did it take for it to go to it so first of all one thing I should say that if and equals 100 and this is driving me crazy I really just need a variable here which is I'm going to call max iterations and I'm going to set that equal to 100 because I hate that I'm typing this everywhere so I put this here and I put this here and then put this here so now if n actually gets to max iterations let's say the brightness is zero and now you can sort of see like ah look it's all black in the center and then there's some white kind of on the outside and there's so many different ways you could color stuff here's one way I'd use this sort of mapping way another thing that I could do is I can say n times 16 and I can say modulus 255 so I recycle back down to 0 and you can see oh that looks kind of interesting I know I don't know what that what good that did maybe I need to floor that for to look like what I wanted to look like boy that thought I thought this is how I colored it in a previous thing welcome back it was an awkward cut but so what I was having some trouble figuring out how to color the Mandelbrot set so I think it would be best to look at first actually it's just two completely simplify things so this is what the Mandelbrot set looks like if there's only two possible colors if there is a essentially a background color and a foreground color the background color is set to be 200 so every pixel is 200 unless it's something unless it's a pixel that's made it all the way to the max iterations that's with that's something that's bounded that's within the Mandelbrot set so if it's within the Mandelbrot set it's bright this is 0 it's a black pixel otherwise its brightness is 200 so we can see it so what I want to do is keep that core Mandelbrot set the set itself with a pixel value of 0 and now you could probably Google Mandelbrot set color system and you could probably find all sorts of ways of doing it but thankfully the Internet chat came to my rescue let's just look at one other way of coloring this particular fractal so what I'm going to do is what I want to do is say ok well the iterations got somewhere between 0 and 100 so I'm going to map I'm just be a little quieter now so I think a session quicker the next group I'm going to map the number of iterations from zero to max iterations and I'm going to make that some brightness value between 0 and 255 let's look at that yeah kind of work but you can barely see what's going on there at the edges so we need a way of changing the kind of scale here and actually a better way of doing this would be to actually first just normalize n but which goes somewhere between 0 and max iterations normalize that between a value of 0 and 1 and then I'm going to say bright equals map the square root of that value which also but incidentally has a range between 0 and 1 to between 0 and 255 so if I do that and i refresh this page now you can see this is starting to look more like what you might be used to seeing in a kind of Mandelbrot set visualization and the other thing you'll notice here is I'm just sort of looking at this zoomed out version of the Mandelbrot set the reason why it's zoomed out is because the minimum and maximum range here are between negative two point five and two point five so what if I went between negative one point five and one point five come on now you can see I'm kind of zoomed in on it and what if I went between negative 0.5 and 0.5 and by the way what if I just made these variables so what if I said min X equals a negative 0.5 min y equals and actually I'm just going to say I'm going to say min val is negative 0.5 and Max val is 0.5 and what I'm actually going to do is let's make let's make a min slider I can't do that up here and a max slider Minn slider equals create slider now I need the minimum value to be some value between like I don't know negative 2 point 5 and 0 and I'm going to start with negative 2 point 5 and have a range of increment value of 0.01 and the max value this is kind of silly what I'm doing how I'm doing this but max value is going to be the same but between 0 and 2.5 and we'll start at 2.5 and then what I'm going to do is actually say min value min slider value max slider dot value and I'm going to do this now for a and B now I'm going to map Y as well so now I have two sliders so if I run this program whoops create sliders not defined okay I forgot to include the p5 Dom library so let me include that p5 Dom library and you can see okay there's some sliders down here now now there's sort of an issue which is that I'm done changing the sliders but I'm not seeing anything change so let's figure out what's going on here it is at negative one point five one oh I have no loop in my code because then draw it before I didn't want it to change so I just had no loop so I'm going to take out no loop so that it loops but there really is another issue which is that you know it's I can I can make these changes but look how slow so this pixel operations are really really slow so I'm going to do this just in I'm gonna make like a 100 by 100 oh the other reason why it's so slow is I made this ridiculous 1000 max iterations meaning for every pixel it's going to iterate 1,000 times so that's terrible I don't need let's just do it like 50 times and now you can see like I can start to zoom in two different parts of the fractal it's actually quite fast so now we can see like well maybe I should let it be a little bit bigger and maybe I should let the maximum iterations be 100 and it's still kind of like at a reasonable speed and you can see ice and start to zoom in and we can really get the sense of the fractal this idea of a fractal of the entire shape of the Mandelbrot set there it is up there I can't reach up there because my hands get cut off but you see the idea if you could still here yes okay quietly this has kind of been kind of a crazy video but hopefully you got something out of this talked a little bit about complex numbers imaginary numbers looked at how to set pixels according to what the properties of iterating those numbers happen over a plane of X Y values and looked at a little bit of how we can manipulate it with sliders and what I would love to see from you if you watch this video when I make something with it look at the code think of a more thoughtful way of adjusting the range of doing a zoom a more thoughtful way of coloring them or thoughtful way of exploring how what this algorithm can do and in the next video someday I will not make this till next week I'm going to look at what it means to create something called the Julia set which are little fractal patterns that are kind of like leaves or branches coming off of the Mandelbrot set look at those in the next fractal Mandelbrot Julius that coding challenge video thanks for watching
Info
Channel: The Coding Train
Views: 315,656
Rating: undefined out of 5
Keywords: challenge, coding, mandelbrot, set, tutorial, creative coding, daniel shiffman, nature of code, coding challenge, programming challenge, p5.js, fractals, fractal, programming, p5.js tutorial, algorithms, processing tutorial, javascript, javascript (programming language), p5js, p5 js, mandelbrot javascript, mandelbrot tutorial, mandelbrot source code, mandelbrot fractal, fractal tutorial, complex number, imaginary number, complex numbers explained, mandelbrot set
Id: 6z7GQewK-Ks
Channel Id: undefined
Length: 25min 28sec (1528 seconds)
Published: Mon Jun 13 2016
Related Videos
Note
Please note that this website is currently a work in progress! Lots of interesting data and statistics to come.