WEBVTT X-TIMESTAMP-MAP=LOCAL:00:00:00.000,MPEGTS:900000 00:00:02.322 --> 00:00:03.030 CARTER ZENKE: OK. 00:00:03.030 --> 00:00:07.330 Well, hello, one and all, and welcome to CS50's very first section. 00:00:07.330 --> 00:00:10.560 My name is Carter Zenke, one of the course's preceptors here on campus. 00:00:10.560 --> 00:00:14.460 And the goal of sections is to help you bridge the gap between lectures 00:00:14.460 --> 00:00:15.940 and problem sets. 00:00:15.940 --> 00:00:17.850 So let's say there's something in the lecture 00:00:17.850 --> 00:00:20.070 that you think you might have understood, 00:00:20.070 --> 00:00:23.910 but now it's your turn to try to put that idea into practice actually 00:00:23.910 --> 00:00:25.620 writing some code along the way. 00:00:25.620 --> 00:00:27.820 That is the goal of these sections here. 00:00:27.820 --> 00:00:33.060 So this week's section is on our very first week in CS50, week one. 00:00:33.060 --> 00:00:37.290 We're moving from Scratch into learning this language called C that you use 00:00:37.290 --> 00:00:40.410 to build increasingly complex programs. 00:00:40.410 --> 00:00:42.150 So, again, my name is Carter Zenke. 00:00:42.150 --> 00:00:44.970 If you'd like to reach out to me at any time after this section 00:00:44.970 --> 00:00:47.820 or while you're taking CS50x online, you can reach out to me 00:00:47.820 --> 00:00:52.830 here at this email, carter@cs50.harvard.edu. 00:00:52.830 --> 00:00:54.430 But what's on the agenda today? 00:00:54.430 --> 00:00:57.010 So today, we have a few different things from lecture. 00:00:57.010 --> 00:01:00.070 We have this idea of variables and types, 00:01:00.070 --> 00:01:03.500 how we store information inside of our programs. 00:01:03.500 --> 00:01:06.520 We also have an idea of taking input from a user 00:01:06.520 --> 00:01:09.520 and trying to print some of those values back out to the user 00:01:09.520 --> 00:01:11.530 as they use our program. 00:01:11.530 --> 00:01:15.130 Later on, we'll see these ideas of functions and loops 00:01:15.130 --> 00:01:19.300 and conditionals allowing us to design ever more complex programs. 00:01:19.300 --> 00:01:21.520 And finally, towards the end, we'll work a bit 00:01:21.520 --> 00:01:25.210 on those very first steps in Problem Set 1 to help you get started 00:01:25.210 --> 00:01:29.660 and go on your way to completing that very first problem set. 00:01:29.660 --> 00:01:34.130 So let's dive in here into our first topic, this one called Variables 00:01:34.130 --> 00:01:35.480 and Types. 00:01:35.480 --> 00:01:38.380 So, as we said before, a variable is simply 00:01:38.380 --> 00:01:42.400 some way of storing information inside of a computer. 00:01:42.400 --> 00:01:44.980 But I'm curious, for those of you who are here, 00:01:44.980 --> 00:01:49.930 how would you describe a variable in a single sentence? 00:01:49.930 --> 00:01:52.600 Let's say we have a contact application. 00:01:52.600 --> 00:01:55.780 We're trying to store information about, let's say, different people 00:01:55.780 --> 00:01:57.430 we're in contact with. 00:01:57.430 --> 00:02:03.330 How would you describe what a variable is in a single sentence? 00:02:03.330 --> 00:02:05.110 I'm seeing a container. 00:02:05.110 --> 00:02:06.360 Certainly, that's a good idea. 00:02:06.360 --> 00:02:08.490 A variable is a container for some value. 00:02:08.490 --> 00:02:13.440 It could hold some piece of information, like a number or a character. 00:02:13.440 --> 00:02:15.510 Any other ideas too? 00:02:15.510 --> 00:02:18.990 Containers, something like a group. 00:02:18.990 --> 00:02:21.030 I think that idea could work. 00:02:21.030 --> 00:02:23.730 It's something like trying to put some piece of data, 00:02:23.730 --> 00:02:28.260 like a number or a character or even some word, into a particular container, 00:02:28.260 --> 00:02:31.260 maybe something we could call a group and often, 00:02:31.260 --> 00:02:34.540 if I could add on to the idea, is giving it some name. 00:02:34.540 --> 00:02:38.020 So I see someone else in the chat has said, it's a name given to some value. 00:02:38.020 --> 00:02:40.200 So often we'll have these containers that 00:02:40.200 --> 00:02:42.210 will have some values inside of them. 00:02:42.210 --> 00:02:46.060 And a variable allows us to give that value a name. 00:02:46.060 --> 00:02:48.880 So visually, you could think of a variable a bit like this. 00:02:48.880 --> 00:02:52.320 Let's say we have a container represented by this black box here. 00:02:52.320 --> 00:02:56.490 And inside is some value, like this value 0. 00:02:56.490 --> 00:03:01.140 But it's not quite a variable yet, really any place in our computer 00:03:01.140 --> 00:03:02.950 could have some value. 00:03:02.950 --> 00:03:07.270 But what makes this piece special is that it has a particular name. 00:03:07.270 --> 00:03:11.020 In this case, if we're building a contacts application, we could say, 00:03:11.020 --> 00:03:13.830 this variable's name is calls. 00:03:13.830 --> 00:03:16.920 So this variable, this container for some value, 00:03:16.920 --> 00:03:19.530 now has this name called calls. 00:03:19.530 --> 00:03:22.210 And calls could store really any particular value. 00:03:22.210 --> 00:03:23.430 That's why it's a variable. 00:03:23.430 --> 00:03:25.510 This value could change over time. 00:03:25.510 --> 00:03:28.020 Maybe I'm calling my sister, for instance. 00:03:28.020 --> 00:03:30.780 And maybe I'm tracking how many times I've called her. 00:03:30.780 --> 00:03:33.160 So I've called her currently 0 times. 00:03:33.160 --> 00:03:34.410 But let's say I call her. 00:03:34.410 --> 00:03:37.355 That value gets updated from 0 now to 1. 00:03:37.355 --> 00:03:42.240 It could also be 2 later on in time, maybe 3 or so on. 00:03:42.240 --> 00:03:47.310 We could think of this variable as a name for a value that can change. 00:03:47.310 --> 00:03:49.530 In this case, our variable is named calls. 00:03:49.530 --> 00:03:53.850 And it has this value, first 0, then 1, then 2, then 3, 00:03:53.850 --> 00:03:57.190 that is changing over time. 00:03:57.190 --> 00:03:59.310 So this works visually. 00:03:59.310 --> 00:04:04.110 But there's also some syntax we can use in this new language called 00:04:04.110 --> 00:04:07.380 C to actually give us this variable, give us 00:04:07.380 --> 00:04:10.350 this value in memory in our computer. 00:04:10.350 --> 00:04:13.170 And syntax, as you'll learn, is simply the characters 00:04:13.170 --> 00:04:18.380 we type to write some C code and tell our computer what to do. 00:04:18.380 --> 00:04:21.700 So, in this case, if we wanted to have this variable called calls, 00:04:21.700 --> 00:04:24.320 we'd simply write something a bit like this. 00:04:24.320 --> 00:04:31.330 We'd say int calls equals 3 and a semicolon at the end, 00:04:31.330 --> 00:04:35.283 int calls equals 3 followed by a semicolon. 00:04:35.283 --> 00:04:38.200 And I'm curious, for those of you in the room who maybe have seen this 00:04:38.200 --> 00:04:46.160 from lecture, what are the three parts you notice inside of this syntax here? 00:04:46.160 --> 00:04:49.610 What parts do you notice here? 00:04:49.610 --> 00:04:56.565 I'm seeing a type, some name for the variable, maybe its value. 00:04:56.565 --> 00:04:58.190 And I think we're on to something here. 00:04:58.190 --> 00:05:02.260 So if we break this down into smaller pieces, this single line of syntax, 00:05:02.260 --> 00:05:05.120 we'll see there are really three important parts to it. 00:05:05.120 --> 00:05:07.840 So the first part is the name for the variable. 00:05:07.840 --> 00:05:12.670 What are we going to call this place in memory that now has this value 3? 00:05:12.670 --> 00:05:17.020 Well, as we see on the right, we have this container that has the value 3. 00:05:17.020 --> 00:05:18.880 And up above, it has this name called calls. 00:05:18.880 --> 00:05:22.540 So we can say that when we type int calls equals 3, 00:05:22.540 --> 00:05:26.920 we're telling our computer that this variable is named calls. 00:05:26.920 --> 00:05:30.220 Now, there's one more piece, also the type, as somebody else said. 00:05:30.220 --> 00:05:35.620 So here we say, what kind of value does this container store? 00:05:35.620 --> 00:05:37.990 We've given it a name called calls. 00:05:37.990 --> 00:05:41.770 But then we have to define, what kind of value could I put in this container? 00:05:41.770 --> 00:05:46.600 Is it going to be maybe a character or an integer, as in a whole number, 00:05:46.600 --> 00:05:48.160 or something else entirely? 00:05:48.160 --> 00:05:50.450 That's the type of this variable. 00:05:50.450 --> 00:05:55.910 And we often define that up front, up first, even before the variable name. 00:05:55.910 --> 00:05:58.880 And then finally, as somebody else pointed out here, 00:05:58.880 --> 00:06:04.820 we have the actual value for this variable, in this case, the value 3. 00:06:04.820 --> 00:06:08.600 Now, there is still one piece of syntax, actually maybe two, 00:06:08.600 --> 00:06:10.100 we haven't quite talked about yet. 00:06:10.100 --> 00:06:15.080 We've seen the type, the name of this variable, and the value. 00:06:15.080 --> 00:06:19.360 But what have we not talked about yet in this syntax? 00:06:19.360 --> 00:06:21.943 I'm seeing that equal sign. 00:06:21.943 --> 00:06:23.860 So this equal sign, we haven't yet touched on. 00:06:23.860 --> 00:06:25.630 But it does have a special name. 00:06:25.630 --> 00:06:29.040 It's probably less so an equal sign and more so 00:06:29.040 --> 00:06:31.650 what we'd call an assignment operator. 00:06:31.650 --> 00:06:35.490 So I see some folks saying in the chat too, this is our assignment operator. 00:06:35.490 --> 00:06:40.170 We're not so much saying that this value, this calls here, is equal 00:06:40.170 --> 00:06:44.040 to 3 as much as we're saying we've created some container 00:06:44.040 --> 00:06:45.630 and called it calls. 00:06:45.630 --> 00:06:48.900 And we're going to assign the value of that container 00:06:48.900 --> 00:06:55.590 to be equal to 3, so difference between equals and the assignment operator 00:06:55.590 --> 00:06:56.230 here. 00:06:56.230 --> 00:06:59.490 And if we wanted to read this in terms of just plain old English, 00:06:59.490 --> 00:07:01.690 we could do so a bit like this. 00:07:01.690 --> 00:07:05.280 We could say we're going to create an integer named 00:07:05.280 --> 00:07:09.690 calls that gets the value 3. 00:07:09.690 --> 00:07:15.210 So now that we've seen this overview of variables and, in this case, 00:07:15.210 --> 00:07:17.950 types as well, I want to ask you a question. 00:07:17.950 --> 00:07:23.010 Let's say I give you this variable here, a variable called country_code. 00:07:23.010 --> 00:07:26.130 And it looks a bit like this on the right. 00:07:26.130 --> 00:07:31.920 I'm curious, how would you read the code on the left-hand side in plain English? 00:07:31.920 --> 00:07:34.170 Based on what we saw before, how might you 00:07:34.170 --> 00:07:36.930 read the code on the left-hand side? 00:07:36.930 --> 00:07:39.210 What exactly are we doing here? 00:07:42.990 --> 00:07:46.140 So I'm seeing a few folks saying something a bit like this. 00:07:46.140 --> 00:07:48.690 So if we had this syntax on the left-hand side, 00:07:48.690 --> 00:07:50.670 we could read it exactly as follows. 00:07:50.670 --> 00:07:55.160 We could say, we're going to create an integer that is named country_code. 00:07:55.160 --> 00:07:59.180 And that container that is an integer called country_code, 00:07:59.180 --> 00:08:02.730 that will get the value of 65. 00:08:02.730 --> 00:08:04.910 And if you're curious here, country_code refers 00:08:04.910 --> 00:08:08.840 to a cell phone number or a regular phone number where oft, 00:08:08.840 --> 00:08:12.080 if you're calling somebody outside of your own home country, 00:08:12.080 --> 00:08:13.880 you prepend some number. 00:08:13.880 --> 00:08:16.460 Like for the United States, it's the number 1. 00:08:16.460 --> 00:08:21.492 For, I believe, Singapore, it is the number 65 in this case. 00:08:21.492 --> 00:08:23.450 So if you wanted to call somebody in Singapore, 00:08:23.450 --> 00:08:26.180 you'd call them using this country code, 65, 00:08:26.180 --> 00:08:29.610 and then add their phone number right afterwards. 00:08:29.610 --> 00:08:36.110 Now, one question we often get is, why do we begin all of these statements 00:08:36.110 --> 00:08:38.330 about variables with this type? 00:08:38.330 --> 00:08:40.010 Like, here we have int. 00:08:40.010 --> 00:08:44.310 And it's the very first thing we say when we declare or initialize 00:08:44.310 --> 00:08:45.600 some variable. 00:08:45.600 --> 00:08:46.500 But why? 00:08:46.500 --> 00:08:49.120 And I'm curious about your idea for this too. 00:08:49.120 --> 00:08:50.670 Feel free to chime in. 00:08:50.670 --> 00:08:56.280 Why do you think the very first thing we write is the type of this variable? 00:08:56.280 --> 00:08:57.630 Why do we even care about types? 00:08:57.630 --> 00:09:01.350 Why do we even have them in this case? 00:09:01.350 --> 00:09:05.110 I'll give you a minute to think here. 00:09:05.110 --> 00:09:07.465 Why do we care about types? 00:09:11.030 --> 00:09:12.410 So I'm seeing a few ideas. 00:09:12.410 --> 00:09:16.600 So someone says that it will determine what we can make the variable do 00:09:16.600 --> 00:09:18.220 or what aspect it possesses. 00:09:18.220 --> 00:09:19.340 I like that idea. 00:09:19.340 --> 00:09:23.860 So certainly we can do some things with numbers, like add them up, 00:09:23.860 --> 00:09:27.640 for instance, that we couldn't do with characters. 00:09:27.640 --> 00:09:31.480 Someone else says, it tells us how to handle that value in memory. 00:09:31.480 --> 00:09:32.720 That's also a good idea. 00:09:32.720 --> 00:09:37.390 So you could think of, perhaps, maybe different numbers and characters 00:09:37.390 --> 00:09:41.740 are represented differently underneath the hood inside of our computer. 00:09:41.740 --> 00:09:48.710 As we saw in lecture, for instance, the letter A corresponds to the number 65, 00:09:48.710 --> 00:09:52.210 which in binary is something like-- well, I don't know the exact binary. 00:09:52.210 --> 00:09:53.660 But it represents something. 00:09:53.660 --> 00:09:56.860 It tells us how to represent that character in memory. 00:09:56.860 --> 00:10:03.070 Other ideas here too, to reserve enough space to store that data type. 00:10:03.070 --> 00:10:05.330 That's also a good idea as well. 00:10:05.330 --> 00:10:08.080 So why don't we give a bit of a concrete example 00:10:08.080 --> 00:10:10.460 as to why we really care about these types. 00:10:10.460 --> 00:10:15.020 So here I'm trying to store this value, 65, as part 00:10:15.020 --> 00:10:17.060 of this variable called country_code. 00:10:17.060 --> 00:10:20.240 But as we just discussed, everything in our computer 00:10:20.240 --> 00:10:22.880 is stored in terms of zeros and ones, these little bits 00:10:22.880 --> 00:10:26.270 that we can use to represent all kinds of things. 00:10:26.270 --> 00:10:31.260 And for the decimal number 65, well, if we want to represent that in binary, 00:10:31.260 --> 00:10:36.830 it would be exactly this, 01000001. 00:10:36.830 --> 00:10:39.590 This is the binary, what our computer is actually 00:10:39.590 --> 00:10:43.780 storing, to represent that number 65. 00:10:43.780 --> 00:10:46.580 So underneath the hood, we could kind of see it like this. 00:10:46.580 --> 00:10:49.660 We have this value, the decimal number 65, 00:10:49.660 --> 00:10:54.580 and our computer is actually storing what you see underneath, 010001, 00:10:54.580 --> 00:10:56.180 and so on. 00:10:56.180 --> 00:11:01.990 But let's say we actually changed the type of this variable from an int 00:11:01.990 --> 00:11:09.580 instead to what we call a char, or a character, here representing not 65, 00:11:09.580 --> 00:11:13.060 but now the letter A. Anyone else have an idea 00:11:13.060 --> 00:11:21.850 of why if we change the type from an int to type char, we get A instead? 00:11:21.850 --> 00:11:22.555 Any ideas? 00:11:25.390 --> 00:11:28.150 So I'm seeing somebody saying, we learned from lecture 00:11:28.150 --> 00:11:31.240 this idea of ASCII, the American Standard Code 00:11:31.240 --> 00:11:32.740 for Information Interchange. 00:11:32.740 --> 00:11:37.870 And the ASCII folks, they decided that decimal number 65, when 00:11:37.870 --> 00:11:41.440 you want to think of that value as instead a character, 00:11:41.440 --> 00:11:46.450 it represents the letter A. So here with this code on the left-hand side 00:11:46.450 --> 00:11:52.483 I'm saying, let's store that decimal value 65 but treat it as a character. 00:11:52.483 --> 00:11:54.400 And if we say we are representing a character, 00:11:54.400 --> 00:11:56.680 well, I'm not going to get that decimal number anymore. 00:11:56.680 --> 00:11:58.722 I'm going to get the actual character represented 00:11:58.722 --> 00:12:00.880 by that decimal number, which in this case 00:12:00.880 --> 00:12:05.230 is A. As we'll see later on in the course, these decisions about types 00:12:05.230 --> 00:12:08.770 actually influence how much memory we're going to use 00:12:08.770 --> 00:12:13.870 and how we actually store the data on our computer underneath the hood. 00:12:13.870 --> 00:12:16.370 So more on types a bit later. 00:12:16.370 --> 00:12:17.530 But let's keep going here. 00:12:17.530 --> 00:12:20.113 And let's see what we can do that's more interesting than just 00:12:20.113 --> 00:12:23.290 focusing on single pieces of variables, like single variables themselves. 00:12:23.290 --> 00:12:27.500 We can also try to add things up or change variables over time. 00:12:27.500 --> 00:12:29.320 And there's a few operators you might want 00:12:29.320 --> 00:12:32.490 to know to be able to actually do that kind of work. 00:12:32.490 --> 00:12:35.460 So, for instance, here are a few of them. 00:12:35.460 --> 00:12:38.210 We have this variable now called calls. 00:12:38.210 --> 00:12:40.280 And we're setting it to that value 4. 00:12:40.280 --> 00:12:43.770 But let's say later on I want to add 2 to that value. 00:12:43.770 --> 00:12:46.430 I could use this operator here, that plus sign, 00:12:46.430 --> 00:12:52.040 to say take calls, add 2 to it, and reassign it to that container 00:12:52.040 --> 00:12:53.840 that we called calls. 00:12:53.840 --> 00:12:57.110 And then later in my program, maybe they could subtract from calls. 00:12:57.110 --> 00:13:00.950 I could say, well, let's make calls 1 less than what it currently is. 00:13:00.950 --> 00:13:03.170 To do that I could say, let's take calls, 00:13:03.170 --> 00:13:08.690 subtract 1, and then reassign it back to that variable called calls, and so 00:13:08.690 --> 00:13:11.510 on, for multiplication here on that fourth line 00:13:11.510 --> 00:13:15.740 and division on that fifth line, so multiplication using our star 00:13:15.740 --> 00:13:18.580 and division using our slash. 00:13:18.580 --> 00:13:20.960 But there's an even shorter way to do much 00:13:20.960 --> 00:13:23.840 of this in C, this language we're currently using. 00:13:23.840 --> 00:13:26.180 There's this thing called syntactic sugar we could 00:13:26.180 --> 00:13:28.490 use to actually shorten these lines. 00:13:28.490 --> 00:13:33.290 I could take the very same operators, plus, minus, star, 00:13:33.290 --> 00:13:39.030 the slash for division here, and I could append an equal sign of it like this. 00:13:39.030 --> 00:13:43.370 I could say calls plus equals 2, calls minus equals 1. 00:13:43.370 --> 00:13:49.040 And that is shorthand for saying calls equals calls plus 2 00:13:49.040 --> 00:13:55.070 or calls equals calls minus 1, just kind of a way to update that value in place 00:13:55.070 --> 00:13:56.940 over time. 00:13:56.940 --> 00:14:00.260 So I'm curious here, if you were to walk through this step 00:14:00.260 --> 00:14:06.200 by step, what do you think the value of calls would be? 00:14:06.200 --> 00:14:08.810 We have some code on the left-hand side. 00:14:08.810 --> 00:14:10.700 Maybe pause the video, take a moment. 00:14:10.700 --> 00:14:12.965 What would be the value of calls? 00:14:16.260 --> 00:14:18.930 So I'm seeing 5, and I believe that is correct. 00:14:18.930 --> 00:14:20.330 So we'll start with 4 here. 00:14:20.330 --> 00:14:21.470 And we're going to add 2. 00:14:21.470 --> 00:14:25.340 So 4 plus 2 is 6, minus 1 is 5. 00:14:25.340 --> 00:14:26.510 Multiply that by 2. 00:14:26.510 --> 00:14:27.320 That's 10. 00:14:27.320 --> 00:14:28.490 Divide it by 2. 00:14:28.490 --> 00:14:30.080 That's back to being 5. 00:14:30.080 --> 00:14:30.830 So you're correct. 00:14:30.830 --> 00:14:34.610 Calls, in this case, would be 5. 00:14:34.610 --> 00:14:38.220 Now, here's a different kind of question. 00:14:38.220 --> 00:14:40.590 Let's say we take a look at this. 00:14:40.590 --> 00:14:41.820 So, again, calls here is 5. 00:14:41.820 --> 00:14:46.050 Let's say we take a look at this next set on the left-hand side. 00:14:46.050 --> 00:14:49.100 What would be the value of calls now? 00:14:51.930 --> 00:14:53.115 Here, again, is our code. 00:14:57.730 --> 00:15:01.500 What would be the value of calls? 00:15:01.500 --> 00:15:03.220 Now, I'm seeing a few options. 00:15:03.220 --> 00:15:05.790 So I'm seeing 4.5. 00:15:05.790 --> 00:15:08.210 And I'm seeing 4. 00:15:08.210 --> 00:15:12.610 And I'll ask you, which one of those do you think is correct, 4 or 4.5? 00:15:17.020 --> 00:15:18.700 So let's walk through this step by step. 00:15:18.700 --> 00:15:20.770 We have calls first being 4. 00:15:20.770 --> 00:15:24.640 We'll add one, which makes it 5, subtract 2, which makes it 3, 00:15:24.640 --> 00:15:29.410 multiply that by 3, which is now 9 because 3 times 3 is 9, 00:15:29.410 --> 00:15:32.950 and divide 9 now by 2. 00:15:32.950 --> 00:15:36.730 And technically, if you were doing it on your own head, 00:15:36.730 --> 00:15:41.170 you might think, well, 9 divided by 2, that's 4.5. 00:15:41.170 --> 00:15:43.930 But actually, it'll be 4 in the end. 00:15:43.930 --> 00:15:47.690 And I'm curious, why do you think it will be four? 00:15:47.690 --> 00:15:51.398 I'm seeing somebody saying that it's 4 because we're storing an integer. 00:15:51.398 --> 00:15:52.190 And you're correct. 00:15:52.190 --> 00:15:56.030 So calls here-- up front, we said calls is going to be an integer. 00:15:56.030 --> 00:15:57.690 That is a whole number. 00:15:57.690 --> 00:16:04.220 And if we take 9 and divide it by 2, we get this decimal number, 4.5, also 00:16:04.220 --> 00:16:06.380 called a floating point number. 00:16:06.380 --> 00:16:11.480 But because calls is strictly an integer, it can't store 4.5. 00:16:11.480 --> 00:16:13.100 So what will happen instead? 00:16:13.100 --> 00:16:17.270 In C, it will simply do what we call truncating that value. 00:16:17.270 --> 00:16:19.970 We'll say, we have 4.5. 00:16:19.970 --> 00:16:23.400 There is some decimal value after that decimal point. 00:16:23.400 --> 00:16:26.240 But we're going to simply get rid of it, not care about it, 00:16:26.240 --> 00:16:29.690 and take whatever whole number we see up front. 00:16:29.690 --> 00:16:33.620 So if our calculations yielded 4.1, what would we get? 00:16:33.620 --> 00:16:34.910 Well, just four. 00:16:34.910 --> 00:16:38.630 If we even had 4.8, we'd get simply 4. 00:16:38.630 --> 00:16:40.730 So to be clear, it's not rounding, but it 00:16:40.730 --> 00:16:46.490 is truncating, taking off that last bit of the decimal place there. 00:16:46.490 --> 00:16:52.120 So I'm curious now, what questions do we have about variables, about assignment, 00:16:52.120 --> 00:16:54.500 about updating them over time? 00:16:54.500 --> 00:16:57.385 Any questions we can take while we're here live? 00:17:02.777 --> 00:17:05.569 And feel free to write those questions in the chat for those of you 00:17:05.569 --> 00:17:06.139 who are here. 00:17:13.910 --> 00:17:14.619 OK. 00:17:14.619 --> 00:17:17.260 Not seeing too many questions, which maybe is a good sign. 00:17:17.260 --> 00:17:21.069 But certainly feel free to ask if you're watching this recording. 00:17:21.069 --> 00:17:21.790 Ask a friend. 00:17:21.790 --> 00:17:24.130 Ask online in CS50's communities, certainly 00:17:24.130 --> 00:17:26.347 get those questions answered for you. 00:17:26.347 --> 00:17:28.930 Now, we'll continue here and try to do something a little more 00:17:28.930 --> 00:17:31.450 interesting with our variables. 00:17:31.450 --> 00:17:35.410 I think what we'll do is think about how to take input from the user 00:17:35.410 --> 00:17:38.480 and then print that input back out to the user. 00:17:38.480 --> 00:17:42.040 So we'll talk about input now and printing. 00:17:42.040 --> 00:17:45.910 One of the first things you might want to do is get input from your users. 00:17:45.910 --> 00:17:48.340 If you're running some program, you want them to control 00:17:48.340 --> 00:17:50.660 how that program is actually working. 00:17:50.660 --> 00:17:54.550 So there are a few ways, at least in CS50 and in C in general, 00:17:54.550 --> 00:17:57.100 to get input from your user. 00:17:57.100 --> 00:18:00.340 Let's say I want to, in this case, get an input 00:18:00.340 --> 00:18:04.840 from the user that will tell me, what should the value of calls be? 00:18:04.840 --> 00:18:10.630 Well, in CS50, you'll have access to this function called get_int. 00:18:10.630 --> 00:18:12.470 And there's a few pieces here. 00:18:12.470 --> 00:18:17.510 Get_int takes this argument, this input, called calls, in this case, 00:18:17.510 --> 00:18:19.940 calls colon followed by a space. 00:18:19.940 --> 00:18:22.910 And you'll see that separated by quotes here. 00:18:22.910 --> 00:18:26.930 And moreover, that then is surrounded by these parentheses 00:18:26.930 --> 00:18:29.750 that tell us this is the input to this function 00:18:29.750 --> 00:18:32.550 that we're going to call calls. 00:18:32.550 --> 00:18:35.720 So there's a few things to keep in mind as we start to use 00:18:35.720 --> 00:18:38.780 these functions to get user input. 00:18:38.780 --> 00:18:43.620 First, what we're doing right here, this is called a function call. 00:18:43.620 --> 00:18:48.680 So before we assign the value of calls, we're going to run this function 00:18:48.680 --> 00:18:51.840 and wait for the user to input some value. 00:18:51.840 --> 00:18:54.740 So get_int, this function on the left-hand side, 00:18:54.740 --> 00:18:59.360 that will first be run before we store that value inside this variable we 00:18:59.360 --> 00:19:01.760 created called calls. 00:19:01.760 --> 00:19:05.540 But let's say that the user does give us some value. 00:19:05.540 --> 00:19:07.670 And they give us the value 4. 00:19:07.670 --> 00:19:11.810 Well, the whole point of get_int is that once it finishes running, 00:19:11.810 --> 00:19:16.500 it returns to us or gives us back the value the user entered. 00:19:16.500 --> 00:19:19.190 So let's say they enter this value 4. 00:19:19.190 --> 00:19:23.810 Well, it's kind of like saying this function runs and gets almost replaced 00:19:23.810 --> 00:19:25.520 by this value 4. 00:19:25.520 --> 00:19:28.490 Such that in the end, it's almost exactly like writing some code 00:19:28.490 --> 00:19:32.840 like this, int calls gets the value 4. 00:19:32.840 --> 00:19:33.920 How do we get that? 00:19:33.920 --> 00:19:36.710 By running this function called get-int that 00:19:36.710 --> 00:19:40.170 returned to us what the user typed in. 00:19:40.170 --> 00:19:42.690 So we're going to get user input here. 00:19:42.690 --> 00:19:45.440 But now we can think about how we can print that back out. 00:19:45.440 --> 00:19:49.880 And to print things in C, we'll use this function called printf. 00:19:49.880 --> 00:19:52.280 So here we have that same line of code. 00:19:52.280 --> 00:19:54.680 Int calls gets the value 4. 00:19:54.680 --> 00:19:59.030 Notice how now calls is storing that value called 4. 00:19:59.030 --> 00:20:02.750 But now on the bottom, we see calls is-- 00:20:02.750 --> 00:20:09.140 well, calls is %i backslash n comma calls. 00:20:09.140 --> 00:20:11.240 And that seems a little cryptic. 00:20:11.240 --> 00:20:13.550 So I'm curious, for those of you who are here, 00:20:13.550 --> 00:20:16.370 what do you think will actually get printed out 00:20:16.370 --> 00:20:19.185 if we were to run this line of code? 00:20:19.185 --> 00:20:21.435 What will we actually see on the screen? 00:20:26.580 --> 00:20:33.800 So I'm seeing we'd literally see the text, "calls is 4," the actual value 4. 00:20:33.800 --> 00:20:36.770 And to show you here, we'd see this. 00:20:36.770 --> 00:20:40.670 Calls is, again, that numeric value 4. 00:20:40.670 --> 00:20:43.385 And this is a special property of printf. 00:20:43.385 --> 00:20:46.710 And if you're wondering, well, why is there an F at the end? 00:20:46.710 --> 00:20:49.370 Turns out that F stands for Formatted. 00:20:49.370 --> 00:20:52.460 So I'm going to print something that will be formatted. 00:20:52.460 --> 00:20:57.866 And I have, on the inside of this string if you will, calls is %i. 00:20:57.866 --> 00:21:04.310 I will replace that %i with the value of this variable called calls. 00:21:04.310 --> 00:21:07.490 Now, the follow up question is, well, how did I know to put the value 00:21:07.490 --> 00:21:10.790 of calls in that placeholder, %i? 00:21:10.790 --> 00:21:15.890 Well, what I did is I followed up my text, denoted in quotes here, 00:21:15.890 --> 00:21:20.030 "calls is %i backslash n" with a comma. 00:21:20.030 --> 00:21:22.580 And I gave another input to printf. 00:21:22.580 --> 00:21:28.620 This time I said, I want to put in the value of this variable named calls. 00:21:28.620 --> 00:21:31.650 So whatever follows, your text that you give 00:21:31.650 --> 00:21:35.550 to printf by a comma, whatever variable you include there, 00:21:35.550 --> 00:21:37.860 the value of that variable will be included 00:21:37.860 --> 00:21:41.100 inside whatever format code you've included there 00:21:41.100 --> 00:21:44.650 or in replacement of that format code itself. 00:21:44.650 --> 00:21:47.612 So there are a few other format codes you're probably familiar with. 00:21:47.612 --> 00:21:48.820 A few of them look like this. 00:21:48.820 --> 00:21:53.460 We have this one for integers, %i, that we saw earlier, 00:21:53.460 --> 00:21:59.070 one for floats or decimal numbers, %f, one for characters, %c, 00:21:59.070 --> 00:22:02.940 and one for strings, actual not just single characters, 00:22:02.940 --> 00:22:05.670 but whole collections of text like we saw earlier. 00:22:05.670 --> 00:22:08.340 That would be %s. 00:22:08.340 --> 00:22:12.610 So you'll see these over time as well. 00:22:12.610 --> 00:22:17.520 So questions then on types and format codes, which ones we 00:22:17.520 --> 00:22:18.615 should use in which cases? 00:22:24.930 --> 00:22:25.470 All right. 00:22:25.470 --> 00:22:27.720 So seeing none so far here. 00:22:27.720 --> 00:22:30.710 What we'll do is actually get some practice writing code. 00:22:30.710 --> 00:22:33.040 So I think this is enough review of the lecture so far. 00:22:33.040 --> 00:22:35.700 And one of our first steps in this week's problem set 00:22:35.700 --> 00:22:38.610 is to write a program called hello, world. 00:22:38.610 --> 00:22:42.090 And this is often the first program many people write when they're beginning 00:22:42.090 --> 00:22:43.410 their computer science journey. 00:22:43.410 --> 00:22:45.452 In this case, we're going to write a program that 00:22:45.452 --> 00:22:49.800 simply says hello, world to the user and, of course, perhaps, to the world. 00:22:49.800 --> 00:22:54.300 So I'll go over and I'll open up cs50.dev. 00:22:54.300 --> 00:22:58.770 So you should see something a bit like this if you were to go to cs50.dev 00:22:58.770 --> 00:23:01.050 and log in with your GitHub account. 00:23:01.050 --> 00:23:03.240 No need to follow along exactly like this. 00:23:03.240 --> 00:23:06.090 But if you're watching the recording, you certainly can. 00:23:06.090 --> 00:23:10.320 Notice how I have a few different areas in cs50.dev. 00:23:10.320 --> 00:23:13.680 I have a top area up here that will soon be 00:23:13.680 --> 00:23:17.100 able to have a file that I can actually edit things in. 00:23:17.100 --> 00:23:19.740 And down below, I have this place called the terminal. 00:23:19.740 --> 00:23:23.630 I can interact with this computer that I've loaded up in the cloud. 00:23:23.630 --> 00:23:27.610 So I'm now connected to some other computer, not my own, 00:23:27.610 --> 00:23:31.420 where I actually write my own code and where we, CS50, 00:23:31.420 --> 00:23:36.650 have installed some software for you to actually write C code very easily. 00:23:36.650 --> 00:23:41.440 So let me try, in this case, to open up a file called hello.c. 00:23:41.440 --> 00:23:45.610 I'll type code hello.c in my terminal. 00:23:45.610 --> 00:23:47.650 Let me zoom in a bit so you all can see that. 00:23:47.650 --> 00:23:50.440 Here I now have code hello.c. 00:23:50.440 --> 00:23:51.610 I'll hit Enter. 00:23:51.610 --> 00:23:56.110 And I'll see this blank file up top called hello.c. 00:23:56.110 --> 00:23:59.860 So now I'll actually go ahead and type in some C code. 00:23:59.860 --> 00:24:02.590 Maybe I want to say hello to the user. 00:24:02.590 --> 00:24:05.920 What's the first thing I should do? 00:24:05.920 --> 00:24:08.950 For those of you who watched lecture, what might I 00:24:08.950 --> 00:24:10.870 need to do at the top of my file? 00:24:13.650 --> 00:24:15.990 I need to include some stuff people are saying. 00:24:15.990 --> 00:24:20.490 So in CS50, and actually in C in general, 00:24:20.490 --> 00:24:24.990 we have this idea of a library or some code somebody else has written for us 00:24:24.990 --> 00:24:27.420 that we could then use in our own program. 00:24:27.420 --> 00:24:31.440 And it turns out that somebody else wrote this function called printf. 00:24:31.440 --> 00:24:35.260 And because they wrote it and included it in this library, 00:24:35.260 --> 00:24:38.640 we can then actually use that function in our own code 00:24:38.640 --> 00:24:40.440 without worrying how they made it. 00:24:40.440 --> 00:24:42.790 We just kind of know that it just works. 00:24:42.790 --> 00:24:46.170 So to get access to functions like printf, 00:24:46.170 --> 00:24:49.020 I can type this special piece of syntax up top. 00:24:49.020 --> 00:24:55.660 I can say, #include stdio.h and hit Enter here. 00:24:55.660 --> 00:25:02.040 So this is allowing me to include this file called stdio.h, a header file that 00:25:02.040 --> 00:25:05.530 has printf defined inside of it. 00:25:05.530 --> 00:25:09.930 And now, what's the next step I might need to do here? 00:25:09.930 --> 00:25:13.520 I have Standard I/O included. 00:25:13.520 --> 00:25:18.970 But how I might start off my program as we usually do in C? 00:25:18.970 --> 00:25:21.350 So I'm seeing we need to make a main function. 00:25:21.350 --> 00:25:25.120 So by convention, in C, when we want to make a new program, 00:25:25.120 --> 00:25:28.420 we always include that entire program inside this 00:25:28.420 --> 00:25:32.680 function we call main, int main(void). 00:25:32.680 --> 00:25:37.000 And now here i have-- let me fix that formatting here. 00:25:37.000 --> 00:25:41.170 I have this function called main. 00:25:41.170 --> 00:25:43.510 Yours might be syntax highlighted, not quite sure 00:25:43.510 --> 00:25:45.070 why mine isn't highlighting here. 00:25:45.070 --> 00:25:47.300 But I'll resolve that a little bit later. 00:25:47.300 --> 00:25:49.510 So here we have int main(void). 00:25:49.510 --> 00:25:54.100 And we could type in our actual code inside of this function 00:25:54.100 --> 00:25:55.780 that we are calling main. 00:25:55.780 --> 00:25:58.990 Now, what kind of code could we type to say hello 00:25:58.990 --> 00:26:02.110 to the user based on what we saw a little earlier? 00:26:02.110 --> 00:26:05.290 What function should we use? 00:26:05.290 --> 00:26:06.610 Probably printf, right? 00:26:06.610 --> 00:26:08.020 So I'll say, printf. 00:26:08.020 --> 00:26:10.220 And then why don't I do this? 00:26:10.220 --> 00:26:12.910 I'll say, hello, world. 00:26:12.910 --> 00:26:19.330 And now if I hit a period here to say a sentence, backslash n, 00:26:19.330 --> 00:26:24.950 I should be able to hopefully run this program down in my terminal. 00:26:24.950 --> 00:26:26.750 So let me try this. 00:26:26.750 --> 00:26:32.950 If I want to run, I could try saying ./hello and hit Enter. 00:26:32.950 --> 00:26:37.610 But I get this error, no such file or directory. 00:26:37.610 --> 00:26:41.790 So what did I actually miss in this case? 00:26:41.790 --> 00:26:44.760 Yeah, some of you are saying I forgot to make this file. 00:26:44.760 --> 00:26:46.650 So as we saw in lecture, there's this idea 00:26:46.650 --> 00:26:50.220 of taking the source code that is this C file 00:26:50.220 --> 00:26:54.000 and compiling it to machine code or the zeros and ones 00:26:54.000 --> 00:26:56.070 a computer actually understands. 00:26:56.070 --> 00:27:00.810 So to take this C code and convert it to the code a computer understands, 00:27:00.810 --> 00:27:03.060 we have this special program called make, 00:27:03.060 --> 00:27:07.020 which is a compiler that simply says take whatever is in hello.c 00:27:07.020 --> 00:27:11.470 and convert it for me to an actual program my computer can run. 00:27:11.470 --> 00:27:17.370 So in my terminal, I will choose to make hello, hit Enter, 00:27:17.370 --> 00:27:18.930 and now nothing seemed to happen. 00:27:18.930 --> 00:27:20.263 But that's actually a good sign. 00:27:20.263 --> 00:27:24.300 If I type ls to list my files, I'll see hello star, 00:27:24.300 --> 00:27:27.000 which means this is a file my computer can run. 00:27:27.000 --> 00:27:33.610 I'll say ./hello, hit Enter, and now I see hello comma world. 00:27:33.610 --> 00:27:36.610 So syntax highlighting aside, which you hopefully 00:27:36.610 --> 00:27:39.070 see in your own code space, this is how we can actually 00:27:39.070 --> 00:27:42.340 write our own hello, world program. 00:27:42.340 --> 00:27:46.960 What questions do we have then on these lines of code? 00:27:50.435 --> 00:27:51.560 I'm seeing a question here. 00:27:51.560 --> 00:27:55.500 What is the difference between a library and a header file? 00:27:55.500 --> 00:27:58.760 So that's two pieces of vocabulary we've used here. 00:27:58.760 --> 00:28:04.160 We often say we're going to include a header file or, conversationally, 00:28:04.160 --> 00:28:05.870 include some library. 00:28:05.870 --> 00:28:08.730 But there's a difference between these two things. 00:28:08.730 --> 00:28:15.380 So notice how this, stdio.h, that is an actual file we're calling a header 00:28:15.380 --> 00:28:16.050 file. 00:28:16.050 --> 00:28:19.100 And in this particular file, we've defined 00:28:19.100 --> 00:28:23.750 all the functions that are included in this library, like, for example, 00:28:23.750 --> 00:28:24.860 printf. 00:28:24.860 --> 00:28:27.470 But in that header file, we haven't actually 00:28:27.470 --> 00:28:30.590 defined the entirety of the printf function. 00:28:30.590 --> 00:28:35.150 We've just defined a few particular things, like what inputs printf takes 00:28:35.150 --> 00:28:37.370 or what outputs it gives to us. 00:28:37.370 --> 00:28:40.850 Now, the entire library likely has more files 00:28:40.850 --> 00:28:44.180 than just this header file under which those functions are actually 00:28:44.180 --> 00:28:48.140 defined under which they tell us what exactly does printf do. 00:28:48.140 --> 00:28:50.760 So the library, in general, you can think of it 00:28:50.760 --> 00:28:53.790 as including all kinds of functions, some like printf. 00:28:53.790 --> 00:28:59.280 But the header file is our way of defining what functions are inside 00:28:59.280 --> 00:29:01.590 this library to begin with. 00:29:01.590 --> 00:29:03.550 A great question. 00:29:03.550 --> 00:29:05.950 So let's keep going and make this a little more advanced. 00:29:05.950 --> 00:29:11.490 So our next step in problem set 0 is to not just say hello to the world, 00:29:11.490 --> 00:29:14.680 but to say hello to a particular user. 00:29:14.680 --> 00:29:17.850 So in this case, we want to get input from the user 00:29:17.850 --> 00:29:22.810 and allow them, in this case, to say hello back to themselves. 00:29:22.810 --> 00:29:25.740 So I'll go back to my program, hello.c. 00:29:25.740 --> 00:29:29.560 And now I want to get input from the user. 00:29:29.560 --> 00:29:31.470 So what could I do? 00:29:31.470 --> 00:29:33.210 Maybe I want to make a variable. 00:29:33.210 --> 00:29:36.990 And I'll actually ask you all who are here, what kind of variable 00:29:36.990 --> 00:29:37.800 should I make? 00:29:37.800 --> 00:29:42.495 If I want to store some text from the user, what type might be good for that? 00:29:45.130 --> 00:29:46.110 I'm seeing a string. 00:29:46.110 --> 00:29:49.980 A string is a variable that can store a collection of text, not just 00:29:49.980 --> 00:29:52.380 a single character, but a whole collection of it. 00:29:52.380 --> 00:29:54.330 So I'll type string here. 00:29:54.330 --> 00:29:55.560 This is the type. 00:29:55.560 --> 00:29:59.450 And now, what should I name this variable? 00:29:59.450 --> 00:30:01.775 What might be an appropriate name here? 00:30:01.775 --> 00:30:02.900 We could just call it name. 00:30:02.900 --> 00:30:05.450 This is a variable whose name is name because it 00:30:05.450 --> 00:30:07.730 stores someone's actual name, kind of confusing, 00:30:07.730 --> 00:30:09.680 but we'll go with it, string name. 00:30:09.680 --> 00:30:12.150 And then it gets some value. 00:30:12.150 --> 00:30:14.150 So I'll use this assignment operator here. 00:30:14.150 --> 00:30:17.920 What value should it get? 00:30:17.920 --> 00:30:22.130 I could type just Carter here, like this, to get my own name. 00:30:22.130 --> 00:30:23.900 But I want to get the user's name. 00:30:23.900 --> 00:30:26.080 So what could I do? 00:30:26.080 --> 00:30:28.730 I'm seeing I could use get_string as we saw before. 00:30:28.730 --> 00:30:31.960 So get_string is a function that is included 00:30:31.960 --> 00:30:35.560 in the CS50 library that allows you to safely get 00:30:35.560 --> 00:30:38.090 some user input that is a string. 00:30:38.090 --> 00:30:41.590 And as input inside these parentheses here, 00:30:41.590 --> 00:30:45.920 get_string can take some piece of text itself or a string. 00:30:45.920 --> 00:30:50.080 So I'll say, "What is your name?" 00:30:50.080 --> 00:30:53.770 And leave a space so the user can type in their name after that. 00:30:53.770 --> 00:30:57.700 And now, down below, I should think about what I should update here. 00:30:57.700 --> 00:30:59.350 I have hello, world. 00:30:59.350 --> 00:31:02.790 But now what should I change this to? 00:31:02.790 --> 00:31:05.010 Not hello, world, but what? 00:31:07.492 --> 00:31:09.700 Probably a placeholder, as I'm seeing some folks say. 00:31:09.700 --> 00:31:13.760 I want to have a placeholder for this variable we created called name. 00:31:13.760 --> 00:31:18.256 So I'll say hello comma and then a space %s. 00:31:18.256 --> 00:31:23.500 %s is our format code, our placeholder, for a variable of the type string. 00:31:23.500 --> 00:31:27.430 And now, how could I make sure that the value of name gets included here? 00:31:27.430 --> 00:31:32.540 I could simply follow this text with a comma, then say the variable name. 00:31:32.540 --> 00:31:36.850 And now I'll make sure that whatever value is stored by this variable called 00:31:36.850 --> 00:31:42.280 name, I should be able to have a placeholder for it here in %s. 00:31:42.280 --> 00:31:43.120 So now let's try it. 00:31:43.120 --> 00:31:46.360 I'll do make hello to recompile our program, 00:31:46.360 --> 00:31:49.150 update it, and turn it back into machine code. 00:31:49.150 --> 00:31:50.590 I'll hit Enter. 00:31:50.590 --> 00:31:52.610 And I get a fatal error. 00:31:52.610 --> 00:31:53.920 Let's see. 00:31:53.920 --> 00:31:55.420 What might be wrong? 00:31:58.700 --> 00:32:03.240 So there's a few clues here, "use of undeclared identifier string." 00:32:03.240 --> 00:32:04.700 Did I mean standard in? 00:32:04.700 --> 00:32:06.950 It's actually not what I meant in this case. 00:32:06.950 --> 00:32:11.180 But often if you'll see, you might get some errors saying something 00:32:11.180 --> 00:32:14.152 is undeclared, undefined in some ways. 00:32:14.152 --> 00:32:15.860 When that happens, you might want to take 00:32:15.860 --> 00:32:19.950 a look at which files you're including at the top of your program. 00:32:19.950 --> 00:32:22.460 And in this case, I told you that get_string 00:32:22.460 --> 00:32:24.920 was included in the CS50 library. 00:32:24.920 --> 00:32:26.893 But I didn't include it up top. 00:32:26.893 --> 00:32:28.310 So let me go ahead and include it. 00:32:28.310 --> 00:32:35.030 I'll say, #include and then cs50.h to include that CS50 header file. 00:32:35.030 --> 00:32:37.940 And just for style's sake, what I'll do is actually 00:32:37.940 --> 00:32:43.350 move CS50 above Standard I/O just to keep things alphabetized up here. 00:32:43.350 --> 00:32:46.970 So C comes before S. I'll make sure I have all my header files 00:32:46.970 --> 00:32:49.280 alphabetized just for style's sake. 00:32:49.280 --> 00:32:51.110 It would work the other way too, but just 00:32:51.110 --> 00:32:54.580 to keep things a little cleaner around here. 00:32:54.580 --> 00:32:56.020 So let me try this. 00:32:56.020 --> 00:33:00.810 I'll say make hello, hit Enter, nothing seemed to happen, which is good. 00:33:00.810 --> 00:33:03.910 I'll type ./hello, which is my program, hit Enter. 00:33:03.910 --> 00:33:05.160 I'll see, "What is your name?" 00:33:05.160 --> 00:33:06.300 And I'll type Carter. 00:33:06.300 --> 00:33:09.000 And I should see, "Hello, Carter." 00:33:09.000 --> 00:33:12.360 So all seems to work in this case. 00:33:12.360 --> 00:33:17.095 Now, what questions do we have on writing our very own hello to you 00:33:17.095 --> 00:33:17.595 program? 00:33:24.260 --> 00:33:27.020 Seeing none so far. 00:33:27.020 --> 00:33:29.748 And now let's move on to something that's a little more advanced. 00:33:29.748 --> 00:33:31.290 Actually, there is one question here. 00:33:31.290 --> 00:33:36.230 So why do we put name after %s backslash n? 00:33:36.230 --> 00:33:38.720 So it's kind of just by convention. 00:33:38.720 --> 00:33:43.940 The people who wrote printf, who came before us and made this function, 00:33:43.940 --> 00:33:49.730 they simply decided that printf would take one or more inputs. 00:33:49.730 --> 00:33:53.960 So here I say, hello %s backslash n. 00:33:53.960 --> 00:33:56.480 And if I want to include-- 00:33:56.480 --> 00:34:00.320 if I want to take the value of this variable name and put it in this 00:34:00.320 --> 00:34:04.880 placeholder, I just simply follow up with this first input called hello 00:34:04.880 --> 00:34:10.054 comma %s backslash n and include that variable itself. 00:34:10.054 --> 00:34:12.679 If you want to get more advanced with this, you actually could. 00:34:12.679 --> 00:34:16.219 So let's say I want to take a first name and a last name. 00:34:16.219 --> 00:34:21.350 I could actually have two placeholders, hello %s space %s. 00:34:21.350 --> 00:34:24.810 And now if I wanted to include another variable, 00:34:24.810 --> 00:34:30.870 one let's say changes name to first name and then have one later called 00:34:30.870 --> 00:34:33.929 last name, here's how I could use printf. 00:34:33.929 --> 00:34:37.510 I could now have three inputs separated by commas. 00:34:37.510 --> 00:34:41.190 The first is the actual string I want to print with the placeholders. 00:34:41.190 --> 00:34:46.139 The next one is the first variable to replace that is the value of first name 00:34:46.139 --> 00:34:49.350 will go into this first placeholder and then 00:34:49.350 --> 00:34:54.060 the second variable, last name, that will go into the second placeholder 00:34:54.060 --> 00:34:54.806 here. 00:34:54.806 --> 00:34:55.889 So I'll update my program. 00:34:55.889 --> 00:34:58.110 I'll say hello string first name. 00:34:58.110 --> 00:35:00.240 What is your first name? 00:35:00.240 --> 00:35:04.080 And then here I'll say, string last name gets 00:35:04.080 --> 00:35:09.570 the value of get_string asking, what is your last name? 00:35:09.570 --> 00:35:11.640 --and a semicolon to finish. 00:35:11.640 --> 00:35:14.760 So now I'll type make hello. 00:35:14.760 --> 00:35:16.890 And I'll run ./hello. 00:35:16.890 --> 00:35:19.560 I'll type Carter followed by Zenke. 00:35:19.560 --> 00:35:22.440 And now I'll see "Hello, Carter Zenke." 00:35:22.440 --> 00:35:26.340 So there's some other ways to use printf if you want to actually involve 00:35:26.340 --> 00:35:30.550 more than one variable in your output. 00:35:30.550 --> 00:35:33.010 Now, building on this, let's actually continue on. 00:35:33.010 --> 00:35:37.720 And let's try actually making a more advanced program to store our contacts. 00:35:37.720 --> 00:35:39.440 So I'll go back to my slides. 00:35:39.440 --> 00:35:40.550 And I'll show you this. 00:35:40.550 --> 00:35:45.070 We're going to write a program that takes in and stores and then later 00:35:45.070 --> 00:35:48.560 prints out a user's contact information. 00:35:48.560 --> 00:35:51.130 And so if you're going to write this program, 00:35:51.130 --> 00:35:55.120 I want you to include the following three attributes of somebody. 00:35:55.120 --> 00:35:58.360 Make sure you include, let's say, their name. 00:35:58.360 --> 00:36:03.430 You can treat it as either first name or first name and last name, their age, 00:36:03.430 --> 00:36:09.833 and also their phone number, so name, age, and phone number. 00:36:09.833 --> 00:36:12.250 And I want you to, if you're watching this as a recording, 00:36:12.250 --> 00:36:15.610 maybe pause the video here and try to write this program 00:36:15.610 --> 00:36:19.285 yourself and then come back and we'll write it all together. 00:36:21.880 --> 00:36:22.380 All right. 00:36:22.380 --> 00:36:23.550 So if you're back from writing this program, 00:36:23.550 --> 00:36:25.758 let's go ahead and try to write it all together here. 00:36:25.758 --> 00:36:27.240 Go back to my code space. 00:36:27.240 --> 00:36:29.640 And this time, I'll get rid of hello.c. 00:36:29.640 --> 00:36:30.900 I'll x out up top. 00:36:30.900 --> 00:36:35.700 And now I'll type code contacts.c to create this new file that 00:36:35.700 --> 00:36:38.550 is a C program called contacts. 00:36:38.550 --> 00:36:42.360 And I'll include my initial libraries. 00:36:42.360 --> 00:36:49.300 I'll say include stdio.h and include, perhaps up top here, cs50.h as well. 00:36:49.300 --> 00:36:55.240 Now I'll type int main(void), what we do to kick off all of our C programs here. 00:36:55.240 --> 00:36:57.525 And now I need to get the information from the user. 00:36:57.525 --> 00:36:59.400 So I'm curious, for those of you who are here 00:36:59.400 --> 00:37:03.585 live, what should I be doing to actually get the user's name? 00:37:03.585 --> 00:37:05.460 Well, probably similar to what we did before. 00:37:05.460 --> 00:37:10.800 I could say, string name equals get_string what is your name? 00:37:10.800 --> 00:37:12.090 Just like this. 00:37:12.090 --> 00:37:14.350 But now I want to get their age. 00:37:14.350 --> 00:37:19.580 And I'm curious, what type might be good for getting their age? 00:37:19.580 --> 00:37:20.670 Maybe an integer. 00:37:20.670 --> 00:37:28.160 So I could say int age equals get_int what is your age? 00:37:28.160 --> 00:37:29.250 Just like this. 00:37:29.250 --> 00:37:34.610 And then finally, down below, I want to get their phone number. 00:37:34.610 --> 00:37:37.220 But what type might be best for a phone number? 00:37:40.080 --> 00:37:43.010 Seeing a few options here. 00:37:43.010 --> 00:37:45.310 So one might be an integer. 00:37:45.310 --> 00:37:46.850 It is a phone number. 00:37:46.850 --> 00:37:50.350 So it could just be an integer value. 00:37:50.350 --> 00:37:54.160 But it might be better to find as a string. 00:37:54.160 --> 00:37:56.880 So the difference here is that if I say int, 00:37:56.880 --> 00:38:03.460 let's say just number for phone number, get_int what is your phone number? 00:38:03.460 --> 00:38:08.670 Well, that restricts the user to entering only digits. 00:38:08.670 --> 00:38:12.360 And sometimes you might see phone numbers written with dashes or plus 00:38:12.360 --> 00:38:14.020 signs for country codes. 00:38:14.020 --> 00:38:16.470 And if I wanted to include those, well, if I have an int, 00:38:16.470 --> 00:38:18.130 I actually can't include those. 00:38:18.130 --> 00:38:22.950 So if I wanted to be able to have the user type in pluses along with numbers, 00:38:22.950 --> 00:38:24.940 a string might be good for this. 00:38:24.940 --> 00:38:27.510 So I'll say instead string number and use 00:38:27.510 --> 00:38:29.520 get_string what is your phone number? 00:38:29.520 --> 00:38:36.030 Now the user could include not just numbers, like 7 or 1 or so 00:38:36.030 --> 00:38:39.210 on, they could also include parentheses, dashes, 00:38:39.210 --> 00:38:43.320 plus signs, whatever they need to enter their phone number. 00:38:43.320 --> 00:38:46.020 And now to print all this out, I'll go back down below. 00:38:46.020 --> 00:38:51.930 And I'll say, let's say, why don't we print out name followed by their name? 00:38:51.930 --> 00:38:55.930 And why don't we print out, in this case, 00:38:55.930 --> 00:39:05.730 the age followed by their age using %i for our integer here and then printf 00:39:05.730 --> 00:39:11.950 and then number followed by %s backslash n semicolon. 00:39:11.950 --> 00:39:14.850 And now I'll be able to include all of these 00:39:14.850 --> 00:39:19.080 as placeholders, name, age, and number. 00:39:19.080 --> 00:39:22.680 And I'll be able to take the value of name and put it in this placeholder, 00:39:22.680 --> 00:39:24.570 for instance. 00:39:24.570 --> 00:39:25.920 So why don't we do this? 00:39:25.920 --> 00:39:30.020 I'll say, make contacts, then ./contacts. 00:39:30.020 --> 00:39:31.250 Hit Enter. 00:39:31.250 --> 00:39:32.390 What is my name? 00:39:32.390 --> 00:39:33.260 Carter. 00:39:33.260 --> 00:39:34.490 What is my age? 00:39:34.490 --> 00:39:35.600 25. 00:39:35.600 --> 00:39:36.770 I'll type in a phone number. 00:39:36.770 --> 00:39:38.450 I'll say, plus one. 00:39:38.450 --> 00:39:44.570 Let's go with 555-555-5555 for a random phone number here. 00:39:44.570 --> 00:39:45.410 Hit Enter. 00:39:45.410 --> 00:39:50.570 And now I see that same information being printed back out to me. 00:39:50.570 --> 00:39:54.500 So what questions do we have on this contacts application here? 00:40:01.670 --> 00:40:02.580 OK. 00:40:02.580 --> 00:40:05.070 So I'm not seeing any from our live audience. 00:40:05.070 --> 00:40:08.270 But what we'll do is kind of round out this week's section 00:40:08.270 --> 00:40:11.540 by focusing now on not just getting input from the user 00:40:11.540 --> 00:40:14.540 and storing it in variables, but actually writing 00:40:14.540 --> 00:40:18.350 our programs with our very own functions and loops and conditionals. 00:40:18.350 --> 00:40:20.330 And I think things get a lot more interesting 00:40:20.330 --> 00:40:23.580 when we get to use other kinds of building blocks here. 00:40:23.580 --> 00:40:27.830 So let's talk now about, again, functions, loops, and conditionals. 00:40:27.830 --> 00:40:30.200 And in this week's problem set, you'll see 00:40:30.200 --> 00:40:34.610 you'll be tasked with making your very own pyramid like the pyramid that's 00:40:34.610 --> 00:40:38.480 in Mario, that very old game and also somewhat new game 00:40:38.480 --> 00:40:42.680 coming out very soon that Mario has to go through and fight enemies and go 00:40:42.680 --> 00:40:45.590 through a higher level by jumping over things like this pyramid 00:40:45.590 --> 00:40:48.300 that we see on this video here. 00:40:48.300 --> 00:40:50.030 So there are a few kinds of loops. 00:40:50.030 --> 00:40:53.300 And one of these loops is called a while loop. 00:40:53.300 --> 00:40:57.410 A while loop is great for when you want to maybe do something 00:40:57.410 --> 00:41:01.870 while some condition is true in your program. 00:41:01.870 --> 00:41:04.230 So as one example of this, let's say I have 00:41:04.230 --> 00:41:07.770 a while loop that looks a bit like this on the left-hand side. 00:41:07.770 --> 00:41:12.540 Well, I will tell you right now that the output of this piece of code 00:41:12.540 --> 00:41:16.140 is going to look a bit like this on the right-hand side. 00:41:16.140 --> 00:41:21.030 I'll get four hashes on the right-hand side. 00:41:21.030 --> 00:41:23.290 But how did we get here? 00:41:23.290 --> 00:41:27.010 Let's walk through it step by step using the syntax that we see here. 00:41:27.010 --> 00:41:31.410 So the very first line of code, int j, gets the value 0. 00:41:31.410 --> 00:41:34.170 Well, that creates this container in memory 00:41:34.170 --> 00:41:37.050 called j that has this value called 0. 00:41:37.050 --> 00:41:40.080 And now here's where things are a little more interesting. 00:41:40.080 --> 00:41:40.980 I have this variable. 00:41:40.980 --> 00:41:43.420 But I want to do something with it. 00:41:43.420 --> 00:41:45.510 I could make a condition out of it. 00:41:45.510 --> 00:41:48.300 I could say, I want to do something in my program 00:41:48.300 --> 00:41:53.130 while it is true that the value of j is less than 4. 00:41:53.130 --> 00:41:55.680 That is this condition right here. 00:41:55.680 --> 00:42:00.120 Now, what do I want to do while the value of j is less than 4? 00:42:00.120 --> 00:42:05.260 Let's say I first want to print this single hashtag down below. 00:42:05.260 --> 00:42:10.120 So now I've gone and I've said, well, is j less than 4? 00:42:10.120 --> 00:42:10.620 It is. 00:42:10.620 --> 00:42:11.850 It's currently 0. 00:42:11.850 --> 00:42:14.670 So I'll print out a single hash. 00:42:14.670 --> 00:42:16.110 And then what will I do? 00:42:16.110 --> 00:42:19.230 I'll then say, let's increase j by one using 00:42:19.230 --> 00:42:23.290 the syntax of plus plus, some syntactic sugar here, to say j 00:42:23.290 --> 00:42:27.610 is now one more than what it previously was. 00:42:27.610 --> 00:42:32.440 And now, logically in this loop, I'll go back up to the top. 00:42:32.440 --> 00:42:34.720 And I'll reassess this condition. 00:42:34.720 --> 00:42:39.100 I'll say, is j still less than 4? 00:42:39.100 --> 00:42:43.580 And for those of you who are here live, is j is still less than 4? 00:42:43.580 --> 00:42:44.630 I think it is, right? 00:42:44.630 --> 00:42:45.500 So we'll keep going. 00:42:45.500 --> 00:42:47.630 We'll go through this loop one more time. 00:42:47.630 --> 00:42:49.820 I'll say, print out another hash. 00:42:49.820 --> 00:42:52.190 And then I'll increase j by one. 00:42:52.190 --> 00:42:54.350 So now what is j? 00:42:54.350 --> 00:42:55.850 j is 2. 00:42:55.850 --> 00:42:56.750 I'll ask again. 00:42:56.750 --> 00:42:59.050 Is j less than 4? 00:42:59.050 --> 00:42:59.550 It is. 00:42:59.550 --> 00:43:00.570 So let's do this again. 00:43:00.570 --> 00:43:02.210 I'll print out a hash. 00:43:02.210 --> 00:43:03.560 And I'll increase j by one. 00:43:03.560 --> 00:43:08.000 And finally, I'll go back up to the top, ask, is j less than 4? 00:43:08.000 --> 00:43:09.030 Well, it still is. 00:43:09.030 --> 00:43:09.950 It's still 3. 00:43:09.950 --> 00:43:14.870 I'll print another hash, add one, and now when I go back up to the top 00:43:14.870 --> 00:43:19.100 to assess this condition, is j less than 4? 00:43:19.100 --> 00:43:21.050 Well, j is equal to 4. 00:43:21.050 --> 00:43:22.460 It's not less than 4. 00:43:22.460 --> 00:43:25.290 So we'll stop doing the code in this loop. 00:43:25.290 --> 00:43:27.350 And we'll instead print out the special character 00:43:27.350 --> 00:43:33.020 we saw in lecture, backslash n, that says we'll move to a new line. 00:43:33.020 --> 00:43:39.290 So that is one way, in this case, to get some set of hashes going along 00:43:39.290 --> 00:43:44.243 the bottom of, let's say, our pyramid using some kind of while loop. 00:43:44.243 --> 00:43:45.910 But there's also another way to do this. 00:43:45.910 --> 00:43:48.600 We could think of it not just in terms of a while loop, 00:43:48.600 --> 00:43:52.180 but in terms of another tool called a for loop. 00:43:52.180 --> 00:43:55.172 So a for loop is-- 00:43:55.172 --> 00:43:57.630 it can allow you to do very similar things to a while loop. 00:43:57.630 --> 00:44:00.720 But it's good for when you know the exact number of times 00:44:00.720 --> 00:44:02.130 you want to iterate. 00:44:02.130 --> 00:44:06.540 A while loop is great if you're not exactly sure how many times you 00:44:06.540 --> 00:44:10.770 want to do something, but you know you want to do it while something is true. 00:44:10.770 --> 00:44:14.160 A for loop is great when you know the exact number of times 00:44:14.160 --> 00:44:17.050 that you want to actually loop, in this case. 00:44:17.050 --> 00:44:20.610 So we could actually write that very same while loop using code a bit 00:44:20.610 --> 00:44:23.172 like this on the left-hand side. 00:44:23.172 --> 00:44:25.880 There's a few components here though that we need to break apart. 00:44:25.880 --> 00:44:31.580 So maybe the first piece here is going to be this part on the left-hand side. 00:44:31.580 --> 00:44:33.540 Let me actually zoom through this. 00:44:33.540 --> 00:44:35.270 Let me show you-- oops. 00:44:35.270 --> 00:44:36.330 Let me come back here. 00:44:36.330 --> 00:44:38.550 What do I want to show you? 00:44:38.550 --> 00:44:39.050 Yeah. 00:44:39.050 --> 00:44:41.383 So let's actually go back to the very beginning of this. 00:44:41.383 --> 00:44:44.840 If we go here, let's look at the very top of this for loop. 00:44:44.840 --> 00:44:54.040 So for int j equals 0 semicolon j is less than 4 semicolon j plus plus. 00:44:54.040 --> 00:44:57.370 That probably looks familiar from our while loop, right? 00:44:57.370 --> 00:44:59.950 We had those kind of very same things in our while loop. 00:44:59.950 --> 00:45:02.230 We first set j to be 0. 00:45:02.230 --> 00:45:05.530 Our condition was, is j less than 4? 00:45:05.530 --> 00:45:11.740 And the thing we did each loop was increase j by one using j plus plus. 00:45:11.740 --> 00:45:16.090 So we've taken all those same components but simply put them at the top of our 00:45:16.090 --> 00:45:17.500 for loop. 00:45:17.500 --> 00:45:19.490 And it allows us to simplify our syntax here. 00:45:19.490 --> 00:45:22.030 So on the inside, we just say what we're going 00:45:22.030 --> 00:45:27.490 to do for each iteration of this loop, which is print out a single hash. 00:45:27.490 --> 00:45:30.100 So to visualize this, on the right-hand side, 00:45:30.100 --> 00:45:33.280 let's say our very first thing we do in this for loop 00:45:33.280 --> 00:45:38.710 is we create a variable called j that gets this value called 0. 00:45:38.710 --> 00:45:42.340 Then we're going to print out a single hash. 00:45:42.340 --> 00:45:44.360 We're going to ask that question again. 00:45:44.360 --> 00:45:46.220 Is j less than 4? 00:45:46.220 --> 00:45:47.240 Well, it is. 00:45:47.240 --> 00:45:50.525 So we'll do that thing we said we'd do at the very end of this for loop, j 00:45:50.525 --> 00:45:51.350 plus plus. 00:45:51.350 --> 00:45:53.600 Now j becomes 1. 00:45:53.600 --> 00:45:56.030 We'll go through, print out another hash. 00:45:56.030 --> 00:45:58.790 And then we'll say, is 1 less than 4? 00:45:58.790 --> 00:45:59.690 It still is. 00:45:59.690 --> 00:46:02.000 I print another hash and keep going. 00:46:02.000 --> 00:46:04.620 And now we'll see, is 2 less than 4? 00:46:04.620 --> 00:46:05.120 Well, it is. 00:46:05.120 --> 00:46:07.160 So it will print another hash. j is 3. 00:46:07.160 --> 00:46:08.960 Now j is 4. 00:46:08.960 --> 00:46:11.960 No longer will it be printing out these hashes. 00:46:11.960 --> 00:46:14.720 That condition, j less than 4, is no longer true. 00:46:14.720 --> 00:46:19.970 We'll instead print backslash n to finish things off at the bottom. 00:46:19.970 --> 00:46:25.330 So what questions do we have here on the syntax for while loops and for loops, 00:46:25.330 --> 00:46:25.930 if any? 00:46:28.733 --> 00:46:31.150 A good question, is there any difference between the while 00:46:31.150 --> 00:46:34.960 loop and the for loop other than the initial condition 00:46:34.960 --> 00:46:39.370 and the update in the same line in the for loop? 00:46:39.370 --> 00:46:40.390 Any differences? 00:46:40.390 --> 00:46:42.860 I think the main difference is more syntax. 00:46:42.860 --> 00:46:45.490 So as you see here, they are in a different kind of order 00:46:45.490 --> 00:46:47.200 as we saw in the while loop. 00:46:47.200 --> 00:46:50.290 I'm going to go out on a limb and say I think that most 00:46:50.290 --> 00:46:52.780 things you could do in a while loop, you can also 00:46:52.780 --> 00:46:55.180 do in a for loop and vice versa. 00:46:55.180 --> 00:46:57.610 Generally though, the syntax of a while loop 00:46:57.610 --> 00:47:00.670 is better suited for if you have some condition, 00:47:00.670 --> 00:47:04.330 you're not sure when it will be true, but you know what that condition is. 00:47:04.330 --> 00:47:07.035 So you'd include that in the while loop, whereas a for loop 00:47:07.035 --> 00:47:09.160 is good because you kind of get to actually specify 00:47:09.160 --> 00:47:10.993 the exact number of times you want something 00:47:10.993 --> 00:47:13.452 to do that loop over and over again. 00:47:13.452 --> 00:47:15.910 If that makes sense and answers your question, let me know. 00:47:15.910 --> 00:47:19.980 If not, I can give you another take on that. 00:47:19.980 --> 00:47:22.800 Let's see. 00:47:22.800 --> 00:47:28.530 Why is the j plus plus now outside of those brackets here, these curly braces 00:47:28.530 --> 00:47:30.250 that you see on the left-hand side? 00:47:30.250 --> 00:47:34.230 So that's simply the way that the makers of C decided it would be. 00:47:34.230 --> 00:47:37.560 You might see some very similar syntax across different languages 00:47:37.560 --> 00:47:42.390 beyond C, also in things like Java and maybe even Python as well. 00:47:42.390 --> 00:47:45.960 Basically this allows us to simply make things a little more compact. 00:47:45.960 --> 00:47:49.800 We're moving that increment, what we do each loop, to increase this variable, 00:47:49.800 --> 00:47:50.340 j. 00:47:50.340 --> 00:47:55.380 We're moving it to the actual definition of the for loop. 00:47:55.380 --> 00:47:57.480 Nice. 00:47:57.480 --> 00:47:58.820 OK. 00:47:58.820 --> 00:48:04.130 So with these kinds of tools, I want to pose a question 00:48:04.130 --> 00:48:07.670 to you, which is, let's say we're able to get to a point 00:48:07.670 --> 00:48:10.400 where we're printing out a single line of hashes. 00:48:10.400 --> 00:48:16.530 This code here prints out a single line of hashes and moves to that new line. 00:48:16.530 --> 00:48:18.000 But let's think for a moment. 00:48:18.000 --> 00:48:22.350 What could I do to get not just a single line of hashes, 00:48:22.350 --> 00:48:28.705 but maybe even a full square of hashes, having multiple lines now? 00:48:31.570 --> 00:48:36.090 I have one loop to make a single line. 00:48:36.090 --> 00:48:38.590 I'm seeing an idea coming up in the chat. 00:48:38.590 --> 00:48:43.960 Maybe we could use another loop to have more than one line, 00:48:43.960 --> 00:48:47.260 not just a single line, but maybe multiple, like four lines of four 00:48:47.260 --> 00:48:49.902 hashes to make a square of hashes. 00:48:49.902 --> 00:48:50.860 And it's actually true. 00:48:50.860 --> 00:48:54.880 You can take a loop, like this, and put it inside 00:48:54.880 --> 00:48:58.340 of another loop, a bit like this here. 00:48:58.340 --> 00:49:04.570 So notice how the inner loop, this for int j equals 0, j is less than 4, 00:49:04.570 --> 00:49:08.530 j plus plus, that is still printing out a single line of hashes. 00:49:08.530 --> 00:49:14.290 But now I'm going to do that step four times per the for loop that 00:49:14.290 --> 00:49:20.590 is around that loop, for int i equals 0, i is less than 4, i plus plus. 00:49:20.590 --> 00:49:28.910 The result of this will be the square we see on the right-hand side of hashes. 00:49:28.910 --> 00:49:34.480 So as you're working on a program like Mario, don't be afraid to make a loop 00:49:34.480 --> 00:49:36.700 and then put that loop inside of, perhaps, 00:49:36.700 --> 00:49:39.190 another loop to help you solve the problem you're 00:49:39.190 --> 00:49:41.920 trying to solve in this case. 00:49:41.920 --> 00:49:45.400 Now, to help us focus even more on functions 00:49:45.400 --> 00:49:48.310 even beyond loops in particular, let's go ahead and actually try 00:49:48.310 --> 00:49:51.940 to take a first step towards writing that Mario problem that we 00:49:51.940 --> 00:49:53.770 see in this week's problem set. 00:49:53.770 --> 00:49:56.380 And, in this case, we're going to-- 00:49:56.380 --> 00:49:58.090 well, actually in the problem set, you're 00:49:58.090 --> 00:50:00.580 asked to write a right-aligned pyramid. 00:50:00.580 --> 00:50:05.090 In this case though, we'll actually write a left-aligned pyramid. 00:50:05.090 --> 00:50:08.530 So if you think of your right hand and your left hand and thinking which 00:50:08.530 --> 00:50:11.710 way should the pyramid go, a right-aligned pyramid kind of 00:50:11.710 --> 00:50:15.220 goes up to your right, whereas a left-aligned pyramid goes up 00:50:15.220 --> 00:50:16.240 to your left. 00:50:16.240 --> 00:50:19.870 And I would probably argue a left-aligned pyramid is a bit easier 00:50:19.870 --> 00:50:21.170 than a right-aligned pyramid. 00:50:21.170 --> 00:50:23.920 But I'll leave that part up to you as you work on the problem set. 00:50:23.920 --> 00:50:27.640 And today we'll focus on our left-aligned pyramid. 00:50:27.640 --> 00:50:31.300 So a left-aligned pyramid looks a bit like this. 00:50:31.300 --> 00:50:31.800 Oops. 00:50:31.800 --> 00:50:34.340 Looks a bit-- oh, sorry. 00:50:34.340 --> 00:50:37.400 I didn't have those slides in this presentation. 00:50:37.400 --> 00:50:37.970 That's OK. 00:50:37.970 --> 00:50:40.730 We will do, instead, talking about functions 00:50:40.730 --> 00:50:43.295 and what we could do to create a left-aligned pyramid if you 00:50:43.295 --> 00:50:44.420 can visualize in your head. 00:50:44.420 --> 00:50:47.270 Let me go to my actual code space over here, what that looks like. 00:50:47.270 --> 00:50:50.752 I'll say, code pyramid.txt. 00:50:50.752 --> 00:50:51.960 And I'll show you an example. 00:50:51.960 --> 00:50:57.290 So here, this is an example of a left-aligned pyramid. 00:50:57.290 --> 00:51:00.050 This is a pyramid of height five. 00:51:00.050 --> 00:51:02.840 But if I wanted to have a pyramid of height four, 00:51:02.840 --> 00:51:05.750 I could simply get rid of a hash here and a hash there 00:51:05.750 --> 00:51:07.350 and a hash there and a hash there. 00:51:07.350 --> 00:51:11.030 And now I have a pyramid of height four. 00:51:11.030 --> 00:51:14.900 And pyramid of height three too, I could say get rid of this hash and this hash 00:51:14.900 --> 00:51:16.387 and this hash and this hash. 00:51:16.387 --> 00:51:18.095 And now I have a pyramid of height three. 00:51:18.095 --> 00:51:22.910 I could keep going, a pyramid of height two and even a pyramid of height one, 00:51:22.910 --> 00:51:27.270 just to help you visualize what's at stake in this problem here. 00:51:27.270 --> 00:51:32.480 So if we want to make our very own pyramid, a program that 00:51:32.480 --> 00:51:36.588 prints our very own pyramid, why don't we go ahead and make a file 00:51:36.588 --> 00:51:37.130 called Mario. 00:51:37.130 --> 00:51:38.750 I'll say code mario.c. 00:51:38.750 --> 00:51:41.180 And inside I'll do the usual things. 00:51:41.180 --> 00:51:44.090 I'll include stdio.h. 00:51:44.090 --> 00:51:51.050 I'll include cs50.h, these header files that have the CS50 library and Standard 00:51:51.050 --> 00:51:53.760 I/O library somewhat defined in them. 00:51:53.760 --> 00:51:56.900 I'll then say int main(void) to kick off this program. 00:51:56.900 --> 00:52:02.500 And on the inside, what's the first thing I should do? 00:52:02.500 --> 00:52:05.230 I probably want to get height from the user. 00:52:05.230 --> 00:52:07.960 But how could I do that, those of you who are here live? 00:52:07.960 --> 00:52:12.430 How could I get a height from the user to print out this pyramid? 00:52:16.640 --> 00:52:21.970 So I'm seeing, maybe I want to use something like an integer 00:52:21.970 --> 00:52:25.820 to store the height because, again, this pyramid will be some number of blocks 00:52:25.820 --> 00:52:26.320 tall. 00:52:26.320 --> 00:52:27.370 So I like the idea. 00:52:27.370 --> 00:52:28.300 Let's go with that. 00:52:28.300 --> 00:52:30.640 I'll say int height here. 00:52:30.640 --> 00:52:35.830 And I could, for instance, say int height equals 5 off the bat. 00:52:35.830 --> 00:52:38.950 But I could probably get the input from the user using that function 00:52:38.950 --> 00:52:41.590 we saw earlier, get_int, like this. 00:52:41.590 --> 00:52:45.370 And I'll prompt the user for some height. 00:52:45.370 --> 00:52:49.110 So now it's a good idea, once I'm at some stopping point in my program, 00:52:49.110 --> 00:52:51.420 to try to compile it and see if it works. 00:52:51.420 --> 00:52:56.280 I'll then type make mario, hit Enter, and I'll type ./mario. 00:52:56.280 --> 00:52:58.290 I'll see I'm prompted for a height. 00:52:58.290 --> 00:53:01.000 I'll hit 5 here and nothing happens. 00:53:01.000 --> 00:53:06.880 But at least I know my program tends to work at this particular stage. 00:53:06.880 --> 00:53:12.400 So let's think about how we could use functions to be solving this problem. 00:53:12.400 --> 00:53:15.510 Now, here we have this function called get_int. 00:53:15.510 --> 00:53:19.560 But it's worth actually diving into what get_int is doing for us 00:53:19.560 --> 00:53:22.320 and talking through some vocabulary that can help us understand 00:53:22.320 --> 00:53:24.450 what get_int is actually doing. 00:53:24.450 --> 00:53:26.760 So for that, we'll focus on functions. 00:53:26.760 --> 00:53:31.350 And notice here how we can actually define get_int. 00:53:31.350 --> 00:53:34.780 We, at CS50, define this function for you. 00:53:34.780 --> 00:53:37.440 You don't see its definition in your actual code 00:53:37.440 --> 00:53:39.960 because you can only just use it now. 00:53:39.960 --> 00:53:43.300 But we did work on defining this function for you. 00:53:43.300 --> 00:53:46.060 And notice a few pieces of this function. 00:53:46.060 --> 00:53:51.090 Notice how, up front, we have this idea of the name for this function, 00:53:51.090 --> 00:53:53.130 this one called get_int. 00:53:53.130 --> 00:53:55.530 We could think of it kind of like that black box 00:53:55.530 --> 00:53:57.070 we saw Dave mention in lecture. 00:53:57.070 --> 00:54:02.700 We have some algorithm, some function, that is called get_int, 00:54:02.700 --> 00:54:07.180 some black box here that's going to take an input and give us some output. 00:54:07.180 --> 00:54:10.360 Now, we can also define the output of get_int. 00:54:10.360 --> 00:54:12.490 We could do this part for you. 00:54:12.490 --> 00:54:15.340 We said that it will take an input, in this case, 00:54:15.340 --> 00:54:18.620 called prompt that is of type string. 00:54:18.620 --> 00:54:23.650 So notice how when I used get_int, I typed in a string as the input 00:54:23.650 --> 00:54:24.580 to get_int. 00:54:24.580 --> 00:54:28.070 This input was called height followed by a colon. 00:54:28.070 --> 00:54:32.530 So now, in this case, we see that get_int takes a string that 00:54:32.530 --> 00:54:35.380 within that function is called prompt. 00:54:35.380 --> 00:54:37.480 And then what does get_int give us? 00:54:37.480 --> 00:54:42.190 Well, at the very end of the day, it gives us back an integer, in this case, 00:54:42.190 --> 00:54:46.130 a whole number that the user actually typed in themselves. 00:54:46.130 --> 00:54:50.300 And so, of course, we would use this function a bit like this. 00:54:50.300 --> 00:54:53.990 We could say, take in a prompt to give us back two or four or so on. 00:54:53.990 --> 00:54:58.810 But we use it using int height gets the value of something 00:54:58.810 --> 00:55:01.270 like this function, get_int followed by height. 00:55:01.270 --> 00:55:04.330 And when this function runs, it returns to us 00:55:04.330 --> 00:55:08.290 what we said it would return over here, something of type integer, 00:55:08.290 --> 00:55:11.120 if that makes sense. 00:55:11.120 --> 00:55:17.010 So questions then on this function declaration, what we did over here 00:55:17.010 --> 00:55:19.785 to define what get_int is doing for us? 00:55:28.110 --> 00:55:28.920 OK. 00:55:28.920 --> 00:55:33.310 Not seeing too many questions here. 00:55:33.310 --> 00:55:36.930 So why don't we keep working on our Mario program? 00:55:36.930 --> 00:55:38.280 I'll go back over here. 00:55:38.280 --> 00:55:45.150 And we saw before that I could print out a single row of hashes 00:55:45.150 --> 00:55:46.890 using a for loop, right? 00:55:46.890 --> 00:55:50.130 But maybe it would be worthwhile to consider 00:55:50.130 --> 00:55:54.390 how I could put that code that prints out a single line of hashes 00:55:54.390 --> 00:55:57.360 into its own separate function that I could 00:55:57.360 --> 00:56:01.900 use in my main part of my program, this one called main up here. 00:56:01.900 --> 00:56:08.520 If I wanted to define that code that writes that line of hashes for me 00:56:08.520 --> 00:56:11.790 separately, I could probably put it in its own function. 00:56:11.790 --> 00:56:16.290 And to define my own function, I could probably go down below here 00:56:16.290 --> 00:56:17.820 and say something like this. 00:56:17.820 --> 00:56:20.040 Why don't I create this new function. 00:56:20.040 --> 00:56:23.520 I'll call it, in this case, print_row. 00:56:23.520 --> 00:56:28.920 And what kind of input do you think print_row should take, ideally? 00:56:28.920 --> 00:56:33.270 Maybe I want to modify the length of the row. 00:56:33.270 --> 00:56:38.480 How could I say print_row takes an input to modify the length? 00:56:38.480 --> 00:56:39.770 Any ideas in the chat? 00:56:43.240 --> 00:56:47.680 One thing I could do is think, well, the input to this function, 00:56:47.680 --> 00:56:51.190 I want it to be the number of hashes to print on the row. 00:56:51.190 --> 00:56:54.410 So that seems to be a number, an integer. 00:56:54.410 --> 00:57:00.220 So I could say, print row takes an input that is of type integer. 00:57:00.220 --> 00:57:01.880 And I have to give it a name. 00:57:01.880 --> 00:57:05.560 I'll call it, in this case, length, the length of that row. 00:57:05.560 --> 00:57:10.180 And now I'll think, what should print_row return to me? 00:57:10.180 --> 00:57:12.022 Well, it doesn't really return me a value. 00:57:12.022 --> 00:57:14.980 If I'm going to use it, it simply just prints things out to the screen. 00:57:14.980 --> 00:57:18.220 In lecture, we saw a difference between return values and side effects. 00:57:18.220 --> 00:57:19.970 In this case, it just has a side effect. 00:57:19.970 --> 00:57:21.470 It just prints things to the screen. 00:57:21.470 --> 00:57:25.360 So actually make sure that this return value is simply void. 00:57:25.360 --> 00:57:27.380 It's nothing in particular. 00:57:27.380 --> 00:57:31.100 So now print row is a separate function. 00:57:31.100 --> 00:57:34.070 It has an input called length that is of type int. 00:57:34.070 --> 00:57:36.220 And it returns to me nothing in particular, 00:57:36.220 --> 00:57:38.510 just prints things out to the screen. 00:57:38.510 --> 00:57:43.070 So now inside of print row, I could have that very same loop we 00:57:43.070 --> 00:57:44.960 saw earlier, perhaps a for loop. 00:57:44.960 --> 00:57:47.330 I'll say for int i is 0. 00:57:47.330 --> 00:57:49.790 And i is less than-- 00:57:49.790 --> 00:57:51.200 i is less than what? 00:57:51.200 --> 00:57:57.710 Before, we saw 4 to get a length of 4 or 3 to get a length of 3. 00:57:57.710 --> 00:58:00.920 But now I want it to be a variable length. 00:58:00.920 --> 00:58:04.960 I could decide later what I want the length to be. 00:58:04.960 --> 00:58:06.710 I'm seeing some folks saying maybe I could 00:58:06.710 --> 00:58:11.150 use this variable that's input to print_row called length. 00:58:11.150 --> 00:58:12.020 I'll try that. 00:58:12.020 --> 00:58:14.660 i is less than length i plus plus. 00:58:14.660 --> 00:58:22.220 So now when I use this function print_row, I could pass in some number. 00:58:22.220 --> 00:58:26.180 And then I'll loop that many times in my for loop. 00:58:26.180 --> 00:58:27.740 And what will I do for each loop? 00:58:27.740 --> 00:58:32.790 Well, I'll print out, in this case, I will print out a hash each time. 00:58:32.790 --> 00:58:37.370 At the end of all that looping, I'll print out simply backslash n 00:58:37.370 --> 00:58:40.130 to move to a new line. 00:58:40.130 --> 00:58:43.260 So this is my print_row function down below. 00:58:43.260 --> 00:58:46.670 Now, if I go up top, I could try to use print_row. 00:58:46.670 --> 00:58:51.900 I could say, well, I want to print a row that has the length of four, like this. 00:58:51.900 --> 00:58:54.740 So I'll first get the input of height from the user. 00:58:54.740 --> 00:58:56.360 And I'll not use it for now. 00:58:56.360 --> 00:58:59.570 I'll just use print_row with the value 4. 00:58:59.570 --> 00:59:04.160 I'll go to my terminal here, type make mario, hit Enter, 00:59:04.160 --> 00:59:06.690 and I seem to be getting an error. 00:59:06.690 --> 00:59:08.760 What is the error? 00:59:08.760 --> 00:59:15.270 You'll see here, implicit declaration of function print_row is invalid in C99. 00:59:15.270 --> 00:59:17.760 What ideas does that bring up for you here? 00:59:17.760 --> 00:59:19.095 What might I be doing wrong? 00:59:23.315 --> 00:59:25.190 Yeah, so it seems I haven't actually included 00:59:25.190 --> 00:59:27.453 what we're calling the prototype for this function. 00:59:27.453 --> 00:59:30.620 So if I look down below here-- actually, if I read my program top to bottom, 00:59:30.620 --> 00:59:34.070 like C would, I'll see I'm going to include some files, 00:59:34.070 --> 00:59:38.120 have a main function, get the height, and then call this function 00:59:38.120 --> 00:59:42.320 or use this function called print_row and give it the value 4. 00:59:42.320 --> 00:59:45.020 But up until now, if I'm reading top to bottom, 00:59:45.020 --> 00:59:49.040 I actually haven't seen the definition for print_row. 00:59:49.040 --> 00:59:49.652 Where is it? 00:59:49.652 --> 00:59:50.360 Well, it's below. 00:59:50.360 --> 00:59:51.830 It's down here on line 10. 00:59:51.830 --> 00:59:55.460 But I can't be calling this function if I 00:59:55.460 --> 00:59:59.910 haven't told C that's going to come up in my program yet. 00:59:59.910 --> 01:00:03.950 So what I should do instead is take the function prototype, that 01:00:03.950 --> 01:00:07.880 is its name, its input, and its return value, 01:00:07.880 --> 01:00:13.610 and put it at the top of my program, often by convention, below my includes. 01:00:13.610 --> 01:00:15.860 And I'll follow it with a semicolon here, 01:00:15.860 --> 01:00:18.620 saying this is my function prototype. 01:00:18.620 --> 01:00:22.640 This is the line of code that tells C, I promise 01:00:22.640 --> 01:00:26.590 I'm going to define for you what print row is later. 01:00:26.590 --> 01:00:29.740 But for now, just let me use it when I say I'm going to use it. 01:00:29.740 --> 01:00:34.020 So now in main, hopefully C doesn't actually 01:00:34.020 --> 01:00:36.390 complain when I use print_row because up top I told it 01:00:36.390 --> 01:00:39.970 exactly what I'm going to use as well. 01:00:39.970 --> 01:00:43.750 So now I'll type make mario, hit Enter, and that seems to work. 01:00:43.750 --> 01:00:49.380 So now I'll type ./mario, hit Enter, say the height is 6, hit Enter, 01:00:49.380 --> 01:00:55.130 and I get this line of only four hashes. 01:00:55.130 --> 01:00:58.610 But what could I do to update this program 01:00:58.610 --> 01:01:05.610 to print out not just four hashes, but the same number that the user typed in? 01:01:05.610 --> 01:01:07.800 I want to modify this piece here. 01:01:07.800 --> 01:01:09.480 But how could I modify it? 01:01:13.323 --> 01:01:14.490 Yeah, I'm seeing some ideas. 01:01:14.490 --> 01:01:16.958 I could probably use this variable called height. 01:01:16.958 --> 01:01:18.750 So we know that this variable called height 01:01:18.750 --> 01:01:22.140 is a container for the number I typed in, in this case, 6. 01:01:22.140 --> 01:01:27.120 So if I want to pass in that same value to print_row for it to print out 01:01:27.120 --> 01:01:33.690 a row of that length, I could instead say print_row parentheses height 01:01:33.690 --> 01:01:35.200 and save that. 01:01:35.200 --> 01:01:40.710 Now I'll type make mario, ./mario, and type in a height of 5. 01:01:40.710 --> 01:01:46.080 Now I get, in this case, five hashes down below. 01:01:46.080 --> 01:01:51.180 And notice in particular that in this case, the name of the variable that I 01:01:51.180 --> 01:01:54.420 am, what we call, passing into, or inputting to, 01:01:54.420 --> 01:01:58.470 this function print_row that is not the same as the variable 01:01:58.470 --> 01:02:02.640 I said I would get down below, this integer called length. 01:02:02.640 --> 01:02:08.430 What actually happens is height, we have storing a value, in this case, 01:02:08.430 --> 01:02:13.470 five down below, that value for height is given to print_row. 01:02:13.470 --> 01:02:17.970 And as long as I'm running the code in print_row, 01:02:17.970 --> 01:02:24.010 that value, 4, will be associated with this name, length, in this case. 01:02:24.010 --> 01:02:28.920 So I took the value that height stored, 5, I gave it to print_row. 01:02:28.920 --> 01:02:32.790 And as long as print_row is running, that value, 5, 01:02:32.790 --> 01:02:37.750 is now called length in the context of this function print_row. 01:02:37.750 --> 01:02:42.690 We call that this idea of scope in computer science. 01:02:42.690 --> 01:02:47.900 So here we have a way to take the user's height and a way 01:02:47.900 --> 01:02:51.080 to print a row of that height. 01:02:51.080 --> 01:02:52.880 We're not quite all the way there yet. 01:02:52.880 --> 01:02:56.330 But what questions do we have on the code so far? 01:03:00.555 --> 01:03:01.680 I'm seeing a question here. 01:03:01.680 --> 01:03:04.530 Is there any situation where not prototyping but declaring 01:03:04.530 --> 01:03:07.110 the function above main would be better? 01:03:07.110 --> 01:03:11.310 So notice here we had the prototype for print_row above main. 01:03:11.310 --> 01:03:14.650 But we had the definition for print_row below it. 01:03:14.650 --> 01:03:19.440 Now, I think the question is asking, is it ever useful to do essentially this, 01:03:19.440 --> 01:03:23.860 to cut and paste this and put it above main, a bit like this? 01:03:23.860 --> 01:03:25.110 You certainly could. 01:03:25.110 --> 01:03:27.870 But I find it more readable, in this case, 01:03:27.870 --> 01:03:33.090 to have the main function up first because when we run our program, 01:03:33.090 --> 01:03:39.570 the main function will always be the first to run, so more style 01:03:39.570 --> 01:03:44.310 for style's sake than anything else, in this case. 01:03:44.310 --> 01:03:45.030 Question here. 01:03:45.030 --> 01:03:50.730 In line 4 and 12, you have declared void print_row int length two times. 01:03:50.730 --> 01:03:54.292 Why is that OK because we can't do that with variables? 01:03:54.292 --> 01:03:55.750 That's actually a good observation. 01:03:55.750 --> 01:04:00.840 So if I were to, for instance on line eight, create a variable called height 01:04:00.840 --> 01:04:05.440 and then later on create a new variable called height, like this, 01:04:05.440 --> 01:04:09.180 I would find that C, when I try to compile my program, doesn't like that. 01:04:09.180 --> 01:04:13.470 I can only have one variable under one name at the same time. 01:04:13.470 --> 01:04:15.960 I can't have two variables with the same name. 01:04:15.960 --> 01:04:19.500 Here though it seems like I have two functions with the same name. 01:04:19.500 --> 01:04:24.150 I have one called print_row up here and print_row down below. 01:04:24.150 --> 01:04:28.770 I think the answer to this is that built in to C 01:04:28.770 --> 01:04:32.790 is this syntax that if you have a function you want to use and to define 01:04:32.790 --> 01:04:36.360 later in your code, you simply copy and paste the prototype, 01:04:36.360 --> 01:04:40.380 its name, its input, its output, put it at the top of your file, 01:04:40.380 --> 01:04:44.510 and C knows this is a function that will later be defined. 01:04:44.510 --> 01:04:49.180 It's on a separate function with the same name. 01:04:49.180 --> 01:04:50.830 And one more question here. 01:04:50.830 --> 01:04:54.640 Why is height printing length when logically height is up and down 01:04:54.640 --> 01:04:55.630 and not left to right? 01:04:55.630 --> 01:04:56.630 That's a great question. 01:04:56.630 --> 01:04:58.670 We're going to fix that in just a moment. 01:04:58.670 --> 01:05:02.320 So here we notice that, in my separate file-- 01:05:02.320 --> 01:05:05.830 I'm going to make code pyramid.txt. 01:05:05.830 --> 01:05:10.510 If I wanted a pyramid of height, let's say, three, 01:05:10.510 --> 01:05:15.620 notice how the bottom row has length three, in this case. 01:05:15.620 --> 01:05:21.010 So a pyramid of height three, the bottom most row, that has the length of three. 01:05:21.010 --> 01:05:27.350 But also notice how above this has length two and then length one up top. 01:05:27.350 --> 01:05:30.400 So there's probably an association between the height 01:05:30.400 --> 01:05:33.640 and the actual length of these rows I'm printing. 01:05:33.640 --> 01:05:36.560 So what if we tried something a bit like this. 01:05:36.560 --> 01:05:39.070 I know I want to print more than one row. 01:05:39.070 --> 01:05:43.780 And I probably want to do it in a way that involves a loop. 01:05:43.780 --> 01:05:46.430 We saw a loop as a way to do things more than once. 01:05:46.430 --> 01:05:56.270 So I could say maybe something like, for int i equals 0 i is less than-- 01:05:56.270 --> 01:06:01.400 well, how many rows should I print in this case? 01:06:01.400 --> 01:06:07.360 If I have a pyramid of height three, how many rows should I print? 01:06:07.360 --> 01:06:08.350 Seems like three. 01:06:08.350 --> 01:06:12.850 So I think, in this case, it's safe to loop height number of times 01:06:12.850 --> 01:06:16.850 and increase i by one every time we go. 01:06:16.850 --> 01:06:21.010 So now inside this loop, I'll print_row. 01:06:21.010 --> 01:06:24.530 And maybe I'll keep it the same with this input called height. 01:06:24.530 --> 01:06:25.580 So let's try that. 01:06:25.580 --> 01:06:32.470 I'll say make mario, ./mario, height of three. 01:06:32.470 --> 01:06:34.620 And I got a square. 01:06:34.620 --> 01:06:37.500 So it seems like we're getting there. 01:06:37.500 --> 01:06:40.940 But I need to change something about this program. 01:06:40.940 --> 01:06:42.680 What should I change do you think? 01:06:49.870 --> 01:06:51.920 So I'm seeing a few ideas. 01:06:51.920 --> 01:06:55.690 One is actually to use this variable here, 01:06:55.690 --> 01:07:00.170 i, that we declared and initialized inside of our for loop. 01:07:00.170 --> 01:07:05.170 So as long as we are within this for loop, within its curly braces, 01:07:05.170 --> 01:07:10.120 I actually have access to this variable, i. i is what's called in scope. 01:07:10.120 --> 01:07:13.550 I could use it throughout this portion of my code. 01:07:13.550 --> 01:07:17.950 So maybe I don't want to print a row that is of length height, 01:07:17.950 --> 01:07:20.440 but maybe of length i. 01:07:20.440 --> 01:07:22.720 So first, i would be zero. 01:07:22.720 --> 01:07:24.130 And then it would be one. 01:07:24.130 --> 01:07:26.360 And then it would be two and so on. 01:07:26.360 --> 01:07:30.430 So actually, if I look at my pyramid, my very first row 01:07:30.430 --> 01:07:35.410 is one, then two, then three. 01:07:35.410 --> 01:07:39.310 So maybe I don't want to first print out zero, I want to print out one. 01:07:39.310 --> 01:07:44.060 But how could I change this to not print out zero first, but one? 01:07:44.060 --> 01:07:44.720 Any ideas? 01:07:47.610 --> 01:07:50.768 I'm seeing maybe I could just add one as we go. 01:07:50.768 --> 01:07:52.060 So that's actually a good idea. 01:07:52.060 --> 01:07:54.990 Why don't I say, first i is zero. 01:07:54.990 --> 01:07:57.990 But when i is zero, I want to print out one hash. 01:07:57.990 --> 01:08:01.050 So I'll say, just take i and increase it by one. 01:08:01.050 --> 01:08:05.970 Well, next, i will be one after going through this loop. 01:08:05.970 --> 01:08:08.460 Then I'll say, well, how many hashes do I want to print? 01:08:08.460 --> 01:08:10.960 Well, just one more than what i currently is. 01:08:10.960 --> 01:08:15.600 So I'll maybe say that's print out a row of length i plus one again. 01:08:15.600 --> 01:08:17.580 And then i will be two. 01:08:17.580 --> 01:08:18.893 I want three hashes. 01:08:18.893 --> 01:08:20.310 So I'll just say i plus one again. 01:08:20.310 --> 01:08:21.560 And so maybe this should work. 01:08:21.560 --> 01:08:27.390 So I'll say, make mario and then ./mario, pyramid of height three. 01:08:27.390 --> 01:08:29.170 And now I seem to be getting somewhere. 01:08:29.170 --> 01:08:31.069 So I'll make my terminal bigger. 01:08:31.069 --> 01:08:37.710 I'll say, make mario, ./mario again, height of five. 01:08:37.710 --> 01:08:43.200 And I seem to be getting what I'm looking for, this left-aligned pyramid. 01:08:43.200 --> 01:08:47.939 So let me ask, what questions do we have on this implementation of Mario 01:08:47.939 --> 01:08:51.465 using left-aligned pyramids and functions in general? 01:08:59.689 --> 01:09:00.200 All right. 01:09:00.200 --> 01:09:01.529 So seeing none here. 01:09:01.529 --> 01:09:03.740 And, again, the goal for these sections is 01:09:03.740 --> 01:09:07.109 to give you some tools to which you can go off and solve this week's problem 01:09:07.109 --> 01:09:07.609 set. 01:09:07.609 --> 01:09:10.370 And now, one more tool I'll give to you is 01:09:10.370 --> 01:09:13.790 to think about how you could use the same idea of defining a function 01:09:13.790 --> 01:09:17.899 to actually work in your favor on this next Mario problem that 01:09:17.899 --> 01:09:22.620 asks you to write not a left-aligned pyramid, but a right-aligned pyramid. 01:09:22.620 --> 01:09:26.960 So we saw just now we created some function that looked 01:09:26.960 --> 01:09:28.700 a bit like this called print_row. 01:09:28.700 --> 01:09:30.710 In this case, it takes an input called bricks. 01:09:30.710 --> 01:09:32.870 We called it length, same thing. 01:09:32.870 --> 01:09:37.520 Here we're able to take a length of hashes to print 01:09:37.520 --> 01:09:39.620 and then just print that out as we go. 01:09:39.620 --> 01:09:43.640 But now you could consider expanding that function's capability 01:09:43.640 --> 01:09:48.319 to take not just one input, but two, maybe one for some number of spaces 01:09:48.319 --> 01:09:52.279 before the actual bricks or hashes come up and then one 01:09:52.279 --> 01:09:55.430 that takes in the number of bricks to actually print out those hashes 01:09:55.430 --> 01:09:56.370 as you go. 01:09:56.370 --> 01:10:01.070 So notice how over here, in pyramid.txt, if I want this to be right-aligned, 01:10:01.070 --> 01:10:05.630 I first print out some number of spaces and then my 01:10:05.630 --> 01:10:09.230 hashes as we go to move this pyramid from being left-aligned 01:10:09.230 --> 01:10:11.690 to now being right-aligned. 01:10:11.690 --> 01:10:16.340 So we'll leave you with that to consider as you solve Mario this week. 01:10:16.340 --> 01:10:18.997 But that was section one here for CS50. 01:10:18.997 --> 01:10:20.580 We'll hope to see you in future weeks. 01:10:20.580 --> 01:10:24.430 Thank you all for joining and see you next time.