 So, in the next section, we're going to go through a review of scientific programming in C and Fortran. It's pretty hard for me to like teach you the whole of both languages and I'm not trying to do that. But what I'm trying to do is show you some example code just so that you get a sense of what's there and also you can always look back in the notes and cheat and copy things out because you know, probably stuff is very similar. So at least you'll have seen it once. In order to kind of walk you through it and give you a problem to look at, we're going to create a Monte Carlo simulator for this Plinko game. You guys ever see the Plinko thing? You go to the fair, county fair or something and there's this game where there's a bunch of pegs on a board and you drop something down the pegs and the coin kind of stutters around and then eventually falls into a spot at the bottom. They do this on the prices right, right? If you get into the middle spot, you like win the big prize, the grand showcase and nobody can ever get exactly on that one spot but anyway, what we're going to do is build a simulator that kind of simulates that motion and the idea is we're going to follow a coin, you drop it from the top, it comes down and each time it hits a peg, we're going to assume that there's an even 50-50 chance that it will go left or right. Now, of course in real life it's not exactly that because the pegs might be slightly off and there's all kinds of other factors but our very simple model just kind of chooses a 50-50 chance when it hits a peg and then it goes down and hits the next peg square on and there's a 50-50 chance of going left or right. So what we can do is drop thousands of coins and simulate thousands of paths through this and at the end, we can count up where all the coins land. So we're going to keep buckets at the bottom and we're going to drop thousands of virtual coins down through this system and we'll see where most of them tend to end up. And they call this Monte Carlo simulation. In fact, it's used a lot in scientific stuff. They call it Monte Carlo simulation because it's like gambling. It's like going to Monte Carlo, you spin the wheel and you see what happens. And here we're spinning the wheel like thousands and thousands of times. Turns out you can use the same strategy if you want to figure out how electrons move through little transistors, you can do the same thing. You shoot the electrons in one at a time and you say, well, I don't know exactly what's going to happen but for this particular track, it's going to bump into an atom and it's going to get hit by a phone on and it's going to go through the oxide and you do all this random stuff. And if you do that for thousands and thousands of electrons, it turns out you can actually simulate it device pretty accurately. That's one strategy for doing simulation. Other strategies involve a lot of calculus and differential equations and all of a sudden you can appreciate the Monte Carlo thing because it's a whole lot easier to think about. So that's my general setup. You can imagine, you know, your advisor hands you this program, tells you that's how it works and here's the code. And what I want to do is not so much explain to you how the Plinko simulator works but I want to kind of show off the features of C-Language in case you saw a program like this that implements something like that. All right, so first of all, when you look at a C-Language program, one of the first things you see near the top are a series of pound-include statements. The pound-include statements are the ways of bringing in the libraries that you need for running a program. And what I've got here are three very standard libraries. STDIO is the standard input output, STDlib is just a bunch of standard library functions and math.h is all the math functions. Of course, Monte Carlo simulator, we're going to be doing a lot of math functions here so we need that. You can bring in other files too. Usually when it's a standard file, you put it in diamond braces. That's the compiler likes that, looks for it in standard places but you can also bring in whatever files you want just by putting a filename in quotes. So whenever you want to bring code in, as if it was included inline, you use a pound-include for that. And that defines all the functions and the variables and stuff. You can also define constants. So in this case, our Plinko is going to have nine levels of pegs. So we've got a system with nine levels. You might write the program, hard-code it with nine everywhere and then your advisor comes back and says, well, I want to try 11 levels. And you're like, don't, you have to go back and fix your program, right? So sometimes instead of hard-coding numbers in, it's better to put parameters in like that. This acts as if it's hard-coded. What the compiler does with the pound-define is everywhere in your code that it sees the word levels, it will literally substitute nine in place of it just before it compiles everything. So all it's doing is a textual substitution of whatever you've got up there, wherever it sees levels. And by convention, in C language, people use all capital letters for that because they want it to be easy to spot in the code where these substitutions are happening. You don't want to get confused. You could define all kinds of stuff and you could redefine the word char in C language and then all hell would break loose in your program because you'd be making substitutions and trying to figure out what the compiler's doing and it's very confusing. So people tend to use all uppercase letters for their pound-defines just to make it real obvious that this is just a text substitution thing. Yeah, and just to emphasize that point, you can see the two spots in my code where I've got the word levels that just gets substituted with nine. So I can size my arrays according to levels and I can loop through the loop according to levels and all that. All right, now we're getting down into the actual code of the program. A main program in C looks like this. It's defined as a function called main and it has to have two arguments, an integer, argc and char, star, star, argv. The stars in C language are references to pointers. In this case, this is a pointer to a pointer of characters. That's how you represent an array of strings, basically, in C language. If you don't understand all that, that's okay. Just copy that because that's what your function prototype needs to look like in main. That's what your C language is and you don't need to worry about that argc and argv stuff unless you actually use the arguments in the program. The arguments, when you call a program in the command line and you give it all the extra words, those are the arguments and argc tells you how many arguments there are in the command line and argv gives you all the different strings for the arguments on the command line. So anyway, you just make a function like that called main and that's your main program and it always returns an int. The integer returns as an integer status code that says whether your program succeeded or failed. So if it returns zero, everything's okay and if it returns anything other than zero, something went wrong and on Unix there's all kinds of different status codes that tell you what might have gone wrong in a program with different numbers that it can return. So you wanna write hello world or whatever? You start with a function like that. All right, now just like in MATLAB yesterday we need to get some input into the program and the way that a lot of people get input into the program, again they prompt the user, they ask them questions and they read things from for example standard input. So the way you can do that in C language there's a printf function, formatted print. Printf in this case I just gave it a simple string, number of drops, the backslash n is a new line. So just read that as a carriage return or a new line. So it's gonna print out number of drops to the question mark and then go down to the next line and then the scanf function is a way of reading in from standard in. Scanf is sort of the opposite of printf. Printf prints out, scanf reads in but it reads in according to a format and the format here is percent d means look for a decimal number and put the result in the word max and scanf at the end returns a value which tells you how many things it was able to successfully scan. So if I'm in good shape it will read a number, a decimal number, it will put it into the variable called max and then it'll return the value one and I'll know if I didn't return the value one then something went wrong. Somebody typed in x, y, z or they didn't type anything or something went wrong. So in this case I'm looking at scanf saying well if it's not equal to one then I print out bad number and then I exit. There's all these different flavors just like yesterday with MATLAB we can see there's an fprintf flavor for printf. Fprintf prints out to a particular file in this case standard error is a way of putting out messages. So but again all of these are very similar. Printf just prints out to the normal standard output. Fprintf with standard error prints out to standard error but in both cases you just give it a string like that bad number or something maybe a new line at the end and it prints out. And then exit, exit one will exit the program and with the status code of one it's kind of like returning from the main program with one. It basically stops your program and signals an error. Yeah and I wrote that down there. So whenever you're ending your program you really should either return zero or exit zero. Exit zero means okay. I always remember it that way. Zero is okay and everything else is failure. One, two, ten, one million and twenty-seven whatever you want to return is a failure. All right now this is how you do a for loop in C language and it's a little different than some other languages. The for loop in C language kind of has three parts to it and they're separated by semicolons. The first part sets up what happens before the loop starts. So in this case it says i equals zero. So at the beginning of the loop it sets i equals zero. And then as it's going through the for loop again and again and again it checks the middle part. It checks to see if i is less than levels plus one. So as long as i is less than levels plus one it keeps going through the loop. And then the last part is done sort of right at the end of the loop to go on to the next version. So in this case it says i plus plus which is the C language way of saying bump the i counter. It's like saying i equals i plus one. People got tired of saying i equals i plus one all the time. So they created i plus plus to increment i. So this is what it's going to do. It's going to start out with the value i equals zero. It's going to run through the loop say count zero is zero. And then it'll bump to the next i one. And then it'll check and see, yep, I'm still got room there so keep going. Count one is zero, count two is zero, count three is zero and it'll keep going all the way through the number of levels that I've defined. And remember way back at the top if I want to change the size of my program I can redefine levels to be 27 and do a different simulation. And this will just keep going as much as it needs to. So all I'm doing there is going through that array of counts and in this case I'm setting all the buckets to empty. Those are the buckets at the bottom of my Plinko thing and I'm zeroing them all out to make sure they're empty. Oh yeah, one thing to point out. In Fortran and in Matlab all the indices start from one but in C language they start from zero. So got to remember like all your arrays start from zero in C language. All right, so here's kind of the meat of my Plinko simulator. This other for loop I start out with a drop value equals zero and I keep going until drop is less than max. So I'm going to keep dropping and dropping and dropping these coins. And each time I increment the drop counter drop plus plus. All I'm doing there is just making sure I'm doing it so many times. So basically we're dropping a coin through and at each point in the levels we're going through all the different levels. The d-rand 48 generates a random number and I'm checking to see if it's less than five or greater than five. If it's less than five then I go to the minus one side and if it's greater than five I go to the plus one side. This is kind of a funny syntax in C language and occasionally a few other languages have borrowed it. It's a really compact way of doing an if statement. So what this does, d-rand 48 generates the random number and checks to see if it's less than five. The question mark says if that's true then use the value minus one and the colon says if it's false then use the value one. So it's a real compact way of writing an if statement. Look at that and if it's true use the value minus one if it's false use the value one. So in our case that's like the coin hit the peg and we're deciding do I want to go left or right? Do I want to go minus one or plus one either way? And in C language you can write really dense code that way I don't know for better or for worse. So what I'm doing is basically with that statement I'm figuring out either plus or minus one randomly and then I'm adding that on to my position. I've got a statement pos plus equals plus or minus one. That means pos equals pos plus one or pos equals pos minus one. So my pos position is going to shift left or right. So you might see like code like that if you're looking through a C language program and I wanted to make sure you've seen the statement before and sort of how that works. By the way as I'm going through if you guys are just if I'm not talking about something and you're wondering what something is feel free to ask but just kind of taking a general tour through C language. So this is that plus plus equals sign that I was telling you about when you say pos plus equals one it's equivalent to saying pos equals pos plus one. Again the guys who wrote C language just got tired of typing stuff out and they invented a kind of a shorter hand notation and that's been borrowed now into a bunch of different languages. So you may have seen that in another language. Okay, so the for loop just keeps going. It keeps dropping coins through and until drop reaches the maximum count. So maybe 500 or 1,000 and that was the parameter that we asked the user for how many drops do we want to do? You could type in 1,000 and then it would go through this loop 1,000 times each time starting at the top, generating a random number and working its way down through the number of levels until it finally reaches the bottom, the certain position. All right, and then at the very end of this program you can see this little block. This is where we're printing everything out. This is the output for our program. First of all, you can see there's a, do I highlight the comment line? So in C language when you want to put comments in your code, the way you do it is with slash star and then some stuff and then star slash. And that's good to know and it's a little tricky because sometimes people forget they have slash star and they start typing a bunch of stuff and they forget to close it off with the star slash or they mistype the star slash. They invert the two characters or something. That comment just stays open. The C language will ignore all of the text until it sees that closing comment, the star slash at the end there. So a lot of times if you don't put that in or if you mess it up then the compiler will just ignore three quarters of your program because it's looking for the end of what it thinks is a gigantic comment. Modern language is now like C++ use two slashes at the beginning of the line or maybe a pound at the beginning of the line. That makes it easier then you just have a comment for the rest of the line. But in C language it stays open until you close the comment like that. So watch out for that. It's good to put comments in your code, right? Otherwise, six months from now, when you put comments in your code you're actually writing a note to your future self. It's like time travel. So because six months from now you'll go back to this program you'll be like, now what was I doing? Especially when there are tricky parts of your code. You want to put a note in there to remind your future self. Hey, don't edit this, don't delete this because it'll cause core dump later or something future self. All right, so underneath the comment I'm printing out a headline statistics and I'm going through again another for loop. I'm going through all the levels in my Plinko program and I'm printing out the values, the results. Again, I'm using the printf statement to print out a string, bucket, and then some decimal number colon and then another decimal number and a new line. So wherever you see the percent d that's gonna get substituted with some decimal value, some integer value. And the two variables that are getting substituted are i and count sub i in the count array the ith element of the count array. So I'm printing out, just like you see over here, bucket zero and then what's the count in bucket zero? Two or whatever. Bucket one and what's the count in bucket one? So forth. So those two variables get substituted in order into the various percent fields. And then at the very end of my program I can either say return zero because main is a function or I can say exit zero which is equivalent. Basically terminates the program and returns the zero status code. Remember zero means okay, that's good. And that status code's important. If your program returns the status code of one and rapture runs your program, rapture will say your program failed. It will tell the user this program failed, right? So you gotta make sure you return a zero exit status code. Otherwise other programs like rapture that depend on your program will say burp, invalid, didn't work, something went wrong. All right, so we got through it. That's the C language code. Now the next step is to actually, if somebody handed you that program you gotta run it, you gotta do something with it. And with C language you have to compile the program down to machine code. So there's a program called GCC for example, the GNU free compiler in C. You can use whatever compiler you want but in here we've got GCC installed. So GCC is the compiler and you can give it some flags and arguments. The dash G argument is important. It says debugging. I wanna turn on debugging so I can get into my program and figure out what the heck is wrong with it. So that's a real important option when you're compiling. The next thing we do is we give it the C language program, plinko.c, that we wanna compile. We tell it to put the output dash O into plinko, program called plinko. So when it's done compiling it will create an executable file called plinko and that's what you run. And then at the very end we added dash LM which is the math library. Your programs depend on other libraries a lot of times. Every pound include that you bring in probably brings in a library. And so at the end you gotta add all those dash LM, dash L rapture dash L whatever when you're compiling stuff to bring those libraries in for your program. All right, so having done that now if I've compiled my program I'll have this executable called plinko and I can run it by saying dot slash plinko. You reason you say dot slash a lot of times people don't have their executable path set up to look in the current directory. So if you say just plinko it may say well I don't know where plinko is and you're like right here dummy dot slash plinko this one right here. So dot slash plinko is a way of saying this plinko executable I just created dot is your current working directory and in the current working directory run plinko and it'll say number of drops and you'll type in 500 or something like that and then it'll go off and start spinning through that loop. And at the end it'll print out the statistics because it gets down to the bottom and it prints out all that printf stuff. So it'll show you bucket zero, bucket one, bucket two and all that. It's interesting because our simulator is not very sophisticated but it kind of works right? I mean I don't know if you've ever been to the carnival and looked at a plinko simulator but when you're dropping like wherever you're dropping the coins tend to kind of pile up in the middle of that plinko simulator. And in fact I think if you know enough math you can figure out it's a Gaussian distribution. So what we're doing is we're doing a Monte Carlo simulation which if we drop enough coins we'll eventually produce the Gaussian simulation which mathematicians will tell you that's the correct answer. So there's our simulator. So just to summarize everything that we just saw and maybe a few other things too this is what the C language program or C language sort of constructs look like. If you want to do a conditional thing if you want to do an if statement in C language it looks like that. You can say if and then some condition and then some statements. And C language also has if like x is greater than zero do this, else if x is less than zero to this and then there's also an all else fails do that. And with C language all those bits of code are all surrounded by curly braces. In other languages like Python and Fortran you don't have that but C language everything gets all wrapped up in curly braces like that. So you have to be careful about those curly braces. There's also something called a switch statement in C language. The switch statement is sort of like an if. It says if x is case one then do this and break. If x is either case two or default then do all this stuff and so forth. So the switch kind of looks at the first value x matches it up against one of the cases and jumps down and runs it. You notice you always gotta break out of a case because otherwise it'll do the statements and just keep going. If I didn't have that break statement there it would do case one and then fall through and do case two and do case three and keep going. So watch out for that. It's another problem. On the looping side of things lots of different ways to loop. You can do a while loop while x is not zero just keep doing that bunch of statements again and again and again. You can do the bunch of statements and then check at the bottom of the loop. Well keep do a bunch of statements and keep doing it as long as x is less than 10. So either the while or the do while form is there. We talked about the for loop setting the condition checking it and incrementing as we go and then there are these statements break and continue. We already talked a little bit about break here. Break breaks you out of whatever you are the middle of doing and continue is sort of like break but it doesn't break you out of the for loop. It'll take you back to the top and have you do it again. So when you hit a continue statement in a for loop it just skips the rest and goes back up to the top and starts over. A lot of times people put that inside an if. They'll start a for loop and they'll say well if this is true then skip the rest of this and go up to the top and keep going again. So those break and continue statements are real useful in loops because they can get you out of loops or kind of take you on to the next case. So that's your cheat sheet of all the different programming statements. I'm gonna switch gears now and kind of show you the same program but now in Fortran you can kind of see how different it is. In Fortran one of the first things you'll notice is that everything is shifted over by six spaces. Everything in your Fortran program starts in column seven and that's because back in the old days in the 1800s like when they used to use computers I don't know if you guys have ever seen these gigantic card punch machines. You ever see that where you basically it's like a giant typewriter that has paper cards that go in the side. You ever been to a computer history museum? No? Well anyway if you went to the computer history museum and you saw the giant keyboard you put in the paper card and it turned out that the first like six columns your program was made up of a series of cards. Each card was one line in your program. So by the, if I wanted to write this whole program I'd end up with a whole deck, a stack of cards representing the program. And they always reserved the first six lines the first six, I'm sorry, first six characters of each line for these kinds of control structures which I'll show you down below. So Fortran's a very antique kind of programming language based on these punched cards that they used to use and we'll talk about some of the control characters like the plus and the C and the 10 in just a minute. But if you're starting your program you say program Plinko and make sure it's over in the seventh column otherwise it won't work. Oh yeah the other thing about punched cards is that punched cards can only go out to about 80 characters. So if your Fortran compiler is really strict and trying to be very old fashioned then it will stop you at 80 characters because that's where the punched cards ran out of space. Modern Fortran compilers of course can go beyond that and some of them do. But some compilers actually force the 80 character limit and they'll give you weird compiler errors if you make long lines. All right now about those funny characters. If you're in the middle of a statement in Fortran I'm declaring my variables here. I've got an integer max and drop and I and pause and I'm declaring all these variables and I'm running into my 80 character limit right? So what do I do when I'm trying to go beyond 80 characters? Well you can continue on the next line but you have to put a plus sign there and it has to be exactly in that spot. So in column six if you put a plus sign or many compilers will let you put any character in that spot usually it's just a plus sign by convention. But any character in that spot says this is a continuation of the previous line. So you can read that as though I'm continuing on integer max drop I pause count levels and so forth. In C language you can just sort of keep going but in Fortran you have to be real careful about the plus sign stuff because of all the punch card. Here's another magic character. If you start with a character in the very first column then it marks the rest of the line as a comment and usually people put a C there like comment kind of reminding you that this is a comment. But again I think most Fortran compilers would say any character in that spot makes it a comment line. So I put a C there and then I said set all counts to zero and that's not programming stuff that's just a note for my future self of what I'm trying to do here. And then finally in C language we had curly braces that kind of helped put all the code together in Fortran when you write a loop you have to use numbers. So I can number a statement like say 10 continue. I can number that statement and then I can set up a loop by saying okay do everything until 10 I equals one go up to levels plus one and keep going blah blah blah. So this is the way you write a loop in Fortran is you have this do continue thing and you have to number the continue statements. So the rest of the space is in between the first column which is for comments and the last column which is for line continuation you have what four other spots there where you can put in line numbers and hopefully you don't have to put too many of them in. Turns out it doesn't matter whether you called that statement one or statement five or statement 10 or statement 999 or whatever Fortran doesn't care you've got four columns there to use numbers and then you just match up all the numbers for your loops. Isn't that interesting this is like a walk through the computer history museum. I forget how many of you guys have actually used Fortran before. No we asked you to okay we asked you yesterday and then I asked you about your grandfathers. All right, all right I remember. Well it turns out that the reason Fortran is stuck around so you may now we're making fun of everybody's grandfathers but the reason Fortran stuck around is because it's actually a very efficient language in terms of math people spent years and years and years developing great math libraries in Fortran and then they decided Fortran was sort of an old language right but it turns out there's tons of code written in Fortran that is very good because of all the math libraries and I wouldn't be a bit surprised if you sit down with your advisor and he says okay here's your code and you're like great is it Python? No, is it Matlab? No it's Fortran. You're like great where's that lecture that where's that Plinko thing that I was supposed to be listening to. All right, a couple of more things now that you know the basic structure of this program. Fortran has variable declarations but it also is old enough that they used to do this thing called implicit declarations. It used to be in Fortran anything that started like in the range of i to n was assumed to be an integer value. So if you created a variable called j, Fortran would assume that's an integer, k is an integer of course right? You actually see a lot of code using ij's and k's and things like that as integers. So in Fortran it'll assume that those are integers. If you pick values like a to h or o to z you get a real number. So if I choose a t for temperature that would be a real number. That's a real easy thing to do. Some people back in the 60s thought that was a great idea but it turns out when you're writing large complex programs that's the easiest way to shoot yourself in the foot is that you declare something that you want to call one thing and it turns out it accidentally makes it an integer. So in every program that I wrote I always turn that off. It's better to be explicit about what you've got. So by saying implicit none that says don't assume anything about my variables I'll tell you about every single one of them. So if I say implicit none, now it's up to me to define all those variables. Integer levels, integer max, integer drop, double precision, r num, all that stuff. And that's safer because that way if I forget to declare a variable the compiler get mad at me it won't assume that it has an integer value or something like that. This is sort of the way of defining constants just like with the pound define in C language instead of the pound define you can set integer levels and then parameter levels equals nine. Parameter is the thing in Fortran that says all right this thing is sort of a constant value but I might change it the next time I compile it. And then I mentioned before about this do loop the fact that you use statements like 10 to kind of tie everything up. So in Fortran I'm going through this loop here for I is one, two, three, four, five and I'm going through and setting all the counts to zero. So in your mind you can imagine this way count one equals zero, count two equals zero, count three equals zero. You remember I said earlier in C language all the indices started from zero and Fortran and MATLAB indices start from one. So that's why we're starting from one here. All right second half of my program. Fortran uses this really crazy notation for things like less than, greater than. You know there's a greater than symbol on the keyboard why not use that? I think back in the old days there wasn't one there. So if you go back far enough it makes more sense. So Fortran has this crazy dot LT and dot LE and all that notation. So here's your cheat sheet of what it means when you're looking at an if statement. In this case I used more of a lengthy if statement to express it. It's a little easier to read. If my random number is less than 5.5, I'm sorry then pos equals pos minus one otherwise pos equals pos plus one. That's exactly what I was doing in C language except in C language it was one line of code and Fortran it kind of is longer. A little more readable but longer. All right so you use all those crazy operators and there's even logical operators for ands and ores and all that. The other thing is when you're writing stuff out Fortran's kind of funny. Fortran has all this crazy stuff for formatting. An easy thing to do if you don't care about formatting is you can say write six comma star. Six is, oh you should know this, six is the unit number for standard out. Everybody knows that right? So when you want to write to the screen you write to six. If you want to read in you read from five and there are all these file descriptors that were hard coded back in the day with Fortran. So anyway you'll see this a lot. When you see people saying write six comma star you can just read that as print f. That's, people use that all the time as just write it out to the screen. Write six comma star as print f. Here I'm writing to six again but now instead of star I'm using a specific format. I'm using format 99 and again you can see I'm using line numbers. So which format? Format on line 99 and that format says I want to print out bucket and then an integer with five spaces and then a colon and an integer with five spaces. So again I'm telling the computer program exactly how I want the output to appear with these letters and integer with this many spaces and all that kind of stuff. And then those are the two values, the i and the counts of i are the two values that get substituted into that format line. So again that's sort of the antique version of the print f. All right and here's your cheat sheet too, similar cheat sheet for Fortran. If you want to write an if statement in Fortran it's similar to C but it doesn't have the curly braces. It's if and then the parentheses then a bunch of stuff and end if. So you use then and end if instead of the curly braces to kind of mark your code. There's an if, then, else if, then and in this case else if is one word. Else and then all else fails you can have those statements too. So those are the if statements. There is no switch statement in Fortran, just if statements but that's fine. There's not really a while loop. This is back in the day before they invented the while loop. So what people used to do was use an if and a go to. I don't know, maybe your programming instructors probably told you never use go to. That's good advice, never use go to except when you're writing a Fortran program because it's the only way to write a while loop. So you can mark the top of the while loop as something like 10 or 20 or whatever the number and you say if x is less than 10 then do a bunch of stuff and then go back up to the top and keep going and keep going until finally you break out of the loop. I think the loop is done. You can do the same kind of thing for a do while thing where you start with a continue statement you do a bunch of stuff and then you check the if at the bottom of the loop just like a do while would and go back up to the top. And then we already saw the for loop where again you're using line numbers to mark the bottom of the loop and going through. The for loop is the start and the end and the increment. So this says go from one to 10 in steps of two. One, three, five, seven, nine. All right, so we made it through the Fortran program too. Shoo! So now we just have to compile it. The GNU Fortran compiler is called G Fortran, the modern one. And again just like the C language program we say G Fortran dash G says I want debugging just like C language, turn on the debugging for me. I give it the name of the program Plinko.f and then I say dash O Plinko. In Fortran you can also have libraries but it turns out you don't need to. Fortran builds in a lot more libraries, the math libraries and everything. So you can add other libraries on in Fortran but most of the time you don't need as many libraries as Fortran builds it in. So now I've got the same thing and you notice it's called Plinko and probably from this point on you can't really tell when I'm running that program Plinko I can't really tell how it was written whether it was written in C or Fortran. On the inside I wouldn't know, it just works the way it works. Just like the other C language version the Fortran version will ask me number of drops and I'll type in 500 and then it'll chug chug chug do its work and then it'll print out the results. One thing you notice because I said I want an integer with five spaces I get a very rigid looking output with spaces in here but it might be slightly different than my C language version. But anyway same stuff and really if I have the same random numbers I should get exactly the same results. Of course my random numbers might change each time I run the program so it changes a little. So now you've seen C and now you've seen Fortran. I want to go back and talk about how we build programs and talk about make files a little bit. We saw make files just a little yesterday and I think it's an important thing for you guys to know because you'll be writing your own programs. If they involve a compiler at all you should have a make file for your program. Why? Because when I'm compiling this program GCC blah blah blah and then I edit the program because there's a bug in it and then I compile it again and then I edit it again and you just keep doing this right? Every time as you're building a program you edit, you compile, you test. You edit, you compile, you test it. You keep going through that loop and if you keep having to type a big long gobbledygook line of complicated stuff it's really irritating, it's easy to get it wrong. Also the more complicated your programs it's not just one line you have to type you might have to do 50 lines like that that you have to type to build the whole thing. So the compiling part can get really complicated in a hurry. Instead of typing all that stuff by hand for the compiling you can just say make and when you say make there's a program on Unix that looks for something called a make file and it follows all the instructions inside of it. So if I say make the make program looks for a make file and the very first thing it finds is something called Plinko and so it says oh okay I'll build that. So how do I build Plinko? The first line says Plinko colon Plinko.c that means Plinko depends on Plinko.c. So if you edit Plinko.c the make file is smart enough to know that you need to rebuild the program. So the make file automatically looks at the dates of all the files and says oh you've just changed the program then if you tell it to make it'll recompile because it knows I need to rebuild this because it depends on that. So make file knows all the dependencies in your code it knows that your program depends on this header file this source file and everything else and the way you tell it is with that colon you say Plinko depends on Plinko.c. Then the next line down you have to tab over and the tab's really important because a lot of times people write a make file and they put in a bunch of spaces because they're copying an example that they see somewhere. If you put in spaces make file gets really mad it has to be a tab. Why? I don't know it was the 70s and it seemed like a good idea at the time right? Who knows what they were smoking back then? But you put in a tab and then you put in the command that you would normally execute to build that. So just like you would have typed on the command line GCC dash G blah blah blah blah. Make file also has a bunch of different syntax so that instead of typing things exactly you can put in all these weird dollar apps and things like that and I'll save that for another day in terms of complexity. But a very simple make file just says Plinko depends on Plinko.c and whenever you need to rebuild it just run this GCC line to rebuild it. You can have other things in the make file too. I also have a target called clean and if I ever say make clean then it'll do that. Clean depends on nothing and when I say make clean it's gonna remove dash F which means force all the dot os and Plinko. So if I had a bunch of dot o files sitting around those are things that are compiled by the compiler it'll clean those up and it'll get rid of the Plinko program and clean everything up. So now I can say make to build my program and I can say make clean to get rid of my program and clean everything up. So very simple make file and you can make it a lot more complicated. All right, so now having done that I can edit my program and I can make and I edit my program and I can make and you just keep doing that and it's a whole lot easier because I don't have to type all that gobbledygook and I don't have to remember, wait did I recompile that? No, if I just say make it'll either do nothing or recompile everything or whatever it needs to do to make it. See if you do make twice, no changes does nothing and then finally I can say make clean at the end and it'll clean everything up it'll remove the dot os and the Plinko whatever I told it to get rid of and clean everything up. All right, you're almost ready for your lab assignment. Almost. What happens when somebody gives you a program and you finally manage to get it to compile and you try to run it and it doesn't work? What happens then? So suppose I type Plinko and it does this you type in number of drops and it says segfaultcordump. You guys ever see that segfaultcordump? Yeah, so that basically means something horribly wrong in your program you're probably trying to address memory that doesn't exist or using a null pointer or something and the program just can't continue it doesn't know what to do so it just stops, dies. So at this point you gotta figure out, well, all right get it in, get it up on the rack and figure out what went wrong. So there's a program in Unix called GDB it goes along with GCC and G Fortran it's the GNU Free Debugger so it's the debugger that works with all of the compilers and if you've compiled remember we talked earlier about minus G so if you compiled with minus G then you can use GDB and it'll work great. So GDB Plinko will start up GDB give you a little GDB prompt in parentheses and you can type in some simple commands one simple command is L and it will list your program out so if you type L, you'll see the program and you can remind yourself, oh yeah line 13 was the printf function you can tell it to stop there and run it and so forth so L lists your program if you wanna tell it to stop somewhere like line 13 you can say break break 13 or B I think works too but anyway you can say break 13 and it'll set up a break point so that when you run the program it'll stop there and it'll let you check everything out before you continue on. All right so I've got this break point now if I say run it'll run the program and it'll stop at 13 waiting for me to do something I can look at some variables I can print some stuff out I can do N, N is next if I type N it'll do the next statement and then stop do the next statement and then stop so you can kinda walk your way through the program just by saying N, N, N, N one statement at a time when I say N here it executes printf and you can see it saying number of drops and then it stops at the next statement so if I say N again it'll wait for me to type something and then continue on so when I say N again now it's doing the scanf and it's just sitting there waiting I type 500 and then it's done with the statement and it continues on so I'm kinda walking my way through the program and I can convince myself as I'm saying N that everything's working I can get into a loop like this and see oh okay I is zero what does count look like I is one what does count look like and I can keep going next, next, next through the program and I can convince myself next, next, next and if I print P is print if I P print I then I can see oh okay now I'm at the case where the loop is one and the loop is two and the loop is three so you can print stuff out and you can figure out like where you are and what's going on in the program and why it's core dumping or hung up or whatever you can also do really fancy stuff with there's a lot more to canoe debugger you can do things like say break at 24 if drop equal equal three which is really cool because that way you can do a bunch of stuff and it'll get halfway into the loop and then it will break as opposed to you going next, next, next until you're blue in the face right so you can do things like that C is for continue when you say C it'll continue to the next break point or to the end of the program so for example it continues until it hits that next break point stops and then at that point I can print out other variables drop and so forth so in general this is your little cheat sheet for canoe debugger if you say L and give it a line number it'll list your program if you say break and give it a line number it'll stop you can say run and give it some command line arguments it'll run your program you can say N for next and S for step and C for continue and P for print and all that so that's your cheat sheet of things when you're stuck inside canoe debugger and you're wondering what to do these are the commands that you can use to work it out all right so it's time to do a lab assignment and you can work your way through it yourself this is going to be you're going to love this you got to really slog your way through this one this is great so the congratulations you've inherited a program that almost works so this is the situation you're going to face where the last student grad student or whatever wrote a program and your advisor says why don't you start with this and then go from there and your advisor doesn't know because he hasn't tried it but it turns out when you try it it's completely broken it doesn't work first of all you can't get it to compile and then second of all when you actually do get it to compile it doesn't work right so you've got to figure out you've never seen this thing before and you've got to figure out what it's doing how to get it to compile and how to make it work um... this program is a lot like the plinko program that we looked at but it's a little different it's a letter frequency counter um... so the idea is you run this program dot slash letters and it'll say type in a sentence and you type in hello world and then it'll go through all the letters in that sentence that you typed and it'll count up statistics so for one thing it'll count that there are two words it ignores punctuation by the way uh... just looks at alphabetic characters um... but it'll count that there are two words hello and world so it prints out two words and then it prints out the letter frequencies there's one d there's one e and you know two o's and three l's and goes through and counts up all the letter frequencies so that's what it's supposed to do and your advisor will swear to you that it works and it does that and the last student had it working and he'll say i don't know what you i don't know what your problem is that you can't make it work right uh... so alright that's your challenge you're like i can make it work i can make anything work so what i want you to do is download one of these two either one you can use wget and then type in that path and uh... either one of those will work wrapped letters dot c or letters dot f if you prefer c-language use letters dot c if you want to walk on the wild side with a punch card time machine then use the letters dot f for fortran either one your first job is going to be to make a make file and that should always be your first job someone hands you a program that you have to compile you say well i'm not going to do it by hand i'll make a make file so i want you to create a make file to compile either letters dot c or letters dot f first job and then i want you to use the make file to compile it and as soon as you try to compile it you're gonna find there's errors in the program so you're gonna go through and at least get it to compile and once you get it to compile and run it you're gonna find it doesn't work and then i want you to get into the debugger and try to figure out why it doesn't work and at the end of this you will have done all of that you will have made a make file you will have fixed the program to the point where it compiles you will have gotten into the debugger you will have figured out everything that's wrong with the program and you'll have a working program that looks like this so let me walk you through the solution that i've got for this particular assignment so i'm in my bootcamp twenty twelve directory and i've got no where am i i was in the right directory alright so there's two flavors of this exercise i'll just walk through the sea language version because i think most people were using that so there's a sea language version here and uh... i'll just copy that uh... because this is sort of the solution already let me make a new directory and copy letters dot c into new so i've got this program now letters dot c and i've got to try to make it work so the first thing that i want to do is create myself a make file because i'm going to be compiling it again and again and again it just makes it easier to have the make file so i don't have to type a bunch of crap so my make file i say i've got a program called letters dot uh... that depends on letters dot c and then the next line down i tab over the tabs real important otherwise make it's all mad at your file and then i say what my compile command is going to be gcc dash g remember dash g is important because i want to debug this program so always put the dash g in there to get the debugging info i think a few of you might have stumbled into that in gdb gdb wasn't showing you anything useful it's because you you're missing the minus g option i'm going to compile letters dash c and put the output into a program called letters and uh... put in the math libraries or whatever else i need i'm also going to make myself a clean target and the clean target just says if i want to start over i can get rid of all the dottos if there are any there won't be in this case and then the word uh... the program letters that i compiled so that's my make file and as long as it's called make file with the capital m like you see here and as long as it's in the same directory as my program uh... and as long as it has that format with the tabs and everything that we talked about then i'll be all set to go so now i can say make and it goes ahead and runs the compiler program and and uh... shows me all my errors now that it's good that i got to make file because i'm gonna be making this a few times i gotta gotta go through each one of these things always start at the top because when when c-language or any compiler encounters an error it'll tell you the error and then it'll try to move on and sometimes that error causes another error which causes another error and if you start at the bottom you'll be like hopelessly confused so start at the top and fix the first error and keep going until they till you try it again at some point alright so the first thing it tells me is that online twenty nine there's uh... a variable called n words it says n words is undeclared so i'll go into my editor and i go to line twenty nine and it tells me that the n words here is undeclared so i have to declare all my variables but i'm like wait a minute right up here it says int n words equals zero int n words equals zero and yet it's telling me n words is undeclared that is like the craziest thing in the world because it's declared now you notice in this particular editor just for readability i turned off syntax highlighting a lot of editors have syntax highlighting build into them so you can kind of see what's going on in a file syntax highlighting is a very good thing uh... let me show you another view of the same thing we go into the assignments and see and new and we pull up my solution or my uh... assignment this is what you know this is your brain on drugs this is your brain on syntax highlighting syntax highlighting will will highlight various key words so you notice like all of your variable declaration types like int at the top int int char int those are all in green you notice words like four and while are all in red you notice all of your your uh... character strings are shown here in purple so it's really easy when you're looking at something with syntax highlighting to see all the parts of your program you can see it the way the compiler sees it this is where the compiler is looking at your program and one of the other things that the compiler does is it draws all comments in blue so right here for example this is a comment it's highlighted in blue and up here we have some comments that are highlighted in blue and you notice this is highlighted in blue as far as the compilers concerned that declaration is a comment why is it a comment you remember in c-language comments start with slash star and they keep going and keep going and keep going until it finds the closing star slash that's a really easy mistake to make in c-language you have a comment that sort of goes and goes and goes and consumes your whole program in this case it consumes the variable declaration and it's like dang it i didn't want it to do that uh... i could do one of a couple of things i could i can end the comment here and then all of a sudden now you notice it's colored differently so as soon as i added that closing comment there int n words equals zero shows up as if the compiler recognizes it some people also put the used to my v i some people also put the uh... star slash star slash at the end of each line and slash at the beginning just to avoid problems like that uh... so you can also do your comments like that and try to keep them one line at a time uh... but anyway it doesn't really matter the the important thing is uh... it's actually nice to have a syntax highlighter when you're very confused about something because it'll show you what the compiler scene so let me compile again and you notice i get a little bit further now it's telling me the air is at line thirty one and it's saying it expected a semicolon so at line thirty one it's saying it expected a semicolon and you notice there is no semicolon and the compiler saying it expected a semicolon it's telling you what the problem is in c-language every statement has to have a semicolon at the end of it you can see that on the line above there's a semicolon but there's not one here so that's okay i can fix it and then i make again it's telling me letters is undeclared at line thirty five and so i go to line thirty five and it's saying c greater than zero c less than letters i say wait a minute i thought i had letters i use that somewhere and if i go to the top of my program and i search for letters it's there right but it's actually n letters so all right i forgot it was supposed to be n letters so everywhere else i was smart enough to say n letters but not there so i'll fix that and make again i'm getting further almost there line forty seven it doesn't like uh... terminating quote character so forty seven uh... oh okay that's because it's telling me i didn't terminate the string and yeah it's right i'm missing a quote character remember with print f i have a string that says what i want printed out letter character uh... some number new line and then these the next things on the the rest of the function call those are the things i want substituted in place of the percents i was missing a quote character just like the compiler said and i make now it finally works hurray now i can run it so i type letters and it's not doing anything but i can type that's okay hold on hello world it's not doing anything now people ask me why is it doing anything and the answer is i don't know ask the program right how do you ask the program you get into gdb when something doesn't work your friend is gdb you say gdb letters and if you say l it'll show you your program so kind of reminds you what's there i'm gonna set a breakpoint at line twenty two because i want to get here figure out what's going on it should say type in a sentence i'm gonna run and i'm not even getting to line twenty two where the heck am i if i hit control c it will tell me where i am it shows me i'm at line nineteen i haven't even gotten to line twenty two yet and if i step remember use n for next next next next next next next next i'm in this loop where it's going through initializing the count and if i print out i it's zero and if i go through a few more times and print out i it's still zero it's like stuck here never going on in the loop what's going on for i equals zero starts at zero while i is less than n letters it's true i aw dang supposed to be i plus plus on a loop right supposed to bump to the next value on the loop alright so i can quit that and i'll edit oops not letters but letters dot c so now i go back there and fix my loop so i'll put in the plus plus so see a loop is supposed to look like that for i equals zero i is less than whatever and then i plus plus that moves it on to the next to the next value so now i have to make again right because if you go try to run your program again nothing's changed if i'm running letters it's still stuck that's because i have to make again i have to make the brand new copy and now when i run letters it's actually doing something different so i can type in a b c d e f and well alright it's sort of there so it's sort of working now i can see it saying a b c d e f there's two words but when i go to print it out it just tells me there's a b and there's a d and there's an f dang it alright let me see what's going on there why isn't it working i don't know ask gdb so in gdb i'm gonna go through the whole program and i'm gonna break down here at like forty four run it and i'm gonna type a b c d e f now at this point i'm about to print out and words which is too that's good and i'm also about to print out the count i look at the count and you can see a b c d e f is good so it should work so now continue dang it the counts are right but it's not printing it what's going on let me take a look more closely i'm gonna run it again start over a b c d e f and now this time i'm gonna step through i'm stepping through and i'm printing out i is zero and i'm gonna print out count sub zero or i can also say count sub i okay one so here's my print statement i can even print out things like i plus a kind of check everything that's the character ninety seven which if you look up in the eski table is a lowercase a right so and i can print out count sub zero and again i convinced myself that that's it all right so i printed out wait a minute it's saying letter b and it's saying one like i thought i convinced myself that i was about to print letter a and it printed out letter b and now when i'm going through my count if i print out i it's a two like i went from zero to two and it printed out letter b like what the heck but if you look real closely we go back through this okay i'm at two and i do that and now i'm at three and now i'm at four dang it like the i counters all goofed up and if you look real closely you'll see right here there's an i plus plus so when i was printing stuff out i printed out i plus a and then i printed out i count sub i and then the plus plus after it says right after i print out the count go ahead and move i and then when i got up to the top of the loop it moved it again so every time through the loop it was kinda bumping i by two bumping it once when i wanted it to and bumping it one more time when whoever wrote this program screwed it up so anyway go back to my program and take that out and try it again hurray and now we can try other cases because i never trust my program everything works so that's how you build and debug and that's like the bread and butter of what you do when you're building when you're doing software right uh... sometimes you get a program that you inherit that you didn't have anything to do with and you got to figure it out sometimes you created the mess but it's the it's the old you it's six months ago you and hopefully six months ago you wrote some enough comments to kind of help future you figure it out uh... but that's it you make yourself a make file to make it easy to compile you get into the debugger and you walk through your program line by line and uh... check every square inch of it there are so many programs with so many bugs because nobody looked you know you just assume if your program runs that it works properly really whenever you write a program you should go through watch it execute once if you if you make if you convince yourself once that everything looks good then you're probably in pretty good shape but uh... a lot of people just write code and then assume it's going to work perfectly the first time out it never does