Comp 11 Lectures Mike Shah Tufts University June 26, 2017 Mike Shah (Tufts University) Comp 11 Lectures June 26, 2017 1 / 57
Please do not distribute or host these slides without prior permission. Mike Shah (Tufts University) Comp 11 Lectures June 26, 2017 2 / 57
Pointers Mike Shah (Tufts University) Comp 11 Lectures June 26, 2017 3 / 57
Comp 11 - Pre-Class warm up If I write the address to your house down on an envelope, I can conveniently send that letter to you and retrieve some response. There are alternatives though I could just move you and your house to where I am standing! Or just rebuild a copy of your house next to me (and also clone you). Mike Shah (Tufts University) Comp 11 Lectures June 26, 2017 4 / 57
Lecture Mike Shah (Tufts University) Comp 11 Lectures June 26, 2017 5 / 57
Radia Perlman Figure 1: Radia Perlman is a MIT Ph.D. graduate best known for her work in computer networks. She holds over 100 patents and is responsible for transforming how Ethernets are able to utilized to create large networks Mike Shah (Tufts University) Comp 11 Lectures June 26, 2017 6 / 57
Memory and Pass by Reference Mike Shah (Tufts University) Comp 11 Lectures June 26, 2017 7 / 57
Memory We have talked about memory briefly when we talked about arrays. A modern computer these days, has quite a bit of memory available. You have memory in your hard disk, memory in RAM, and storage in the Cache. These are all different levels of memory, and our operating system helps us manage where it goes. As an example, your operating system hands you memory, when you run your program Mike Shah (Tufts University) Comp 11 Lectures June 26, 2017 8 / 57
Here is some Memory when you start your program (Note that each box represents 4 bytes of memory in the following slides.) Mike Shah (Tufts University) Comp 11 Lectures June 26, 2017 9 / 57
Then you start storing things int a = 2; Mike Shah (Tufts University) Comp 11 Lectures June 26, 2017 10 / 57
Then you start storing things int a = 2; int b = 7; Mike Shah (Tufts University) Comp 11 Lectures June 26, 2017 11 / 57
And some more int a = 2; int b = 7; int c = 9; Mike Shah (Tufts University) Comp 11 Lectures June 26, 2017 12 / 57
Maybe an entire array int a = 2; int b = 7; int c = 9; int d[9]; // Notice, how the array is contiguous in our memory! Mike Shah (Tufts University) Comp 11 Lectures June 26, 2017 13 / 57
Space in C++ So remember what these little boxes are. They are bytes of memory. Depending on the variable or data structure we use, they take up a different amount of memory. Mike Shah (Tufts University) Comp 11 Lectures June 26, 2017 14 / 57
Sample Data Sizes Type Number of Bytes bool 1 char 1 short 2 float 4 int 4 long 4 double 8 long long 8 Mike Shah (Tufts University) Comp 11 Lectures June 26, 2017 15 / 57
Lets allocate some more memory, of different types int a = 2; int b = 7; int c = 9; int d[9]; double e = 1.01; // Ah, notice that a double takes twice as much space as our int because it is twice as many bytes Mike Shah (Tufts University) Comp 11 Lectures June 26, 2017 16 / 57
A closer look at just one of the boxes int a = 2; 2 So let s just look at the first integer. It contains our integer value But what about the second part of the box? Mike Shah (Tufts University) Comp 11 Lectures June 26, 2017 17 / 57
An address! int a = 2; 2 The address (in hexadecimal) tells us where we are! So just like addresses we have in real life, memory has a unique address. 0x56235325 Mike Shah (Tufts University) Comp 11 Lectures June 26, 2017 18 / 57
Okay, but who cares? Well, having access to the memory address is actually quite powerful! In fact, this is what makes a language like C++ very powerful. We are close to the metal, and have the opportunity to work with the hardware. And at the very least, our C++ compilers and operating systems care about memory (and our end users!) Mike Shah (Tufts University) Comp 11 Lectures June 26, 2017 19 / 57
Address Of If I want to see the memory address, I can use the ampersand operator. Here is an example. 1 #i n c l u d e <i o s t r e a m > 2 3 i n t main ( ) { 4 5 i n t x = 5 6 7 ; 6 7 s t d : : cout << Address o f x i s : << &x << \n ; 8 9 r e t u r n 0 ; 0 } Listing 1: Where in our memory is a variable Mike Shah (Tufts University) Comp 11 Lectures June 26, 2017 20 / 57
Reference Neat, so we can get the address of some variable in memory. We now know where it lives. But we do not get the actual value. Instead we are getting a reference to where some value resides. So when you think &, you think reference from now on. What does this allow us to do? (where is the power? See next slide) Mike Shah (Tufts University) Comp 11 Lectures June 26, 2017 21 / 57
Pass by Value In this class, we have always passed by value. That is, we have not used the & sign, which is pass by reference. When I say pass by, I am referring to functions, lets take a look at an example. Mike Shah (Tufts University) Comp 11 Lectures June 26, 2017 22 / 57
Pass by Value - Example 1 #i n c l u d e <i o s t r e a m > 2 3 v o i d s e t V a l u e ( i n t x ) { 4 x = 9999; 5 } 6 7 i n t main ( ) { 8 9 i n t a = 6 ; 0 s e t V a l u e ( a ) ; 1 // What i s a h e r e? 2 s t d : : cout << a << \n ; 3 4 r e t u r n 0 ; 5 } Listing 2: Pass by Value Mike Shah (Tufts University) Comp 11 Lectures June 26, 2017 23 / 57
Why is a not 9999? 1 #i n c l u d e <i o s t r e a m > 2 3 v o i d s e t V a l u e ( i n t x ) { 4 x = 9999; 5 } 6 7 i n t main ( ) { 8 9 i n t a = 6 ; 0 s e t V a l u e ( a ) ; 1 // What i s a h e r e? 2 s t d : : cout << a << \n ; 3 4 r e t u r n 0 ; 5 } Listing 3: Pass by Value Well, when we pass by value, we are actually passing a copy of a on the stack. So pass by value, is copying a value into the function to be used, but it does not modify the value. Where does that value live again? On the stack (see 2 bullet points up) Mike Shah (Tufts University) Comp 11 Lectures June 26, 2017 24 / 57
Why is a not 9999 - The Stack Table 1: This is a stack with two items parameter 1 - int a return value 4 bytes of memory here In this case, void Stack Memory is allocated when we call a function. The amount of memory is the number of parameters we pass (in our previous example, 1 int), and the number of items we need to return. When we are done with the stack, C++ (and the OS) wants to reclaim that memory for other functions. Mike Shah (Tufts University) Comp 11 Lectures June 26, 2017 25 / 57
Pass by Reference - Example 1 #i n c l u d e <i o s t r e a m > 2 3 // A one c h a r a c t e r change! 4 v o i d s e t V a l u e ( i n t &x ) { 5 x = 9999; 6 } 7 8 i n t main ( ) { 9 0 i n t a = 6 ; 1 s e t V a l u e ( a ) ; 2 // What i s a h e r e? 3 s t d : : cout << a << \n ; 4 5 r e t u r n 0 ; 6 } Listing 4: Pass by Reference Mike Shah (Tufts University) Comp 11 Lectures June 26, 2017 26 / 57
Pass by Reference So why does it work? Remember what we are passing into the function this time We are saying, pass the address of an int type. The address lives in our huge grid of memory that we saw earlier. This means that if we modify an address that is not on the stack, it does not go away with the stack after the function call. Mike Shah (Tufts University) Comp 11 Lectures June 26, 2017 27 / 57
A closer look 1 // Pass x by r e f e r e n c e 2 v o i d s e t V a l u e ( i n t &x ) { 3 // Whatever i s i n the memory at x, s e t 4 // t h a t i n t e g e r v a l u e to 9999 5 x = 9999; 6 } Listing 5: Annotated function example Mike Shah (Tufts University) Comp 11 Lectures June 26, 2017 28 / 57
A quick review Pass by reference means we are only passing an address(0x56235325) to a function, not that actual value. Nothing more, nothing less. Just use the ampersand &. Remember, ampersand is address of, where something is stored in memory. Mike Shah (Tufts University) Comp 11 Lectures June 26, 2017 29 / 57
Stack Memory is different! Pass by value means copying 1 #i n c l u d e <i o s t r e a m > 2 3 v o i d memoryonstack ( i n t a ) { 4 s t d : : cout << &a << \n ; 5 } 6 7 i n t main ( ) { 8 i n t i = 5 ; 9 // i s a d d r e s s s h o u l d be the same 0 // i f i t i s i n the same p l a c e i n memory. 1 // But no! You w i l n o t i c e a copy i s made 2 // ( and s t o r e d where? the s t a c k! ) 3 memoryonstack ( i ) ; 4 s t d : : cout << &i << \n ; 5 6 r e t u r n 0 ; 7 } Listing 6: Annotated function example Mike Shah (Tufts University) Comp 11 Lectures June 26, 2017 30 / 57
Pointers Mike Shah (Tufts University) Comp 11 Lectures June 26, 2017 31 / 57
We have another tool I have exciting news, we have another tool to work with! The asterisk operator *, which is a pointer. A pointer is a qualifier to a type that says point to memory at this location. We might want to still pass by value, but not by reference if we do not want a mutation to take place. Again, a pointer is only a variable that holds a memory address no values are stored! Mike Shah (Tufts University) Comp 11 Lectures June 26, 2017 32 / 57
We might want to still pass by value, but not by reference. A pointer when passed as a parameter, is still copied, but it is only an address, thus cheap. (imagine if you have a struct that has 100s of member variables those all have to be copied!) Let me show you then we ll dive into pointers. Mike Shah (Tufts University) Comp 11 Lectures June 26, 2017 33 / 57
Nasty vector copy 1 #i n c l u d e <v e c t o r > 2 #i n c l u d e <i o s t r e a m > 3 // Doing one s i m p l e o p e r a t i o n r e q u i r e s a copy o f the e n t i r e v e c t o r. 4 v o i d p r i n t V e c t o r ( s t d : : v e c t o r <i n t > vectorcopy ) { 5 s t d : : cout << vectorcopy [ 0 ] << \n ; 6 } 7 8 i n t main ( ) { 9 s t d : : v e c t o r <i n t > veccounter ; 0 1 f o r ( i n t i =0; i < 200000000; i ++){ 2 veccounter. push back ( i ) ; 3 } 4 // Pass a copy o f our v e c t o r to the f u n c t i o n 5 p r i n t V e c t o r ( veccounter ) ; 6 r e t u r n 0 ; 7 } Listing 7: A vector with 200000000 items Mike Shah (Tufts University) Comp 11 Lectures June 26, 2017 34 / 57
Pointers A pointer is a type. There are integer pointers, floating pointers, double pointers, even pointers to your custom defined types (using structs) We often say, a pointer to int, which has the same meaning as above. We use the asterisk (*) to signfify that we want to point to a specific data type. Mike Shah (Tufts University) Comp 11 Lectures June 26, 2017 35 / 57
Pointer syntax 1 1 // A r e g u l a r i n t e g e r 2 i n t x ; 3 // A p o i n t e r to an i n t e g e r 4 i n t px ; 5 // Sometimes we p r e f i x our v a r i a b l e with a p or p to remember i t i s a p o i n t e r. Listing 8: Integer pointer Mike Shah (Tufts University) Comp 11 Lectures June 26, 2017 36 / 57
Pointer syntax 2 1 // A r e g u l a r f l o a t 2 f l o a t x ; 3 // A p o i n t e r to a f l o a t 4 f l o a t p x ; 5 // Sometimes we p r e f i x our v a r i a b l e with a p or p to remember i t i s a p o i n t e r. Listing 9: float pointer Mike Shah (Tufts University) Comp 11 Lectures June 26, 2017 37 / 57
Pointer syntax 3 1 // A s t r u c t we c r e a t e d 2 s t r u c t s t u d e n t { 3 s t d : : s t r i n g name ; 4 i n t age ; 5 } ; 6 // C r e a t e our s t r u c t o b j e c t 7 Student mike ; 8 // A p o i n t e r to our o b j e c t 9 Student p s t u d e n t ; Listing 10: struct pointer Mike Shah (Tufts University) Comp 11 Lectures June 26, 2017 38 / 57
Pointer syntax 4 So remember all a pointer does is point to an address. How do we get an address? Ampersand &! Okay, let us try it out. Mike Shah (Tufts University) Comp 11 Lectures June 26, 2017 39 / 57
Creating and assigning a pointer 1 #i n c l u d e <i o s t r e a m > 2 3 i n t main ( ) { 4 i n t x = 5 ; 5 // I n t e g e r p o i n t s t y p e s match i f i t p o i n t s to 6 // a p r i m i t i v e ( i n t ) t h a t i s an a d d r e s s 7 // We g e t the a d d r e s s with & 8 i n t i = &x ; 9 0 1 2 r e t u r n 0 ; 3 } Listing 11: Creating a pointer Mike Shah (Tufts University) Comp 11 Lectures June 26, 2017 40 / 57
Dereferencing a pointer Great, so we can point to an integer. But what if we want the value for which we point at? We dereference, i.e. Whatever I am referring to, don t give me the address (because remember & means reference), but instead give me the value hence dereference. We dereference by putting an asterisk(*) before our variable. Note that this is a different context, then when we created a pointer type (a pointer to an integer in the previous example). Okay, let s give it a try. Mike Shah (Tufts University) Comp 11 Lectures June 26, 2017 41 / 57
Dereferencing a pointer - Example 1 #i n c l u d e <i o s t r e a m > 2 3 i n t main ( ) { 4 i n t x = 5 ; 5 // I n t e g e r p o i n t s t y p e s match i f i t p o i n t s to 6 // a p r i m i t i v e ( i n t ) t h a t i s an a d d r e s s 7 // We g e t the a d d r e s s with & 8 i n t i = &x ; 9 // D e r e f e r e n c i n g i ( i ) g i v e s us the v a l u e ) 0 s t d : : cout << v a l u e t h a t i p o i n t s to i s : << i << \n ; 1 2 r e t u r n 0 ; 3 } Listing 12: Dereference a pointer Mike Shah (Tufts University) Comp 11 Lectures June 26, 2017 42 / 57
Question If the pointer i points to integer x, does that mean i can modify x s value? Mike Shah (Tufts University) Comp 11 Lectures June 26, 2017 43 / 57
Question Answered 1 #i n c l u d e <i o s t r e a m > 2 3 i n t main ( ) { 4 i n t x = 5 ; 5 i n t i = &x ; 6 s t d : : cout << v a l u e t h a t i p o i n t s to i s : << i << \n ; 7 // L e t s s e t i to something e l s e 8 // We a r e t a l k i n g about v a l u e s, so we de r e f e r e n c e 9 // ( i = 72 would t r y to s e t the memory a d d r e s s to 7 2! ) 0 i = 7 2 ; 1 s t d : : cout << what i s i now : << i << \n ; 2 s t d : : cout << what i s x now : << x << \n ; 3 4 r e t u r n 0 ; 5 } Listing 13: Dereference a pointer Mike Shah (Tufts University) Comp 11 Lectures June 26, 2017 44 / 57
Pointers and functions - parameters are pass by value 1 #i n c l u d e <i o s t r e a m > 2 3 // Pass by v a l u e ( Only p a s s by r e f e r e n c e with &) 4 v o i d settoone ( i n t p ) { 5 // p p o i n t s to something i n memory, so we can 6 // s t i l l modify i t s c o n t e n t s however! 7 p = 1 ; 8 } 9 0 i n t main ( ) { 1 i n t x = 500000; 2 i n t i = &x ; 3 settoone ( i ) ; 4 5 s t d : : cout << x i s : << x << \n ; 6 7 r e t u r n 0 ; 8 } Listing 14: Parameters Mike Shah (Tufts University) Comp 11 Lectures June 26, 2017 45 / 57
Still pass by value 1 #i n c l u d e <i o s t r e a m > 2 i n t g l o b a l = 1 0 ; // C r e a t e some g l o b a l we can p o i n t to. 3 4 v o i d cannotchange ( i n t p ) { 5 p = &g l o b a l ; 6 } 7 8 i n t main ( ) { 9 i n t x = 500000; 0 i n t i = &x ; 1 // Pass by v a l u e 2 cannotchange ( i ) ; 3 // So even i f we p o i n t to something new 4 // Remember, o n l y a copy o f a p o i n t e r i s p a s s e d i n. 5 s t d : : cout << i s h o u l d s t i l l be what x i s : << i << \n ; 6 7 r e t u r n 0 ; 8 } Listing 15: Still only passing a copy of the variable as a parameter Mike Shah (Tufts University) Comp 11 Lectures June 26, 2017 46 / 57
Whew, quite a bit First things first, pointers are fun and they give us power We can now modify variables in functions using either pointers or references. We want to start thinking of functions as having their own memory on the stack. We want to think about where memory is otherwise, and remember the concepts of scope. Speaking of memory there s yet another curveball with arrays. Mike Shah (Tufts University) Comp 11 Lectures June 26, 2017 47 / 57
Passing arrays into functions The first three functions are exactly the same! 1 i n t incrementone ( i n t a r r a y ) { 2 //... 3 } 4 5 i n t incrementtwo ( i n t a r r a y [ ] ) { 6 //... 7 } 8 9 i n t i n c r e m e n t T h r e e ( i n t a r r a y [ 5 ] ) { 0 //... 1 } 2 3 i n t i n c r e m e n t F o u r ( i n t &a r r a y ) { 4 //... 5 } Listing 16: Many variations Mike Shah (Tufts University) Comp 11 Lectures June 26, 2017 48 / 57
Passing arrays into functions - Part 2 The reason is because an array is really just a pointer to memory. That is, a pointer to the first element in our array. incrementone actually gives this away (the other two following examples decay to the same thing). However, we do not know how big the array is, so we will want to pass that as a parameter for our function. Mike Shah (Tufts University) Comp 11 Lectures June 26, 2017 49 / 57
wait, so you skipped incrementfour? This is passing an array(which is a pointer) by reference This is illegal. The C++ Standard forbids it, and if we really understand references, this sort of makes sense. An array syntax (arr[5]) actually is *(arr+5) Mike Shah (Tufts University) Comp 11 Lectures June 26, 2017 50 / 57
Pointer Arithmetic 1 #i n c l u d e <i o s t r e a m > 2 i n t main ( ) { 3 i n t a [ 1 0 ] ; 4 // B r a c k e t s a r e a c o n v e n i e n t s y n t a x f o r us 5 // to a v o i d doing p o i n t e r a r i t h e m e t i c. 6 // What t h i s s a y s i s, 7 // ( 1 ) A s s i g n the v a l u e 5 to the l e f t hand s i d e ( l h s ) 8 // ( 2 ) On the l h s, i n c r e m e n t 5 memory a d d r e s s e s from the s t a r t 9 // ( 3 ) And de r e f e r e n c e t h i s v a l u e and s e t i t to 5. 0 // ( 4 ) Now a [ 5 ] i s e q u a l to 5. 1 ( a+5) = 5 ; 2 3 s t d : : cout << a [ 5 ] << \n ; 4 r e t u r n 0 ; 5 } Listing 17: Incrementing through memory Mike Shah (Tufts University) Comp 11 Lectures June 26, 2017 51 / 57
NULL It is best practice when we create a pointer, to set it to NULL. At any point, we can also point our pointer to NULL, which essentially means it is pointing to nothing. We (you, me, and every C++ programmer) will run into a segfault error at some point. This means you dereferenced a pointer at an illegal memory location. Which really means, you do not have anything at that memory location, and you are trying to access something that does not exist! (e.g. Array out of bounds error). This is good behavior in a way, it gives us a place to start looking. Mike Shah (Tufts University) Comp 11 Lectures June 26, 2017 52 / 57
In-Class Activity http: //www.mshah.io/comp/11/activities/activity8/activity.pdf Mike Shah (Tufts University) Comp 11 Lectures June 26, 2017 53 / 57
Activity Discussion Mike Shah (Tufts University) Comp 11 Lectures June 26, 2017 54 / 57
Review of what we learned (At least) Two students Tell me each 1 thing you learned or found interesting in lecture. Mike Shah (Tufts University) Comp 11 Lectures June 26, 2017 55 / 57
5-10 minute break Mike Shah (Tufts University) Comp 11 Lectures June 26, 2017 56 / 57
To the lab! Lab: http://www.mshah.io/comp/11/labs/lab7/lab.pdf 1 1 You should have gotten an e-mail and hopefully setup an account at https://www.eecs.tufts.edu/~accounts prior to today. If not no worries, we ll take care of it during lab! Mike Shah (Tufts University) Comp 11 Lectures June 26, 2017 57 / 57