Pointers in C / C++ [Full Course]

Pointers in C / C++ [Full Course]
Spread the love

the course you are about to watch is  about pointers in c  the course was developed by the  excellent instructors from  my code school my code school is one of  the earliest software channels on  youtube  and has inspired many developers and  creators in the description i’ve  included a link to an article about the  channel’s amazing story  now let’s get to the course pointer  is a very fundamental and important  concept in programming  but a lot of beginner programmers find  it difficult to understand pointers  so in this lesson we will try to  demystify pointers  and all you need to know to understand  this lesson is  how to write a basic c program how to  declare a variable  and how to do simple arithmetic upon  those variables  okay so let’s get started to understand  pointers  we first should understand how  various data types or various variables  are stored in computers memory  okay so let us say this figure in the  right here  is computers memory and when we talk  about computers memory in context of  program execution we mostly talk about  the random access memory or the ram  we often say that my machine has got 2  gb of 2 gigabytes of ram  or 4 gigabyte of ram now let’s say these  segments  or partitions that we are showing here  in the memory is each  one byte of memory now in a typical  memory architecture in a typical  computer architecture of the memory  each byte of the memory has an  address so let’s say  the first byte in this memory which we  can assume to be  the lowest by deep down here has an  address zero and the address keeps on  increasing as we go towards the top  so we go on like zero one two and let’s  assume  this particular address is  two zero one so the next byte would have  an address of  two zero two and we will go on like two  zero three two zero four and so on  now when we declare a variable in our  program let’s say  for example if we declare a variable a  of type integer  then when this program executes the  computer allocates  some amount of memory corresponding to  this particular variable  how much memory it allocates depends  upon  the data type and also upon  the compiler so in a typical modern day  compiler an integer  is allocated 4 bytes of memory character  variable  is allocated one byte of memory  float is allocated four bytes of memory  and we can have  other variables as well okay so as soon  as the computer sees a declaration  like this during the program’s execution  it knows that this is an integer  variable so we i need to allocate  4 bytes of memory let’s say in our  example it allocates  memory starting address 204 to address  207  for a and the computer has an internal  structure  a lookup table where it stores this  information that there is a variable a  it is of type integer and it is located  at address 204  which is the starting address of the  variable now  if we declare another variable say for  example if we declare a variable named c  which is of type character now once  again when the machine sees this  declaration  it knows that it is a character variable  so it needs one byte of memory  so it looks for some free space let’s  say in this case  it allocates the address 209 the byte  209 for c and once again  it keeps an entry for it in an internal  structure  called lookup table that is c is a  character  and its address is 209. now when we  perform some operation  with these variables like let’s say if  we initialize a to 5  when our machine or computer sees such a  statement  it looks into the lookup table for this  variable a  so it finds this variable a that it is  an integer and  it is at address 204 so  it goes at address 204 and in these four  bytes  starting 204 it writes this value  5. now in reality the value is written  in binary but  for the sake of understanding we are  writing here in decimal form  now once again let’s say we have some  statements and then again after these  statements we  have another statement which increments  a now again  when computer sees that a has to be  incremented it again looks for this  address for a goes to the address and  modifies this  value at this particular address so this  block of memory allocated for a  stores the value 6 now now all of this  is really cool but  can we know the address of a variable  in our program or can we operate upon  these memory addresses in our program  well yes you can do so in a c or c plus  program using the concept of pointers  pointers are variables that store the  address of another variable  and to make you understand about this a  little better i’ll redraw a couple of  these things  let us say we have a block of four bytes  at address 204 that stores an integer  variable  a now we can have another variable  the type of which is pointer to integer  and let us say the name of this variable  is p  now this variable p can store the  address of  a and using the properties of  p or using some operators upon p  we can reach a now p also takes  some memory so let’s say it is stored  at location address 64 and it also takes  4 bytes of memory  we can also modify p to point to  another integer so let’s say if we have  another integer at address208  named b and having value 10 and if we  change the address in p  from 204 to 208 then p  now points to b let us now see  the syntax of pointer variables and see  a normal variable  is declared by writing the data type  and the variable name so int a means  that we have a variable a  of type int if we want to write a  pointer variable that should  point to another variable all we do is  we  put an asterisk sign before the variable  so p is now  a pointer variable that points to an  integer  so p is a variable that can store the  address of an integer  now to store the address of a  in p we need to use a statement like  p is equal to ampersand a  now if we put ampersand in front of a  variable  it gives us the address of that  particular variable in fact it returns a  pointer  to that particular variable okay so  let’s try to see a simulation of this  let’s say when we declared the variable  a then it was allocated an address 204  now we declare an a pointer to  integer p let’s say it was allocated at  a 64.  now when we write a statement like p is  equal to ampersand a  then p now has the address of a  and it kind of points to a  let’s initialize a to some value let’s  say a is equal  to 5 so we fill value 5 into a now  now what will happen if i print b what  will be the output  any guesses think about it  okay so if we try to print p then  the output will be 2 0 4 because p has a  value 2 0 4.  what if we simply try to print ampersand  of a  ampersand of a also gives us the address  of a so this will also be 204  what if we want to print ampersand of  p now p is also a variable and it is  also stored in the memory  so ampersand since it prints the it  gives you the address of that variable  so printing ampersand of p should give  us  64 which is the address of p now there  is one more important property of  pointer  if we put an asterisk sign in front of  the pointer  then it gives us the value at the  location that it points to  so what will happen if we try to print  star of p  as trick of p well it will give us  5 this concept is called as  dereferencing  because we have a reference or we have  stored the  an address in p and we kind of get the  value at this particular address using  this operator  in fact we can modify the value at this  particular location  by saying something like star p is now  eight star p means value at p  and so the value at p is now modified to  eight  so what will happen if you print star p  or print a now  the output will be eight  by value of p i mean value at address p  so p is the address and star p is the  value  at address that is stored in p okay to  just to reiterate uh we define a pointer  variable  using by putting an asterisk sign in  front of the variable name  and if we put an ampersand sign in front  of a variable name we get the address of  it  so if we try to print a pointer variable  without asterisk sign or operate upon it  without asterisk sign we are operating  with the address  while if we put an asterisk sign in  front of the pointer variable  and operate upon it then we are  operating the value at that address  so this was some of the basics of  pointers in the coming lessons we will  some  see some code snippets where we will see  some of the common errors that we make  while using pointers and we will also  learn pointer arithmetic  and pointers in the context of arrays so  thanks for watching  so in our previous lesson introduction  to pointers  we learned the basics of pointers in  this lesson we will see how to work with  pointers  in some real code examples but before  that  a quick recap pointers are variables  that store  address of other variables we declare a  normal  normal variable with a syntax like  the data type or the variable type  followed by  the variable name but we declare a  pointer variable  with a syntax data type and  an asterisk sign followed by the  variable name  we need an integer pointer variable to  store the address of an integer  to store the address of say a character  variable we will need  a character pointer so the same syntax  will be used we put an asterisk sign  and let’s say the name of the variable  is p0  so c is a character variable and p  naught is a  pointer to character and similarly we  can have a pointer  to double and we can also have pointers  to a user defined structure or a user  defined  class also and to get the address of a  variable  we write a statement like p is equal to  ampersand  a now this ampersand works as an  operator that gives us the address of a  and what happens in the memory is  something like this  variable p stores the address of  variable a  so in this figure here b’s value is 2 0  4 which is the address of a  so p points to a and using p  we can also get the value of a  so let’s say if a is 8 and we  use a star operator in front of p then  the star b gives us  8 which is value of a if we try to print  star b  it gives us 8. let us now try to see  some of these  in real code okay so time to see things  moving in a real c program  now what i’ll do is i’ll play a game  with you i will write some print  statements and you need to guess  what will be the output so what i’ll  first do is i’ll declare an  integer variable a and then i’ll declare  another variable which will be  pointer to integer and now i’ll write a  print statement  where i’ll be printing p now  what will be the output of this program  okay so let’s run this program  oops this gives us an error and if it is  too small for you to read  then this is giving an error that the  variable p  is not initialized and we are using it  without initializing so that’s why the  program is crashing  so now i will write a statement p is  equal to ampersand  a now ampersand of a is  nothing but address of a now let’s  run this again okay so this prints  an address and how do we know that this  is the address  or this is the right address that is  stored in p  so i’ll write another print statement  and now  i am printing star p now star operator  when it is  put in front of the address then it  gives us the value at that particular  address  okay so what will be the output of the  second print statement  so when we run this the the first line  gives us the address that p  points to and this address is different  than the previous address because  every time the program runs afresh  new addresses are located but the value  at p  is some garbage value is some integer  that i’m not sure what it is  this is happening because i have not  initialized a  and although memory is allocated for a  there is  some garbage value there that i do not  know about okay so let’s initialize a  let’s say  a is equal to 10 and now the second line  prints the value of a  and now i will write another print  statement  and this time i’ll print ampersand  a now what should be the output of  this third print statement and this  should be pretty easy to guess  ampersand operator gives us the address  and that’s why  the third line is also the address of a  in fact that’s what we have done here  when we have assigned p  the address of a we have used the  operator ampersand  now what i will do is i will modify the  value in  a using the pointer p and to do so i  will write a statement like  star p is equal to 12 and this is read  as  value at address p value at address  being pointed by p  is now 12. this concept is called d  referencing  so now if i try to print a  and let’s also put one print statement  for a  before we modify the value and let’s  run this so the first print gives me 10  which is the value that we had  initialized a with  and the second print gives us a  is equal to 12 because we modified the  value  using the pointer okay so one more thing  that i’ll do here now  i’ll have another variable b that will  have value 20  and now what i’ll say is star p  or value at address p is equal to b  and the question now is that will the  address in p  change now to point to b well  no unless you explicitly write a  statement like  p is equal to ampersand b this reverse  operation will not happen what we are  doing here is actually only  putting in the address of a the value  that b  has but we are not pointing to b and  this will get clear  only if we write some more printf  statements  so before writing the statement i’m  writing two print statements  one to print the address and one to  print the value  and after we write the statement i’ll  write two more print statements  trying to print the address and value  again so let us see what the output is  now  okay so address of p initially is three  one four four five seven six  and value is ten and after this  statement star p is equal to b  only the value is modified and the  pointer still points to a  so a kind of now becomes 20 but the  address does not change  now one more thing sometimes we declare  and initialize a variable in the same  statement  so instead of writing this a equal 10  here we could simply say  that int a is equal to 10  so we can do so for the pointer variable  as well we could simply say  for these two statements one simple  statement like in star  p is equal to ampersand a  and we will not need the statement this  one statement is same as saying the  earlier two statements  the syntax of declaring pointers some  people  write this asterisk sign after end and  do not write it  in front of the variable name this also  works and this is also fine  so you can write in star which is which  means pointer to integer and then you  can write the variable name  and this will also work okay so now we  will point  we will talk about a concept  we will talk about the concept of  pointer arithmetic  but before that i’ll write this rewrite  this  declaration and initialization like  before in two statements  i like it better this way it’s less  confusing now i will write two print  statements here  in the first statement i’ll print p and  in another statement  i will print p plus 1 now is it really  possible to do so  can we really increment and decrement a  pointer variable  well yes we can do so so now let’s  assume  that the address stored in p is  something like two zero zero two so any  guesses what p  plus one will be will it be two zero  zero three  well no p plus one will be two zero 2006  this is because if p is an integer  pointer incrementing it  by one unit takes us to the address of  the next integer  and because the size of an integer is 4  bytes  so to go to the next integer address we  need to skip four bytes so  b plus one increments p by  four bytes i’ll write another print  statement in which i’ll print  the size of an integer variable and i’ll  write something like size of  integer is and we have a function in  c size off that gives us the size of a  data type  so this statement this print statement  will give us the size of integer  and let’s write in the first and third  print statement something like  address p is blah and address p plus one  is blah so let’s now run this and see  what happens  okay so the output is address p is four  five eight six  zero five two which is some address and  then  we print size of integer is four bytes  so for this particular compiler  the size of an integer is four bytes and  address p plus one  is 4 bytes more than address p you can  try this thing out for  a character pointer or a double pointer  or a pointer of some other data type  okay so we could also increment this by  2 and  what happens if we increment this by 2  well it will  increment the address by 8 so  this will be like 2 0 1 0  p plus 2 will be 2 0 1 0 and this 2 0 0  2 and 2 0 1 0 is  something that i’ve picked up randomly  just for the sake of example  okay so now once again what if i want to  print the value at this particular  address  so i’m printing two more lines here now  i’m printing that value at address p  is and i’ll print star p which gives us  the value at that address  and we will print another line where  we’ll say that value at address p  plus 1 is and this should be star  p plus 1 we put the star operator in  front of the address  okay so now what will be the output okay  so the output is that  address p is some address and value at  address p is 10 which is all right  because we had stored the address of  variable  a in p now next line is size of integer  is 4 bytes and p plus 1 is 4  more than the address p and the value at  address p  plus 1 is some integer value that i do  not know about  in fact this is some garbage value  because because  we do not really have an integer  allocated to this particular memory  address  and this is one dangerous thing about c  using pointer arithmetic using pointer  manipulation you can reach  to any address and sometimes these kind  of operations can bring some unwanted  behavior to your program  i recommend trying these things out  these snippet of code with  other data types like character or float  and the result  results will be similar so this was  some playing around with pointers and  in the coming lessons we will talk more  about pointers and we will talk about  pointers in the context of  arrays so thanks for watching  so far in our previous lessons we have  seen how to work with pointer variables  so we pretty much understand the basics  in this lesson we will write some more  code using pointers  and we will look through some of these  concepts  in more detail using some examples the  first thing that i want to point out  is that pointer variables are strongly  typed  what it means is that you need a pointer  variable of a particular type to store  the address of a particular  type of variable so instar or a pointer  to integer will be needed to store the  address of an integer  character pointer will be needed to  store the address of a character  and similarly if we have a user defined  structure or  class then we need a pointer of that  particular type only  but why do we need these strong types  isn’t it that the pointer variables just  store the address of the variable so why  couldn’t we have just one type  that will be some generic type to store  the address  of all kind of variables and the answer  is that we do not use the pointer  variables only to store memory addresses  but we also use them  to de-reference these addresses so that  we can  access and modify the values in these  addresses  now as we know data types have different  sizes  like in a typical modern day compiler an  integer  it’s stored in four bytes a character  variable  is stored in one byte a float  is again stored in four bytes and these  variables differ not only  in their sizes they also differ in how  we store  information in whatever bytes are  available for these  variables or data types let’s say we  have an integer  a and its value is one zero two five and  this  is how it is laid out in the memory each  each bracket here is one byte so let’s  say this particular byte which is the  least significant byte  is byte 0 and then we go on like byte 1  byte 2 and byte 3 now we also know that  each byte in the memory is addressable  let’s say the address of byte 0  is 200 now these four bytes need to be  contiguous let’s say the address of byte  2 byte 1 is 2 0 1 and then we go on like  2 0 2 and 2 0  3 when an integer is represented in the  memory  is stored in the memory the leftmost bit  stores the information that whether this  integer is positive or negative so this  is also called  signed bit sign bit and rest 31 bits are  used to store the value  so if you see we have a 1 at right most  bit with place value 2 to the power 0  and at this particular bit with place  value  2 to the power 10 so the overall value  that we have in binary here  is 1 0 2 5 in decimal  now what if i declare a pointer to  integer  p and store the address of a in p by  using the ampersand operator  what will happen if i print the value of  p the value of p  or the address stored in p will be 2 0 0  the address of byte 0 so we are kind of  saying that  we have the address of an integer  variable starting at address 2 0 0.  if we dereference this address and try  to print asterisk p  we want to know the value at this  particular address then the machine sees  that okay p  is a pointer to integer so we need to  look at  4 bytes starting address 2 0 0  and then the machine knows that how to  extract  extract the value of an integer data  type  so it retrieve it retrieves the value  one zero two five  out of these four bytes now if p was  a character pointer then while d  referencing the machine would have  looked at only one byte because a  character variable  is only one byte if p was a pointer to  float  then although float is also stored in  four bytes but the way  information is written for float in  these four bytes is different  from the way information is written for  an integer data type  so the value printed would have been  something else let’s go write some of  this in a real program  and see what happens in my c program  i’ll first declare an integer a  equal to one zero two five and now i’ll  declare a pointer to integer  p and then i’ll store the address of  a in p by using the ampersand operator  now i’ll write a print statement  like this size of integer  is and we have a function size off and c  which gives us the size of a particular  data type in bytes  and now i’ll write a print statement  like this address is equal to  p and value is equal to  asterisk p with d reference p to print  the  value now let us see what is the output  of this program  no points for guessing this is pretty  straightforward the size of integer  is 4 bytes the address that we are  showing here is sum address  and the value is one zero two five  okay now i’ll do some trick here i’ll  declare a character pointer let’s say  the name of the variable is p0  now i’ll try to put the same address  as we have in p into p0 by writing a  statement like this  but this will give us a compilation  error because p0  is a pointer to character and p is a  pointer to integer  so what we will do here is we’ll type  cast  p to character pointer  and then assign the value and now i’ll  write two more print statements  first size of character is these many  bytes and we use the method size of  again  and the second is the address is p0 and  the value at address is  asterisk p0 so vd reference we try to  dereference p0 now  and let us see what’s the output now the  first line of output is size of integer  is 4 bytes  address because we are running the  program fresh  this address will not be the previous  address the address from the previous  run  this will be a different address by  dereferencing the integer pointer we are  getting the value one zero two five  now the next line of output is size of  character is one bytes  address is five three seven three zero  three two which is the same address  as we have in the second line but the  value this time  is 1 now why is this value 1  once again if we write 1 0 2 5 in binary  using 32 bits  then this will be the representation  when we do this  type casting here trying to store the  address of p  in p0 then the address of this  particular byte  the right most byte is stored in p0  but when we de-reference p0 because p0  is a pointer to character the machine  says that hey this is a pointer to a  character  and the character is only one byte so i  look at only one byte to see the value  and if you see this particular byte in  binary  is one and that’s why this output here  is one  okay i’ll write two more print  statements now  one to print the address p plus one and  the value at address p  plus one now as we know we can add or  subtract  an integer constant from a pointer  variable  this is allowed in fact the only pointer  arithmetic that is allowed is adding or  subtracting some constant integer value  to the pointer p plus 1 will take us to  the address of the next integer  so it will skip 4 bytes and take us 4  bytes ahead  let’s say we also want to print p 0 plus  1 and the value at p 0 plus 1  ok now let’s see the output of this  particular program  the address of a this time is 4 4 six  zero three six  that’s what is allocated for a in this  particular run  the value is one zero two five p plus  one is four four five six  zero four zero if you see this is four  bytes more than  the address of a because size of integer  is 4 bytes and p  is a pointer to integer so incrementing  b takes us 4 bytes forward  and this value is some garbage value  because we have not filled anything in  this particular address  so there is some garbage in the memory  which we are picking up  now the address in p 0 is also 4 4 5 6 0  3 6 which is the address of the  first byte the least significant byte of  a  the value is 1 now p zero plus one is  four four five six zero three seven here  we have  a value which is one byte more and this  is because character  is stored in one bytes now the value  here is four  if you see p zero plus one will take us  to this particular byte the address of  this particular byte  and this particular byte in binary is  4. this was to show you how things  happen in memory when we de-reference a  pointer variable by using the asterisk  operator  and also what happens when we perform  pointer arithmetic  with a particular pointer type this type  casting of pointer variable from one to  another  also has some use cases we will discuss  them later  now we will discuss one pointer type  which is generic pointer type  it does not correspond to a particular  data type and this pointer type is  called void pointer  and we declare this particular pointer  type by using the keyword  void and using an astrix sign in front  of the variable name  okay now we can write something like p0  is equal to p we do not need an explicit  type casting here  like this the statement p 0 is equal to  p  is valid and this will not give you  compilation error  and because this particular pointer type  is not mapped to a particular data type  we cannot de-reference this particular  pointer variable so if you try to print  star  p naught or asterisk p naught this will  give you  an error we are getting a compilation  error  we can only print the address and as we  can see here the address is same as the  address of  a and if we perform arithmetic  if we try to uh do something like p0  plus one access something like p0 plus  one  this is also not possible this will also  give you compilation error  we will come back to the use cases of  void pointers  in forthcoming lessons let’s for now  know that there is something called void  pointers  so this was diving deep into pointer  types  and pointer arithmetic we will have a  lot of fun with pointers in the coming  lessons  so thanks for watching in our lesson  so far we have seen how we can work with  pointers  in some of the basic scenarios but there  are some scenarios  where pointers can be really puzzling  and  one such scenario is when we want to use  pointers to pointers  so in this lesson we are going to see  how we can use  a pointer to pointer let us assume that  this  is a logical view of computers memory  and  each partition here is one byte of  memory now we know that  each byte of memory has an address we  have drawn the memory horizontally here  let us assume that the address increases  as we go from left to right  so if this byte is at address 200 the  next byte would be at address 201  and the next byte would be at address  202 and so on  now let’s say in my program i have  declared  an integer variable named x  and maybe i have initialized it  as and now when the program will run  some amount of memory will be  allocated for this variable x in a  typical architecture  in a typical compiler integer is stored  in  four bytes so four byte will be  allocated for x so  let’s say these 4 bytes at address 225  this block of 4 bytes starting address  225 is allocated for x  and the value stored in this block of 4  bytes for  x is 5. now the next thing that i want  to do is  i want to declare a pointer variable  that will store the address of x now to  store the address of an integer we will  have to declare a pointer to integer  something like this we need to put an  asterisk sign in front of the variable  name  now what will happen is that some amount  of memory will be reserved for this  variable  p in a typical architecture pointer is  also stored  in 4 bytes so let’s say we get this  block of 4 bytes at address 215  for p and now i want to write a  statement like this so i want to fill in  the address of  x in p and that’s how p  points to x ampersand operator gives us  the  address of a variable now one important  thing here  we are able to store the address of x in  p because  p is of type pointer to integer  if p was of type pointer to character  or pointer to some other variable this  statement  p equal ampersand x would not have been  valid  so if i have to write down the types of  these two variables  then x is an integer and p  is pointer to integer or i can also say  that that  p is in star or asterisk  and y pointer variables are strongly  typed  why do we need a pointer to integer to  reference  or store the address of an integer it is  because  we don’t just store the address of a  variable in a pointer variable  we also use the pointer variable to  dereference the address and write some  value there so if i write a statement  like this  this value here at address 225 and this  x is now modified now can i create a  pointer to this variable  p which itself is a pointer to integer  well yes we actually we can do so so  let’s say we want to  create a variable named q that will  store the address of  p now what will be the type of this  variable we need  a pointer of a particular type to store  the address of a particular type of  variable  so to store a pointer to integer we will  have to say  that that we want a pointer  to pointers so we will put two asterisk  sign in front of the variable name  and now this variable q can store the  address  of p so with this first line  with this end astro gastric queue we  created  q let’s say we created q at 2 0 5  and now we are seeing that q will store  the address of  p so q points to p  and the type of queue is int  asterisk asterisk with two we put two  asterisks  simple way to read this is that the type  of variable x is integer  so to store the address of x we will  need a pointer of type in  star so we will put one star to say that  this is a pointer to that particular  type and to store the address of  p we will need a pointer to instar so we  will put  one extra star to say that this is a  pointer to instar  and we can go on like this let’s say we  want to declare  a pointer to pointer to pointer so in  stochastic is pointer to pointer  and we will put one more asterisk we can  put these three asterisk immediately  after this keyword int  or we can put it immediately before the  variable name like we have done in the  case of  q here let’s say we define r as in  star star star so let’s say r gets this  address  230 in the memory now r is  of type int  asterisk asterisk asterisk so it can  store the address of  int asterisk asterisk so it cannot store  the address of  x or p only a statement something like r  is equal to ampersand q will be valid  now i have translated my previous rough  code into  a working c program now let us assume  that  this program is working as per this  memory sketch that we are showing in the  right  now i will write some print statements  and you need to guess the output  so basically you have to assume that  these variables  x p q and r are allocated  these addresses what we are showing here  in the right so  the first print statement that i’m going  to write is  i want to print asterisk p  and this one should be simple for you  asterisk p  would be value stored at address in p so  this will be six  now the next statement that i want to  print is asterisk queue  so asterisk q will be a value at address  stored in queue  address stored in variable q is 215 so  this is nothing but the value of p  so this will be 225 and now i want to  print astro gastric cues so i want to  do day referencing twice first i want to  go to asterisk queue  astray q is this address 225 and now i  want to look at the  value at address 225 so this one will be  6. we could have avoided writing this  parenthesis here we could have said  astrich asterisk q only and that would  have also  that would have meant the same but it’s  a good practice if we are  using this asterisk operator to use  parentheses wherever  we can do it because sometimes when we  are  also using other operators we are not  sure about the  precedence and we want to avoid unwanted  behaviors  now what about these two print  statements astro gastric r  and astro gastric asterisk r asterisk r  means  value in q which will be 215 and then  further  one more dereferencing will take us to  value in p which is 225 and one more  dereferencing will take us to value in  x which will be six if you see this is  really interesting  uh from r we are using one asterisk  operator and we are able to go to  q then we are using the asterisk  operator twice and we reach p  and then we are using the asterisk  operator thrice and we reach  x let’s make some more changes in this  code and  run this in a real compiler so what i’ll  do here is  i’ll write a statement like this  and then after this statement i’ll print  the value in x if you run this now as  you can see  asterisk p astro gastric q and asterisk  asteroid gastric  are all these three values are six  the address will not be same as we had  shown in the example  for obvious reasons and as you can see  we are able to modify  x by doing this chain of the referencing  using this variable  r uh if we would write something like  asterocastry  q is equal to  let’s say something like this  now asterisk p is also uh referencing x  and asterocastric q  is also dereferencing x sorry we are  de-referencing here  so any guesses what will be the output  of this last print statement  well if you see x is incremented by 2  here  so this was pointer to pointer i  recommend that you write some of this  code yourself  and play a little bit in the coming  lessons we will use pointer to pointer  in some real problem scenarios so thanks  for watching  in our previous lessons we defined  pointer variables  and we also saw how to operate upon  pointer variables how to work with  pointer variables  in c or c plus program but we did not  really talk about  the real use cases of pointer variables  in what scenarios we may want to  use pointer variables so in this lesson  we will talk about  one of the use cases of pointer  variables and  the use cases using them using pointers  as function arguments and we also term  this as  call by reference so  let’s discuss a scenario albert is a  beginner programmer  and he has recently learned about the  concept  user defined functions now he tries to  apply this concept  and he writes a simple c program like  this  what he is trying to achieve here is  that he has  an integer variable declared and  initialized in the main method  and he wants to increment the value in  this variable by one  so instead of writing something like a  plus plus or a  equal to a plus one instead of writing a  statement like this  he writes a function increment that will  take  an integer a as argument and inside this  function he’s writing a statement like  a is equal to a plus 1 he calls this  function  increment from the main method passing a  as argument  and then he prints the value of a now  what he is expecting here  is that the value of a will be  incremented to 11  and hence the print statement will print  a  equal 11 but when he runs the program  the output of the print statement is  a equal 10. now albert does not  understand why this is happening  he has declared a variable a and then  he has initialized this variable to 10  and then he is passing the same a to the  function increment  and the same a is been being incremented  by 1  in this function so why the value of a  being  printed is not 11 why is it 10  now what albert does not understand well  or what he probably  forgot is that whenever we declare a  variable  inside a function then we call that  variable a local variable  because as such just using the variable  name  we can access that variable only inside  the same function in which we have  declared the variable  so these two a this a in the function  increment and this a in the function  main  are actually not the same a the a in the  function increment is another a  when main calls the method increment and  passes this  a as argument to the function then  only the value of a is copied to this  another a which is  another variable local to the increment  function  so what i’ll do is i’ll do couple of  modifications in this code to show you a  better picture  i will write two print statements in  this code  first print statement in the increment  method something like this  address of variable a in increment  is and as we know if we put ampersand  operator in front of the variable name  then we get the address  of that variable and i’ll comment out  this print and  i’ll write one more print in the main  method like this  and here i print that address of  variable a in main is ampersand a  let us now run this and see what happens  let me also put  an end of line after we print the  statement and the output is address of  variable a in  increment method is printed as four four  five  four four six zero and in main it is  equal to four four five four six six  zero  this two looks similar but they’re not  the same one  is having four four six zero and then  and another is having four six six zero  what the values are is not important  what the addresses are is not important  what’s  important is that these addresses are  different  if the a in main method and the a in  increment method  were same these two addresses would have  been  same to understand this even better  we will try to understand how things  happen in computers memory when a  program  executes when a program or an  application is  started then the computer sets aside the  machine  sets aside or reserves some amount of  memory  for the execution of this program the  memory that is set aside for the  application is divided into is typically  divided into  these four parts that we are showing  here  one part of memory is allocated to store  the various instructions in the program  the computer needs to keep all these  instructions in the memory  these instructions that we have in the  program like increment or declare these  variables  all these sequential instructions one  part of the memory  is one part of the allocated memory is  for  static or global variables if we do not  declare a variable  inside a function in c plus or c  then it is a global variable now global  variables  can be accessed and modified anywhere in  the program  unlike local variables which can be  accessed and modified within a  particular function or within a  particular code block  now the third part of the application’s  memory is called as  stack and this is really important  this is where all the local variables go  and we will mostly be talking about  stack in this lesson and the fourth  fourth part is heap and we will come to  this later in  in our forthcoming lessons  of these four segments of the allocated  memory  uh the text segment the global variable  segment and the stack segment  these three are fixed and they are  decided when the program  starts executing the application however  can keep asking for  more memory for hits its heap segment  during its execution only  we will cover all of these things in  detail in our forthcoming lessons  please do not get scared by these terms  let us now see what happens when a  program  executes let us say this is our  computer’s overall memory  the ram and as we know each byte in the  memory is addressable  so let’s say uh the memory allocated for  our program is from address 2 0 0  to 8 0 0 and these are the various  segments  of our applications memory and of this  let’s say  address 300 to 600 is allocated  for stack now there is more memory of  course in the ram  after address 800 and before address 200  okay so from 200 to 800 this part of the  memory is assigned for our program  let’s say this c program that we have in  the left  now when a function is invoked like when  the  program starts the main method is  initially invoked  all the information about the method all  the information about the method call  like its parameters all the local  variables  the calling function to which it should  return  the current instruction at which it is  executing all this information  it’s stored in the stack so we will take  out from  the stack some part for the main method  and  create a unit which we call stack frame  each function will have a stack frame  now we have a variable  a now memory is allocated for a from  this stack frame and the value  of a is 10. now the main method calls  increment function what happens when  main method calls  increment is that the machine says that  hey i will stop your execution for some  time  i will stop at this particular  instruction let me go ahead  and finish this method increment  and then i’ll come back to the main  method once i’m done with increment  now another stack frame is allocated for  the increment method  and the parameters in increment method  like we have a parameter a  so fresh local variables are created  corresponding to these parameters  and whatever values have been passed are  copied to these variables these  parameters  now when we say a is equal to a plus 1  here in this statement then what happens  that  this a which is local to the increment  function in this particular stack frame  this a is incremented we cannot access a  variable it  outside its stack frame and now  increment finishes  when increment finishes the control  returns to the main method  and what the machine does is it clears  the stack frame that was allocated for  increment  and main method resumes again so main  method was paused at this particular  instruction increment  so lifetime of a local variable is  till the time the function is executing  now the next statement in main method is  a call to the function printf  printf is not a user defined function it  is a library function  the state of execution of main method is  kind of paused and printf is executing  now  we often call this particular structure  call stack or function call stack  whatever function is at the top of the  stack  is executing and remember this stack is  fixed in size so if you have a scenario  where one function  keeps calling another function in it  definitely like  in the case of in definite recursion  then the memory of this stack will  overflow and our program will crash  okay but that is not relevant for this  scenario  so now you must be getting a picture of  what happens when one function calls  another function  this a is in the stack frame of the main  method  main is our calling function and  increment is our called function  when we call a function in the calling  function the argument is also known as  actual argument and in the call function  the argument is known as  formal argument all that happens is the  actual argument is actually  mapped to a formal argument so when this  function call happens  a is mapped to a as an actual argument  is mapped to another a which is a formal  argument instead of a if we were having  an  x here so we would have written  something like in  x as is the argument and x is x plus 1  then  a would have been mapped to x so the  value of a will be copied to the  variable x  now when we make such a function call  where  we basically have one variable being  mapped to another variable that  value in one variable copied to another  variable then such a function call is  also called as  call by value so this is what albert was  doing  making a call by value and that’s why he  was not able to get the desired result  but can we get the result that albert  wanted to have  all but wanted to use this variable a  which is  local to the main method inside the  increment function  can we really do so well yes we can do  so  if we use pointers as function arguments  let us now look at this code and i am  drawing only the stack here so that i am  able to show the simulation  of program execution neatly now what we  are doing here is that  we do not have an argument which is  integer  in this function increment we have an  argument which is pointer to integer  and pointer to integer as we know we  will it will store the address of an  integer  so now what we are doing is that in the  increment function we are passing the  address of  a so when the program will start  executing the main method will be  invoked first  let’s say this is the stack frame of the  main method  let’s say 300 to 350 this address is the  stack frame of main method  and there would be a local variable  a in this main method let’s say the  address at which a  is stored is 308  this may not be in proportion but still  let’s say this is how it is stored  now when main method calls increment  then a local variable corresponding to  the parameter  p is created and this is a pointer to  integer and the value that is passed to  this particular function  the value that gets stored in this  particular sorry it’s not a function  it’s a variable the value that gets  copied or stored in this particular  variable would be  308 the address of a  so p is pointing to a now in this  statement here when we say  asterisk b we dereference this address  so  we are saying here that asterisk p is  value at address stored in p so we say  that  increment the value stored at address p  by one  the value is stored at address three  zero eight gets incremented by  one so a is now 11.  so now when increment finishes and we  come back to the main method  and the next line gets executed which is  the print statement  then a is now 11. if you run this  program then what gets printed is  a equal 11. such a function call in  which instead of passing the value of a  variable we pass the  address of the variable so that we have  a reference to the variable  and we can de-reference it and perform  some operations is called  call by reference so if we use  pointers as functions arguments then we  are using call by reference  call by reference can save us a lot of  memory because instead of creating a  copy of  a large and complex data type if we just  use a reference to it  and using a reference will also cost us  some memory but very small amount of  memory  then we are saved from creating a new  copy of a complex data type  in the coming lessons we will see more  of the layout of applications memory  and what all things we can do using  pointers  so thanks for watching the concept of  pointers  and arrays in c or c plus plus  go together there is a very strong  relationship between these two concepts  and in this lesson we will be discussing  this relationship  when we declare an array let’s say we  declare  and integer array a of size five  then we create five integer variables  named  a0 a1 a2  a3 and a4 now these five integers will  be  stored in the memory as a block of five  consecutive integers something like  this what we are showing here in the  right if a0 or the first element in the  array  is stored at address let’s say address  200 and  a typical compiler modern day compiler  integer is stored in four bytes  so a one will be four bytes ahead of a0  at two zero four and a two will be at  two zero eight a three will be at two  one  two a four will be at 216. the overall  size of the array would be  20 bytes and these 20 bytes will be one  consecutive  block we are only showing the section of  the memory in which a  is stored sometimes we also show the  memory  horizontally something like this from  left to right  we increase the address but these two  representations are just  for the sake of understanding let’s use  the horizontal representation of the  memory  this time i’ll show this memory a little  more extending towards  the right so that i can accommodate a  couple of more variables  let’s say apart from this integer array  a i have  an integer variable x and its value is 5  and let’s say x is located at address  300 now let’s say i have a pointer to  integer  p and in p i store the address of  x if we print p  then the value in p would be 300 so this  statement will  print 300 and if we de-reference  p and try to print the address stored in  try to print the value stored in this  location  p then the value would be 5.  this is fine but we also know that we  can do an operation something like  increment or decrement a pointer  variable by a constant  so we can do something like p equal p  plus 1  and this will take us to the address of  the next integer  and because integer is 4 bytes so now p  would be 3 0 304  so if i want to print p now then the  output should be 304 but  if we try to dereference p now and try  to print asterisk p  then we do not know the value at this  address so we cannot say what will be  printed  it’s like we know that mr x lives at  address 300 but we do not know  who is his neighbor who lives at address  304  but for this integer array a let us say  i’m writing the same integer array in  the right here  which is located at address 200 if i  declare a pointer to integer p  and store the address of the first  element  by putting an ampersand operator in  front of a0  then printing p would give us in this  scenario  the output 200 and printing  asterisk p would give us but before that  let’s  say we have these values in the array  let’s fill up some values in the array  so asterisk p would be  2 now if i want to print  p plus 1 then the address would be  2 0 4 and if i d reference p plus 1  and try to print this value then it will  be 4  and similarly if we wanted the third  element in the array we could do  a p plus 2 here so using pointer  arithmetic makes sense in the case of  pointers because  in the case of arrays because we know  what is in the adjacent location  there is one more property of the array  if we just  use the name of the array a then a gives  us the pointer to the first element in  the array so we can write a statement  like  p is equal to a in fact we do not even  need to take this  address in another pointer variable if  we simply print  a then this gives us nothing but the  address of the first element in the  array  and if we want to dereference this and  try to print asterisk a  then this will give us the value so  if we want to perform something like we  want to print a plus 1  then this will give us the address to 0  4  and as to k plus 1 will give us the  address of the second element in the  array  value of the second element in the array  for an  element in the array at  index i we can retrieve the address of  this particular element in the memory  using either ampersand a i  or simply a plus  i and these two will give us the address  of a i and the value of a i can be  retrieved using either we simply use a i  or we can also use asterisks a plus i  and astrix a plus i will also give us  the value now this is an important  concept  we can write ampersand a i or a plus i  for each other and they mean the same  and we can write  a i or asterix a plus i for each other  and they mean the same  the address of the first element in the  array  can also be called the base address and  a  simply using the variable name a gives  us the base address  of the array let us now see some code  examples  and try to solidify our concepts further  in my program let’s say we have an  integer array a now as we said if we  simply print  a then this should give us the address  of the first element in the array  and we can also get the address of the  first element in the array by  using ampersand operator in front of a0  if i simply print a0 it will print the  first element in the array  and we can also print the first element  in the array  by using asterisk operator in front of  the variable name a let us now run this  and see what happens  and i also need to put an end line after  each of these print statements  okay so the output is that the first two  lines are the same  they’re giving us the address of the  first element in the array  and the second two lines are giving us  the value in fact if we run a loop like  this from 0 to index 4  then we can print address of the element  at index i as ampersand a i or a plus i  and we can print the value of ith  element as a  i and asterix a plus i  now if we see the output here this is a  fresh run a new run so  the address allocations will change but  if we see the address printed in  two lines for a0 is same the value is  same again for a1 the address is same  four bytes ahead of the previous address  and the value is as expected  and we can go on like this  now one more thing even though just  using the variable name  a returns us pointer to the  base address or the address of the first  element  and we can equate the variable name  a against some pointer variable like  this we cannot do something like a plus  plus  increment the value of a this will give  us compilation error  we can do something like p plus plus  once we assign  a to some point or variable other  pointer variable but  incrementing a itself would be invalid  so this was how arrays are stored in  memory  and how the addresses can be manipulated  and how we can access the values using  pointers in the next lessons in the  coming lessons we will talk about  character arrays and we will talk about  passing arrays  as function arguments so thanks for  watching  in this lesson we will be talking about  one more scenario in which  the concept of arrays and pointers  go together and this scenario is when  you pass  an array as function argument  let us see a code example where we pass  array as function argument and try to  analyze it  i will write a simple c program in which  i will write  a function that will give me the sum of  all the elements in an integer array  this function will take an integer array  as argument  this is one of the ways to pass an  integer array an array in general as  argument  this would be the data type and this  would be the name of the  array and in the main method we have  declared and initialized an array named  a  now in the main method we will call this  function sum of elements  and pass it the array a as argument  and of course we need to write the body  of this function  sum of elements i will declare two  variables  i and another variable sum and  initialize it to zero  i will be used to run a loop so we will  iterate through  all the elements in the array a that is  passed as argument  but wait a minute we do not know the  size of this array a  is there some way to know the size of  the array one of the  ways to find out the size of the array  and by the size of the array we mean the  number of elements in the array here  is to use the function size off so  if we write something like size of a  here in the main method  then this will give us the size of the  array a in bytes  array has five integers and in a typical  compiler  and i know for sure that in this  compiler an integer is stored in four  bytes so  size of a will return 20. if we want to  know the  number of elements in the array then we  can do something like  divide the size of the size and bytes  of the whole array by size of one  integer  so we will say size of a upon size of  each integer in y the size of a0 would  give us the  number of elements in the array and i’ll  write this particular line  below this line the line where we are  calling the function sum of elements  now what we can do is we could either  pass the size of the array as another  argument  so that would be cool and then we can  run the loop  starting 0 till index size  -1 and we keep on adding each element  to this variable sum and finally  we return sum and finally we will write  a  print statement something like this  to print the sum of all the elements in  the array let us now run this program  and  see what happens the output on console  is that  the sum of elements is equal to 15  5 plus 4 plus 3 plus 2 plus 1 is 15. so  this is all right  now what i want to do is i want to  modify this code a little  i do not want to pass the size as  argument here  i want to calculate the size of the  array inside this function  so we will not be passing this size as  argument here so there will be  there will be just one argument the  array  so we have this array as argument the  array a  and we calculate the size here as total  size of the array in bytes  upon the size of one integer in bytes  let us now run this program and see what  happens  oops this seems to be some problem  because the sum of elements  that we have as output on console here  is equal to 1 it should be 15  and why is it so to explain this  behavior i will write  two more print statements one in the  function  sum of elements where i will print the  size of  a and the size of a0  i will be calling these two functions  size off upon  a and upon a 0 respectively and we will  write one more print statements in the  main method  it will again be the same thing printing  the size of a in bytes and the size of a  0 in bytes let us now see the output  in the method sum of elements size of a  is equal to 4 bytes  size of a0 is equal to 4 bytes in the  method main size of a is equal to 20  bytes and the size of  a 0 again is 4 bytes to understand this  concept  why the size of a is 4 bytes in the  method sum of elements and it  is equal to 20 bytes in the main method  we need to dive deep into how compiler  interprets  an array as function argument once again  i will draw this  familiar memory diagram the memory  assigned to an application or a program  is typically divided into these four  parts we have talked about this in our  previous lessons  for the execution of function calls we  use  stack section of the memory this green  rectangle here is  our stack now when the program starts  executing first the main method is  invoked  so some amount of memory from the stack  is allocated  corresponding to the call of the main  method  and this particular section or this  particular part  is also called the stack frame of a  method  all the local variables reside within  this stack frame  now here in main method we have  two local variables one is the array a  and another local variable is integer  total  so around 20 bytes if integer is  4 bytes exactly 20 bytes in fact would  be allocated  from this stack frame for the local  variable a the array a  and four bytes for total the variable  total  and there would be some more information  in the stack frame now when the program  execution reaches this particular line  where we make a call to sum of elements  then the execution of  main is paused and another  stack frame is allocated to execute the  function  sum of elements we have talked about  this  call stack growth and function execution  a number of times in our previous  lessons okay now this  is a local variable this parameter is a  local variable to  the function sum of elements it is not  this a in the  main method what happens when we make a  function call is that  the value of this particular local  variable in the main method  or we should rather say the value from  the variable in the calling function is  copied to the variable in the called  function  so ideally we should have one more a  local to the function called sum of  elements  and the value of a should be copied into  this parameter a  so we would have another array named a  taking 20 bytes in the stack frame of  sum of elements  and it would have the same value same  elements  as the array a in the calling function  main but actually this doesn’t happen  when compiler sees an array as  function argument it does not copy the  whole array  what it actually does it it just  creates a pointer variable by the same  name instead of creating the whole  array it just creates a pointer  to the data type of the array so in this  case it will be pointed to integer  and the compiler just copies the address  of the first element in the array of the  calling function so let’s say uh the  starting address address of the first  element  in this array a that belongs to the main  method is 200 so  in sum of elements all that happens is a  pointer to integer is created and the  value  in this pointer to integer is 200. the  compiler  implicitly converts this int  a to something like in star a  that is this a here in this particular  format is not interpreted as an  array but it is interpreted as pointer  to integer  so whether you write int space variable  name following  these brackets or you write something  like in star space a  they’re both the same we have a term for  this  instead of copying the value of the  variable we are just  copying and storing the address of the  variable  so we make a call by reference here  arrays  always are passed as a reference  parameters  and this makes a lot of sense because  arrays can be  really large in size so it does not make  much sense to create a new copy of the  array each time  it is unnecessarily using a lot of  memory  so for arrays there is no call by value  there is always a call by  reference and that’s why this size of a  here  would give us 4 as output because a  is a pointer to integer here well here  in the main method a is an  array so this format of  passing array as function argument where  we put these  braces to tell that this is an array is  actually interpreted  something like this by the compiler  you can put an asterisk sign here or you  can put an asterisk sign here it’s the  same thing  it makes more sense to write it like  this so a is actually interpreted as  pointer to integer that’s why when we  pass  array as function argument there is no  way to know the  number of elements in the array by using  a trick like this  we actually need to pass the size of the  array  so i’d rather move this  size calculation in the main method and  pass the size  and when we run this program now  we get the output as expected sum of  elements is  15. now we should always keep in mind  that  a variable name which is used as an  array  is different from a variable which is  pointed to integer  even though the compiler gives us some  privileges like we can use  the name of the array to get the pointer  to the first element  like in this function sum of elements we  could say something like  to pass the first element we should we  could have said ampersand a0 the address  of the first element  but if we just use a instead of using  ampersand a0  then that is allowed if a is an array  but if a is an array we cannot do  something like  incrementing or decrementing it like  pointer variables  with pointer variables we can do a  couple of other stuffs  and if we have a pointer to the starting  address of the array  we can pretty much use it like a  variable name for  array because a i is interpreted as  value at address a plus i so we need to  keep these differences and similarities  in mind it’s a little tricky  there is one more thing because the  array is passed by  reference we can modify the elements of  the array in the  called function and it would re reflect  in the calling function  so let’s say instead of  calculating the sum total we want to  double all the elements  each individual element in the array so  our code will go something like this  i want to say that a i is now twice a i  and we will not return an integer let’s  say the return type is  void and in the main method i’ll clear  all this stuff  and what i’ll do is i’ll simply run a  loop  to print all the elements in the array  okay let us now run this and see what  happens  oops i forgot to call the function  double  i must make a call before i print the  elements okay let us now run this  if you see the elements in the array a  are modified each element is  twice its previous value because this is  called by reference the same  copy of the array a  is modified using d referencing  so this was array as function arguments  an important use case of array as  function argument  is when we work with strings in c  so strings in c are nothing but  character arrays  this concept really becomes important in  the context of  character arrays we will be talking  about it in the coming lessons  so thanks for watching in our lesson so  far we have seen  how the concepts of arrays and pointers  go together  now in this lesson we are going to talk  about character arrays  how we can work with character arrays  using pointers  now when we talk about character arrays  in c we  basically want to talk about strings  strings are group or set of characters  and real world data like names  phrases and sentences all of these are  strings to us so these are some of the  examples of strings  character arrays become all the more  important because  we use them to store strings and then  perform  a lot of operations on strings like  modifying a string  copying a string concatenating two  strings or  finding out properties of strings like  finding out the length of a string  to be able to work with strings  efficiently in c  and there are a couple of things that we  need to understand and the first thing  that we  need to understand is how we store  strings in character arrays  to be able to store a string in a  character array the first requirement is  that  the character array should be large  enough to accommodate the string  and what is a large enough character  array a large enough character array is  a character array  of size greater than or equal to  number of characters in the string  plus one so let’s say if our string is  a name of four characters like john  then the size of the array should be  greater than or equal to  5. now the obvious question would be why  do we need space for one extra character  isn’t it that if we declare a character  array of size  4 we can store all the characters in  john j will go at the 0th index  o will go at the 1 index h and  n will go at second and third index  respectively  so i’m storing all the data isn’t it  let’s try to understand it this way  let’s say we have a character array of  size 8  let’s say this is a logical view of our  array c  and we want to store the string john in  this particular array  we have indices from 0 to 7 and this is  an array of size 8.  so we can store j at the zeroth index o  at the 1th index  h at the 2th index and n at the 3th  index  so we have stored all the characters of  the string john in this  array but if you see we have not stored  one information  now we have not stored the information  that this particular character  n is the last character in the string so  the string ends  at index three so let’s say if we pass  this string to a function  and that has to print the string john or  find out the length of the string that  we have stored in this array  then how would the function know that  the string is only till index 3 even  though  we have not filled anything in these  indices at  4 5 6 and 7 there would be some garbage  value there  so either we pass this extra information  or we do something else  to store this information that this is  the end of the string in the character  array  this is the used part of the string and  this is the unused part  we use a simple design at the end of the  string in the next position we put  a null character and null character has  a sky value 0  and we can put a null character at  position 4 in this example something  like this  within single quotes we put a forward  slash and  number 0 this is null character all the  functions for  string manipulation in c expect that  strings will be null terminated  so this is a rule a string in c has to  be terminated by  a null character and that’s why we need  one extra space  to store this null character let us try  to see some running code that will help  us  understand this concept better what i  have done here is i have  taken a character array of size 4 and i  have filled in the characters but i have  not used any space  to null terminate it and then i am using  the printf function this percentile s  here tells that  i want to print a string and then i am  passing this  array c uh let us run this program and  see what happens  as we can see there are these bunch of  characters  that are getting printed after john and  this is happening because  we have broken the assumption for the  printf function that  my string that our string will be null  terminated  so that’s why this undefined behavior is  coming if we change the size of the  character array to five and put  a null termination something like this  at fourth index  and then things will be fine now even if  we change the size of the array to 20  print a function will print till it  finds  a null character so it only prints on  the first four characters in the array  and it’s not just the print function  there are bunch of  functions we have this library string  dot h  that gives us a bunch of function for  string manipulation  so all these functions assume that the  string will be null terminated  so this is one contract that we have to  follow  let’s say we want to use one function  strlen  string length to find out this length of  the string  i’ll print something like this let’s run  this and see  as you can see the output is length is  equal to 4 even though  the array is of size 20. so string  length function also counts till  it sees a null character in  our program instead of writing these  characters individually at this  positions  we could have used string literals  string literals are  a group of characters within double  quotation marks so we could have written  something like this  and this would have initialized c as  this string and the null termination for  a string literal is implicit it is  always  stored with a null termination in memory  remember when we declare and initialize  a character array like  this this has to happen in one line we  cannot do something like we declare  in one line and then we go on and modify  this in the next line this will be  invalid  uh we could also avoid writing this size  here  and this would have been fine in this  case the size of c  will be five units five bytes where one  byte stores one character  so it would be just enough to store the  string  john so if we try to print the size and  bytes of c  using this size of function then size  and bytes is five  one character is stored in one byte so  space has been allocated for five  characters  but the length is four because the null  character does not count in the length  if we write something like c4 is equal  to  this particular string literal with four  characters this will give us compilation  error because the compiler  will force this particular array to be  of minimum size 5. there is one more  syntax of initialization  we can put all these characters as a  comma separated list  within these braces but in this case the  null termination will not be implicit we  will have to do it explicitly  and the size of the array has to be  greater than or equal to the number of  characters here so it should be greater  than or equal to five  okay so these are some of the ways to  initialize character array  the next thing that we need to  understand is  arrays and pointers are different types  that are used in similar manner  now what does it really mean let’s say  we declare a character array c1 of size  6  and initialize it with this string  literal and let’s say this is how it  gets stored in the memory  array is stored in one contiguous block  of memory so let’s say the first  character is at address 200 one  character is of size one byte so the  next character will be at address 2 0  1 and the next will be at 2 0 2 and so  on  now c 1 is the variable name for this  whole  array now what i’ll do is i’ll declare a  variable which is a pointer to character  let’s name this c2 so let’s say we get  this variable c2 somewhere in the memory  a pointer variable in a typical  architecture is stored in 4 bytes  so this variable will also have some  address let’s say this variable is at  address 400  i’m just picking up these numbers for  example sake now what we can do is we  can write a statement like this  c2 is equal to c1 now even though c1  is a character array is a variable name  for character array  and c2 is a variable which is pointer to  character this particular expression is  valid  just using the name of the array  actually  returns the address of the first element  in the array so  what this expression what this statement  will do is  it will fill in the address 200 in c2 so  c2 now points  to the first element in the array  now we can use this variable c2 which is  a character pointer  just like c1 to read and write  into the array so if i write something  like  print c to i let’s say we want to print  c 2  1 then the output will be l  and we can even modify the array let’s  say we want to modify the character at  zeroth index to  a so the string will be modified  and will become this now when we write  c2i  for any position i it is nothing but  asterisk c2 plus i  so c2 is the base address c2 plus i  will take you to the address of the ith  element  so in this case let’s say c2 plus 2 will  be 202  and if we put this asterisk operator we  are basically  dereferencing and finding out the value  so these two syntaxes are  alternate syntaxes and even if it is  an array name we can write these two as  substitutes for each other  so this was all the similarity in how we  actually  use them use arrays and pointers  to read and write let us now look at the  differences  we cannot modify an array with a  statement like this  c2 equals c1 is valid but c1 equals c2  is not valid uh it does not make sense  this will give you compilation error we  cannot even say c1 is equal to  c1 plus 1 we cannot increment or  decrement  this variable c1 now we can do it for c2  which is a pointer variable we can say  c2 plus plus so c2  now points to the next element with this  statement here  all that will happen is c2 will become  201 so  instead of pointing here it’s now  pointing to this particular element e  to traverse an array we run a loop and  we use a local variable let’s say i  and increment it in the loop if we have  a pointer variable we can just keep on  incrementing the pointer  and we can traverse the list we can  reverse the array  we will keep doing this c2 plus plus so  we must understand where we have an  array and where we have a pointer and  what we can do with  which one now the next thing that we  need to understand  is that arrays are always passed to  functions by reference  when we pass arrays to functions we only  pass the base address  of the array in a pointer variable and  we do not pass  a whole copy of the array the compiler  does not let you do  do that we have talked about this in  detail in our previous lesson  arrays as function arguments let us look  through some code and try to understand  this better  in my code i have declared a character  array of size 20  and i have stored a string of length 5  in this character array  the null termination is implicit if we  are using string literal  now i want to print this string but i do  not want to use the library function  printf i want to write my own function  print i want to pass this  array to the function and this function  should print the string part in a  character array  the argument to the function we have  talked about this earlier can be  something like this to say that we are  receiving an array here  but the compiler actually interprets  this  as this so the compiler forces that only  the address  of the character array or the address of  any array  be received as argument to the function  because arrays are large in size so it  is inefficient to create a  copy of the same array for each function  okay so let’s write the logic now now  this print function does not have any  idea that this particular array  is of size 20 it only knows the base  address  so what we can do is we can have a  variable i initialize it to 0 and we can  say something like this  while ci is not equal to  null character we can print the  character ci  and then we will increment i and when we  find  a null character we can come out of this  loop and print  an end of line once again this print  function does not know that this  character array is of size 20 it only  knows the base address  and that’s why in the printf function  when we were not null terminating an  array we were printing all the garbage  value  even after the array was finished  because until we get a null character we  do not know  where to stop and we keep on going into  unwanted memory locations  now this code should work yes this is  fine  in my code here i’m using percentile c  here to say that we want to print  character  and ci we can also write asterisk c plus  i  as substitute for c i and that will also  mean the same  sometimes you’ll see this kind of syntax  as we talked earlier both of these  syntax asterisk c plus i and ci  are valid they are the same there is one  more thing in our code that we may do we  may not  choose to have this particular variable  i we could simply say that  while asterisk c is not equal to null  print asterisk c and then increment  c itself and this code will also work  why this code will work i’ll leave it as  an exercise for you to think  in the coming lessons we will implement  more functions for string manipulation  this is it for now thanks for watching  in part one of our lesson  on character arrays and pointers we saw  how we can store strings in character  arrays  and we also saw how we can work with  character arrays using pointers in some  of the basic scenarios  whenever we are working with pointers  it’s really important that we  visualize how things are happening in  the memory  so the first thing that we will do in  this lesson is we will simulate the  program that we had written in the  previous lesson to  print the characters of a string  and see what goes where in the memory  and we will also look into the concept  of string constants  and constant pointers so this is where  we had left in our previous lesson  we have written a function print to  print the characters in a string  in the main method we have a character  array of size 20  but we have stored a string of length 5  in it  now we have used a string literal so a  null termination is implicit  we have talked about this earlier so let  us  step through this code and see how it is  working now once again i have drawn this  familiar diagram  the memory that is allocated for  execution of a program is typically  divided into these  four parts these four sections one part  of the memory stores the  instructions in the program we call that  the code segment or the text  segment one one section stores the  global variables and stack is where all  the information regarding function call  execution  and all the local variables go whenever  we are writing a program whenever we are  executing a program we should always  visualize  what variable goes where  or what data goes where and what is the  scope of that variable or data  okay so let us run through this code and  see what is happening in the memory  when this program will start executing  first the main method  main function will be invoked whenever  a function is called some amount of  memory from the stack  is allocated for the execution of that  function it’s called  the stack frame of that function so let  us say  this stack frame from address 100 250 is  allocated for the main function  stack is one contiguous block of memory  so let us say in the stack the memory  increases from bottom to top  all the local variables of a function go  into the stack frame of the function  so when we declare a character array uh  20 bytes from this stack frame will be  allocated for this particular character  array  let’s say they are allocated from  address 100 to 120.  each character is stored in one byte so  we need 20 bytes  for character array of size 20. apart  from local variables there may be some  more information  in stack frame so that’s why we have  some more space and now the control  of the program goes to this statement  print c  as soon as we make a call to another  function from a function the execution  of that particular function  is paused at that particular line and  the machine goes on to execute  the called function the call function is  allocated  stack frame on top of the calling  function so print will be allocated a  stack frame on top of  main function whatever function is at  the top of this stack in  at any point is executing main will wait  for this function to finish  let’s say this particular stack frame is  from 150 to 170  main is paused and print is executing  right now  now print will also have a local  variable c but this will be a  pointer variable a pointer variable  takes  four byte of memory in a typical  architecture so this will be  taking four bytes so let’s say starting  address  one five four in this stack frame we  have four bytes for this particular  character pointer so this c  in main is actually not the same c in  print  the c in main and the c in print are  different  they have different scopes we could have  named this particular variable  a or ptr or whatever but all that  happens when we make this particular  call  to print and pass this c here  is that the address 100 which is the  base address of the array  is passed to the print function and the  print function keeps it  stores it in a pointer variable  sometimes it may confuse us when we are  using the same  local variable name in the calling  function and the same  argument name in the called function but  we must always understand that they are  different  okay to run through this code further  i’ll clear some space  here now i’ll draw this array c  outside the stack here now we have an  array of size 20  but we are only showing the first six  positions in the array from address 100  205  and that’s why it is extending towards  the right  the sixth character is a null character  and the first five characters  are the characters of word hello and now  we have this another guy which is c  of print which is a character pointer at  address 154 that stores address 100 so  it points to  the first element of the array now let’s  come back to our program execution  let’s say we are here initially uh i’ll  mark the statement that  is executing by this green arrow let’s  name these two guys this guy’s c but  this guy  is an array local to main and this is  also c but it is a character pointer  local to print  okay so now here what we are saying is  while asterisk c is not equal to the  null character  when we put this asterisk operator in  front of a pointer variable  we are looking at the value at that  particular address  so at this stage when c is pointing to  the  base address asterisk c is h so this  condition is not true  we will go to this line printf that will  simply print asterisk c  which is h let’s write down the output  here so we have  printed h so far and then we say c  plus plus if we understand pointer  arithmetic from our previous lessons  incrementing a pointer by one unit  increments the address by size of the  data type  that the pointer points to c here is a  pointer to character data type and  character data type is  one byte so c plus one c plus plus is  saying  c is equal to c plus one so c now  becomes hundred and one  so now c points to the second character  in the array  and once again we come to verifying this  condition in the while loop  asterisk c is e here it’s not null now  once again we will go inside the loop  and print  e and we will keep on going like this  until the address in this pointer  variable reaches  105 now here the value at this  particular address is  null character so the loop will not  execute  we will come to this statement to print  an end of line  and the execution of print function will  finish  so this particular stack frame for print  will be cleared from the stack will be  deallocated and now main will resume and  finish  so with pointers we should always know  what’s going where  in the memory okay so let us now  modify this particular code to learn  some more concepts  now what i’m going to do in my code is  instead of  creating a character array of size 20  i’ll create a character pointer named c  and equate it against  a string literal in a statement like  this and if you run this program  and the output will be the same what  really happens is  if you use the string literal in  initialization statement of an array  something like this  and then the string gets stored in the  space that is allocated to the array  so in this case it will go into the  stack in this character array of size  20 but if you use the string literal  elsewhere in a statement like this or  maybe when we do something like passing  a string literal  to a function then in these cases  the string gets stored as a constant  during the compile time most probably it  will be stored in the  text segment of the application memory  and  it cannot be modified so if you write a  statement like this let’s say you want  to  change the first character of on this  constant string to  a or running this program will give you  an error  will cause a crash okay coming back to  having  a character array now if we have a  character array and we are passing  uh the address of the array to a  function  that function receives it in a character  pointer  now using this pointer we can modify  the data in this particular array so if  i say something like this  we first change the first character to a  and then we are printing the characters  and then as you can see it is possible  to do so  now sometimes we may want a function  just to read a string and not  write anything to force this kind of  behavior we can  change our argument to const character  pointer  now if we run this code this code will  give us compilation error  now we can read whatever is there in the  array that is passed  but we cannot write to any of the  positions this code  will work fine pointers are really  tricky and even the most experienced  programmers  write buggy code when they’re using  pointers i recommend that you get  your hands dirty by writing some code  yourself that’s the best way to learn  so this is it for this lesson thanks for  watching  in this lesson we are going to talk  about pointers and multi-dimensional  arrays  as we have seen in our previous lessons  the concepts of pointers  and arrays go together we have already  talked about pointers in context of  one-dimensional arrays  how we can work with one-dimensional  arrays using pointers now let’s see how  we can work with  a two-dimensional array or a  three-dimensional array  or a multi-dimensional array in general  using pointers  to understand this concept once again we  first need to understand how  multi-dimensional arrays  are organized in computers memory let’s  first go back to the organization of  one-dimensional arrays in memory  when we declare a one-dimensional array  something like this  let’s say we are declaring an integer  array a  of five elements then basically what we  are doing is we are creating  five different integer variables that we  can name a0  a1 a2 a3 and a4  as one contiguous block of memory  what i’m showing here is a section of  computer’s memory  array a let’s say is stored in this  section of memory  and the starting address of a is 200  as we know each byte in a computer’s  memory has  an address and if we assume that  an integer is stored in 4 bytes which is  what it takes  in a typical compiler then the block of  4 bytes  starting address 200 will be a0 as i’m  showing here  block of 4 bytes starting address 204  will be a1  next block of 4 bytes starting at s208  will be  a2 and so on i’ll fill in some values  here  we had seen this earlier also in our  previous lessons if we write a statement  like this  then this is all right if i just use the  variable name  a then name of the array in an  expression  basically returns a pointer to the first  element of the array  because this is an array of integers so  each element will be an integer  hence a returns a pointer to integer  once i have written a statement like int  asterisk b equal  a i can use pointer arithmetic and d  referencing to  access all the elements in the array if  i would just try to print the address  stored in p  and i’m not using full printf statement  here my output will be 200.  if i would simply try to dereference p  then output will be 2. if i would try to  print something like  asterix p plus 2 then output will be 6  because we have an integer pointer  adding 1  will take us to the address of the next  integer  which will be 4 bytes ahead adding 2  will take us to the address of  next to next which will be 8 bytes ahead  if we would be printing p plus 2 it will  be 208 and if we would  day reference and we would print asterix  p plus 2 then it will be  value 6. we have already discussed  pointer arithmetic in our previous  lessons  now language gives us this flexibility  that we can use  the name of the array just like a  pointer  for all the d referencing so instead of  doing all of this printing with p if we  would do all of this with  a it will still be the same  in fact astex a plus i is same as  a i these are alternate syntax  and a plus i is same as ampersand a i  both will give us the address  of the ith element in the array please  remember that even though we can use the  name of the array  just like pointer for all this  dereferencing and arithmetic  it’s not same as a pointer variable so  we can do something like  p equal a like what we have done here  so this is all right but we cannot do  the other way we cannot say  a equal p this will give you compilation  error  so this is pretty much how we would use  pointers with one-dimensional arrays  let’s now say we want to create  a two-dimensional array i will declare a  two-dimensional array of integers named  b something like this  now what we are doing here is we are  creating  array of array we are creating two  one-dimensional arrays  of three elements each this time  b0 and b1 are both one-dimensional  arrays of three integers each  a one-dimensional array of three  integers would be  12 bytes if each integer is four bytes  in size  so if i have to show this in memory the  first  block of 12 bytes starting address 400  will be b0 and the next  block of 12 bytes starting address  412 will be b1  as we had said name of the array returns  a pointer to the first element  in the array this time each element is  not an integer each element is a  one-dimensional array of three integers  so if i would write a statement like  this int asterisk p  equal b then this will give me a  compilation error  because b will return a pointer to 1d  array of three  integers and not just a pointer to  integer  the type of a pointer matters not when  you have to read the address  it matters when you de-reference or when  you perform pointer arithmetic  it’s really important that we understand  this we can define a pointer to  one d array of three integers like this  and now if i’ll equate this with p  this is all right equate b  with b this time if i would print  just b which is same as printing address  of  b0 this will be 400  if i will print asterisk b which will be  same as  b0 then b0 this time is  variable name for a one dimensional  array of three integers  so just using the name b0 will return us  pointer to the first integer in b0 which  will be accessed  as b00 so i’m putting this ampersand  sign here in front of b00  first integer in b0 will be this block  of 4 bytes  its address once again is 400  okay now i have also created three  blocks of four bytes each in both  b0 and b1 and also fill in some values  now i’m going to write some print  statements and i want you  to guess the output what will be the  output if i’ll try to  print b plus 1 i will write the address  of  each block of 4 bytes in the 2d array  the address  of a block is the address of the first  byte in the block  okay so what will be the value of b plus  one  b this time is returning us a pointer to  one dimensional array of three integers  so if i would do a pointer arithmetic  like adding plus one  we are moving to the next 1d array of  three integers  so we will be moving to address 400 plus  size of one dimensional array of three  integers  in bytes so output will be 412  which makes sense because p plus 1 is  same as  ampersand b1 or address of b1  and address of b1 is 412.  okay now what if i print asterix b plus  one  when we are putting an asterisk signs  when we are trying to dereference this  is when  the type of pointer becomes important b  is a pointer to one dimensional array of  three integers  so b plus one is also a pointer to one  dimensional array of three integers  and when we will de-difference we will  get this whole one-dimensional array of  three integers starting address four  hundred and twelve  asterix b plus one is same as b1 so we  will get b1  now printing b1 means using the  name of this one-dimensional array b1  which should return us the pointer to  the first  integer in b1 so asterisk b plus 1 is  basically pointer to this  integer at address 412  once again this output will be 412.  all these expressions asterisks p plus 1  or  b1 or ampersand b1 0 are returning us  pointer to integer okay now you need to  gear up because i’m going to give you  some tough ones to decode  what will be the output if i will print  asterisk  b plus 1 plus 2 take some time and think  about it  asterix b plus 1 as we saw above will  return  an integer pointer to first integer in  b1  to the integer at address 412 adding 2  here is performing pointer arithmetic  because asterix b plus 1 is a pointer to  integer  storing this address 412 adding two is  basically  going to the address of next to next  integer  which will mean skipping 8 bytes and and  going to reference integer  at address 420 asterisk b  plus 1 in this expression can be written  as b1 simply b1  because they are substitutes for each  other they are alternate syntax  so this is same as b1 plus 2 and once  again  these expressions are returning pointer  to integer they are returning pointer to  this element  b12 and that’s why we can also say  ampersand b12  all these three once again are same  let’s do one more print  if you can get this one right i can say  that you’re good  working with two dimensional arrays  using pointers what will be the output  for this expression asterisk of  asterisks  asterisks of asterisk b plus 1  what will be the output for this  expression think about it  whenever you encounter an expression  with pointed arithmetic  and dereferencing then you must go step  by step  here b is returning us  pointer to one dimensional array of size  three  one dimensional array of three integers  and d  referencing it will give us the one  dimensional array  so asterisk b as we know will give us  b0 as should be is same as b0  now b0 in my expression because b0 is  named for  a one-dimensional array returns me  pointer to the first integer  in the one-dimensional array so b0  returns pointer to integer  we will get a pointer to this integer at  address 400.  now what will happen if you will add one  to an integer pointer  it will take you four bytes ahead to the  next integer it will return your pointer  to the next integer so we will get a  pointer to this integer at address four  zero four  asterisk b plus 1 is basically ampersand  b01  and with this final dereferencing we can  get rid of this ampersand so the overall  expression  will be b01 which is 3  for a 2 dimensional array b  i j where b is named for my 2  dimensional array and  i and j are some indices can be written  as  asterisks of b i  plus j and once again b i can be written  as  asterix of b plus i  so these three expressions are same i  would recommend trying all of this in  real code  so far this discussion has been about  working with two dimensional arrays  using pointers  we will stop here for this lesson in  another lesson we will  play with some real code and we will  also discuss how we can  work with an array of further higher  dimension like a three-dimensional array  we will also discuss passing of arrays  to functions  through pointers this is it for this  lesson thanks for watching  in our previous lesson we saw how we can  work with two dimensional arrays using  pointers  now in this lesson we will see how we  can work with arrays of further higher  dimensions like  three dimensional arrays using pointers  we will also see how we can pass  multi-dimensional arrays as  arguments to functions because that’s  one scenario where pointers once again  will come into picture  i will start with a quick recap of what  we have discussed in our previous lesson  whenever we create a multi-dimensional  array and let’s pick up the example of  two dimensional array that we had  created in our previous lesson  we must think of the multi-dimensional  array as  array of arrays array basically  is a collection of similar things of  similar objects  so a multi-dimensional array is  basically a collection of arrays  this array b here is a collection  of one-dimensional arrays of three  elements each  we have two one-dimensional arrays of  three elements  each what i have tried to show in this  figure is how  array b will be organized in memory i  have assumed that the starting address  of the array is  400 each cell storing an integer  here is a block of 4 bytes as we know  each  byte in computers memory has an address  i am not drawing all the bytes partition  for all the bytes i am trying  blocks of 4 bytes each and that’s why  i’m writing only the starting address of  each  block you can imagine a block of four  bytes  something like this the starting address  is 400 let’s say each partition here  is one byte so the next  byte has address 401 and the next one  has address 402 and the next one has  address 403  overall this first block of 12 bytes  that will that contains these three  integers 2 3 and 6 that i’m showing in  yellow here  is my first one-dimensional array that i  can call b0  and this next block of 12 bytes is my  second one-dimensional array of three  integers that i can call  b1 so we have two one-dimensional arrays  in our collection we have two  collections of three integers  each in our collection and everything is  organized in one contiguous block of  memory  now let’s look at this b0 is from byte  address  400 till 411  we have three integers and we have four  bytes for each integer  the first integer that we can access as  element at  zeroth index of b0 is taking four bytes  starting address 400  the next integer that can be accessed as  b01 one element of b0  will take next four bytes starting 404  and the next one will be b02 element at  index two of p0  and similarly we will have four bytes  for  zeroth element of b1 four bytes for one  element and four bytes for element at  index  2 of b1 as we had seen in our previous  lesson when we just use the  array name then it returns us a pointer  to the first  element of the array here b is  a two dimensional array it is an array  of one dimensional arrays of size  three so b will basically return us a  pointer to  one dimensional array of three elements  pointed to one dimensional array of  three  integers in this statement i have  declared  a variable which is pointed to one  dimensional array of three  integers and the name of the variable is  p a statement like this is all right  a statement like this will not be all  right because b will not return  a pointer to integer b will return a  pointer to one dimensional  array of three integers now i will write  three print statements that i had also  written in our previous lesson  i am not writing the complete syntax for  printf okay so once again you need to  tell me what will be the  output if we would print these three  expressions  we have p asterisk b and b0  well for all these three output will be  400  here when we say b just using the array  name b  will return us a pointer to the first  one dimensional array in b  the type of a pointer variable is  relevant only  when we are trying to dereference or  perform pointed arithmetic  but if we would just try to print the  address  stored in the pointer variable it will  be the starting address  address of the first byte of a block of  memory  so if we have a pointer to this  one-dimensional array that is storing 2  3 and 6  then its address is 400. now when we did  an  asterisk b which is same as b0  we de-referenced and now we have got the  complete one-dimensional array b0  now if i use b0 because b0 is a  one-dimensional array  we will get a pointer to the first  integer in b0  so we will get a pointer to b00  this block of 4 bytes starting address  400  once again if we would just print the  address then the  starting address of this block is 400  that’s why the output here is 400 even  if i would print  ampersand b00 the output will be  400 b and asterisk b are both  returning as pointers the difference is  that b is returning  pointer to a one dimensional array of  three integers  while asterisk b is returning pointer to  an integer  when we are just printing the address  both these objects  the complete one-dimensional array b0  and the first  element in b0 have the same starting  address so the same starting address  will be printed  the type of pointer plays role when you  try to dereference or when you try to  perform  pointed arithmetic we had also seen in  our previous lesson that  b i j can be written as asterisks of  b i plus j if b i for some value of  i is a one dimensional array then b i  will give us an integer pointer will  return  us an integer pointer to the first  integer in bi  then adding j is basically performing  pointed arithmetic  and getting a pointer to integer at  index  j in one dimensional array bi and then  finally this day referencing is getting  the value of that integer  once again b i can be written as  asterisk b plus i b  is a pointer to one dimensional array of  three integers so b  plus i will also return a pointer to one  dimensional array of three integers and  dereferencing this particular day  referencing  will give us the one-dimensional array  and the name of one-dimensional array  returns us  pointer to the first element in the  array so this once again will be  pointer to integer by now if you clearly  understand how all the pointer  arithmetic  and dereferencing is happening in these  expressions  then it’s not very difficult to  understand how things will be  for say a three-dimensional array  now let’s say we have created a  three-dimensional array  named c we have an array of three cross  two cross two a three-dimensional array  is basically  an array or collection of  two-dimensional arrays  so if i have to show c in memory i will  show it something like this  i have assumed that the starting address  of c is byte addressed  800 the first 16 bytes starting address  800 is my first two dimensional array  i am assuming that each integer will  take four bytes  so all these cells in yellow are part of  the first two dimensional array  the next block of 16 bytes starting  address  816 is c1 and the next block of 16 bytes  starting at 32 is c2 we can further  break down the two dimensional arrays  into one dimensional arrays the first  two integers in c0  are part of the first one-dimensional  array c00  and 7 and 9 are part of c01  the first integer in c00 can be accessed  as c000  and we can go on like this okay once  again  i will play the same game i will write  some print statements  and you need to guess the output this  time  just using the array name c will give us  a pointer to a two dimensional  array of integers of size two cross two  so we can write a statement like this i  have declared  a pointer to two dimensional array of  integers  of size 2 cross 2 here the name of the  pointer is p  if i would just print p or c here  and i’m not writing the complete printf  statement once again  my output will be 800 now if  i will perform a d referencing and try  to  print asterisk c then this will be same  as  c 0 and c 0 is a 2 dimensional array  so we will get a pointer to the first  element in c0  all these expressions are returning us  pointer to one dimensional array of  integers  of size two and the address printed will  be  800 remember c is of type  pointer to 2d array of 2 cross 2 and  d referencing once is giving us pointer  to one dimensional array  of two integers c is returning us  pointer to two dimensional array of  integers c  itself is an array there is difference  between the two types  okay for c c i j  k where i j and k are some indices can  be written as  asterix of c i j plus  k and now once again we can write  c i j as asterisks of c i plus  j and the overall expression will look  something like this  and we can go ahead and write c i  as asterisks of c plus i  if you are able to understand how i have  derived these expressions if you are  able to understand all the  pointer arithmetic and dereferencing in  these expressions  then you are good working with  multi-dimensional arrays using pointers  i want a quick answer for this one what  will be  the output for this print statement  well c01 means we are going to this  one dimensional array that has these two  elements seven and nine  and when we are using the array name c01  we are getting a pointer  to first integer in this one-dimensional  array  pointer to this integer seven adding one  we are doing  pointer arithmetic to an integer pointer  so we will go to  nine and day referencing will give us  integer nine in fact this expression is  same as  c of zero one one now what will be the  output for this print statement  asterisks of c1 plus one c1 will return  us a pointer to one dimensional array  the first one-dimensional array in c1  this block containing integers three and  four  adding one is performing pointer  arithmetic and going to the next  one-dimensional array  it’s going to this one-dimensional array  containing  six and one and now d-referencing is  basically  getting the one-dimensional array from  the pointer  and if you just use the name of the  one-dimensional array  you get a pointer to the first element  in one-dimensional array  so we will get a pointer to this integer  six  output will be 824.  this block of 4 bytes storing address  storing integer 3 is 816 next would be  next will be a 20 and next will be 8 24.  we can try out these expressions in real  program  i’m writing this simple c program i have  created this  three-dimensional array c the data  filled in  is same as we were showing in the  example in the first printf statement  i’m writing i’m trying to print  c asterisk c c 0 and ampersand c  0 0 all of these are pointers and  if i would just use person d  address would be printed when i’m  running this code as you can see  the output for all these four  expressions  is same any guesses for what will be the  output for this printf  statement this expression is nothing but  c001  the output for first printf is different  because this is a different  run of the program and in each run  the signed address would change but  whatever the address says it will be  same for these  four expressions i would recommend  trying out all the different expressions  that we were decoding earlier in a real  program like this  okay the next thing that i want to talk  about is passing multi-dimensional  arrays as function arguments  i’m going to declare a function and  let’s name this function  f u n c and  i want this function to accept a  three-dimensional array as argument  so what do i do if i wanted a one  dimensional arrays argument  i could have given something like this  but  as we had discussed in one of our  previous lessons this syntax  is only a syntactical sugar it is  interpreted  like this by the compiler a fresh copy  of  array is not created for a function call  only a reference to it  in the form of a pointer is created  so now if in the main function i have an  array  a one-dimensional array like this and  let’s say  the return type of this function is void  i can make a function called passing  a like this and this will be fine  now let’s say we declare a two  dimensional array of two cross  three and now we want this function to  receive  to take a two dimensional array as  argument  now as we had discussed a will  return us pointer to integer but b  will return us a pointer to array of  three integers  one dimensional array of three integers  for this particular definition of p  so for the function to take this array  b as argument definition should be  something like this the argument should  be something like this  either we can write this or we can write  something like this only the first  dimension can be left empty the other  dimension has to be specified  and now i can pass b there is something  interesting here if i would declare a  two dimensional array something like  this let’s say i declare a two  dimensional array  x of two cross four now i cannot  pass x to the function because  x will return pointer to one dimensional  array of four integers  while this function is supposed to  receive one dimensional array of three  integers  if x is defined something like this of  dimension five cross  three then passing x is fine  now if we want to pass this three  dimensional array  then once again we need to see what  pointer type c  will return so c will basically return  a pointer to two dimensional array of  two cross  two so we can either use a syntax like  this  or something like this and then we can  pass c  so this is how things will be for any  multi-dimensional  array except the first dimension  all other dimensions will be enforced  one common mistake that people do is for  a two-dimensional array  they try to use pointer to pointer  something like this  and for a three-dimensional array they  try to use something like this  which just won’t work so this is pretty  much what we wanted to talk about  pointers and multi-dimensional arrays  thanks for watching  memory is one important  and crucial resource on our machine and  it is always good to know the  architecture of  memory the way operating system manages  memory  and the way a memory is accessible to us  as programmers  in this lesson we will discuss the  concept of dynamic memory  and we will see how to work with dynamic  memory using c or c  plus plus the memory that is assigned  to a program or application in a typical  architecture can be divided into  four segments one segment of the memory  is assigned to store the  instructions that need to be executed  another section stores all the static or  global variables the variables that are  not declared inside a function  and that have the whole lifetime of an  application they are  accessible anywhere during the whole  life cycle of the application as long as  the application is running  one section of the memory is used to  store all the information  of function calls and all the local  variables  and we have also talked about stack in  our lesson on  call by reference local variables are  declared  inside a function and they live only  till the time the function is executing  the amount of memory set aside for these  three segments  the text segment the global variable  segment and the stack  does not grow while the application is  running we will come back to why we use  this  fourth segment heap in a while let us  first understand how  these three segments of the memory are  used when a program  executes i have a simple c program here  we have a function square that gives me  the square of a number  we have another function square of sum  that is given two arguments  x and y and it returns us the square of  x plus y and in the main method i’m just  calling this function  square of sum passing it to arguments a  and b let us now see what happens in the  memory when  this program executes let us say this  rectangle  in green here is memory reserved as  stack and this rectangle in orange is  the memory reserved as  static or global variable section when  the program starts executing first the  main method is  invoked when the main method is invoked  some amount of memory  from the stack is allocated for  execution of  main and this total is a global variable  so it should  sit in this section the amount of memory  allocated on stack for execution of main  can also be called the stack  frame for the method main all the local  variables  arguments and the information where this  function should  should return back to all this  information is stored  within this stack frame the size of the  stack frame  for a method is calculated when the  program is compiling  now when main calls square of sum method  let’s write shortcut s o s  for square of sum then a stack frame is  allocated for  the call to square of sum all these  local variables xyz will sit in this  particular stack frame  now sum of square calls square let’s  again put a shortcut here for square  so another stack frame for square and it  will have its own local variables  at any time during the execution of the  program the function at the top of the  stack is executing and rest  are kind of paused waiting for the  function above to return something  and then it will resume execution i have  drawn this  play and pause button here in case you  do not understand  okay so this total is a global variable  it sits here  in this section global variable because  it is not declaring  declared inside a function we can access  it anywhere  and then we go to this particular  statement where we call square of sum  and square of sum is calling square  so right now this is our call stack  this program may not be the best way to  implement this logic  i have written this program this way so  that i can have some nested methods  calling each other let’s say right now  we are at this particular statement we  are executing  executing this statement so at this  stage cost  a call stack will have these three  methods  now when this method finishes we will  return back to this particular statement  as soon as square function will return  it will be cleared from the stack memory  and now  some square of sum function will resume  once again when square of sum finishes  the control will  come back to this particular line to  line total is equal to square of sum  and main will resume again  now main will call printf so  once again printf will go to the top of  the stack  printf will finish and the control will  come back again to main and now main  will finish  and when main finishes program will also  finish  so in the end our global variables will  also get cleared  there was no need in this program to  keep this variable total as global  we should assign a variable as global  only if  it is needed at multiple places in  multiple functions and it is needed for  the whole lifetime of the  program otherwise it’s a waste of memory  to keep it  keep available for the whole lifetime of  program execution  we had kept one global variable in this  program just to  understand the cost concepts here i must  point out  one more thing when our program starts  our  operating system allocates some amount  of reserved space let’s say  os allocates 1 mb of space  as stack but the actual allocation of  the stack frame  and the actual allocation of the local  variables happens from this stack  during runtime and if our call stack  grows beyond the reserved memory for the  stack like  for example if a method a calls b b call  c and we go on calling  and we exhaust the whole space reserved  for the stack  then this is called stack overflow and  in this case  our program will crash  one common case of stack overflow is  when you write a bad recursion and your  program  goes infinitely into recursion  so as we can see there are some  limitations of stack  the memory set aside for stack does not  grow  during runtime application cannot  request more memory for stack  so if it is 1 mb then if the allocation  of variables and functions in stack  exceeds 1 mb  our program will crash further the  allocation and deallocation of memory  onto the stack happens by a set rule  when a function is called  it is pushed onto the stack on top of  the stack  when it finishes it is popped or removed  from the stack  it is not possible to manipulate the  scope of a variable  if it is on the stack another limitation  is that if we need to declare a large  data type  like an array as local variable then we  need to know the size of the array  at compile time only if we have a  scenario like  we want to decide how large the array  will be based on some parameter  during runtime then it is a problem with  stack  for all these requirements like  allocating large  chunks of memory or keeping a variable  in the memory till the time we want  we have heap  unlike stack applications heap  is not fixed its size can vary during  the lifetime of the application  and there is no set rule for allocation  and deallocation of memory  a programmer can totally control how  much memory  to use from the heap till what time to  keep the data  in the memory during the application’s  lifetime  and heap can grow as long as you do not  run out of memory  on the system itself that is a dangerous  thing also and we need to be really  careful  about using heap for this reason we also  sometimes call  heap free pool of memory or free  store of memory we can get as much as we  want from the heap  how heap is implemented by the operating  system  language runtime or the compiler is  something which can vary which is a  thing of  computer architecture but an abstracted  way  of looking at the heap as a programmer  is that this is one large  free pool of memory available to us that  we can use  flexibly as per our need  heap is also called dynamic memory and  using the heap is referred to as dynamic  memory allocation  and let us now see how to use the heap  in our  c or c plus plus program i will clear  this code in the left  and i will draw one more rectangular  block here  for heap there is one more thing that i  must point out before moving forward  heap is also one data structure and if  you do not know about this data  structure heap yet  you will learn about it in your data  structure course but this nomenclature  here  has nothing to do with the heap data  structure  the term heap here is being used only  for the  large free pool of memory heap data  structure does not come anywhere in this  con  context this term often confuses a lot  of people when they  know about heap data structure stack is  also one data structure but  the stack segment of the memory is  actually an implementation of stack data  structure  but heap is not an implementation of  heap data structure  to use dynamic memory in c we need to  know about  four functions malloc catalog  re-alloc and free to use dynamic memory  in c plus plus we need to know about two  operators  new and delete these four functions  can also be used in c plus because  c plus plus has backward compatibility  it is only a  super set of c but c plus plus  programmers mostly  use these two operators new and delete  we will see some code examples  and try to understand how things happen  when dynamic memory is used  let us first pick up some code example  in c  let us write a c program i’ll clean up  some of this stuff in the right  one mb first tag this was just an  assumption in reality the size of the  stack will be decided by the operating  system  and the compiler it is a thing of  architecture  coming back to the code if we declare a  variable like this  then this variable is a local variable  it goes on the stack  memory for this particular variable a  will be allocated from the stack frame  of the  main method let us say we want to  store an integer on the heap to reserve  or get some space allocated on the heap  we need to call the malloc function  something like this the malloc function  asks for  how much memory to allocate on the heap  in bytes  when we say malloc and passes pass as  argument size of integer  then we are saying that hey give me a  block of memory which is  four bytes four bytes is the typical  size of an integer  so one block of four bytes will be  reserved or allocated on the heap  and malloc will return a pointer to the  starting address of this block  and malloc returns a void pointer let us  say the starting address of this block  of 4 bytes is 200  so malloc will return us the address  200. now we have a pointer to integer p  which is a local variable to main so  this will be uh  this will be allocated in the stack  frame of the main method  we have done a type casting here because  malloc returns pointer to  wide sorry void pointer and p is an  integer pointer  now p stores the address of this block  of memory which is  200 so we have got some block of memory  on the heap  which we want to use to store an integer  right now we do not know what’s there in  this particular  block of memory if we want to fill in  something here  we need to de-reference this location  using the pointer p  and then put in some value in fact the  only way to use  memory on heap is through reference all  the malloc function does is  looks for some free space in the heap  books it or reserves it for you  and give back the pointer and the only  way you can access this particular block  by keeping a pointer variable which will  be local to your  function now let us write something like  this  after writing 10 in this particular  block  i will go ahead and make one more call  to malloc  when i make one more call to malloc one  more block of  four bytes is allocated on the heap and  let us say the address is  400 for this block now the address that  is returned by the second call to malloc  we store this address in the variable p  so what happens  is that p is now pointing to the address  400  the next line writes 20 at this address  we allocated one more block and we  modified the address and p to  point to this block the previous block  will still sit in the heap  this memory we are still consuming it  will not be cleared off automatically  at any point in our program if we are  done using some particular block  of memory which is dynamically allocated  using malloc  we also need to clear it because it is  unnecessary consumption of memory which  is an important resource  so what we should have done here is that  once we were done using this particular  block of memory at 200  we should have made a call to the  function free  any memory which is allocated using  malloc is cleared off  by calling free and to free we pass the  pointer to the starting address of the  memory block  so now with this code this first block  of memory will first be cleared  and then we will be pointing to another  memory address  it is the responsibility of the  programmer to clear anything  on the heap if he has allocated it and  does not need it any further  so if you see in terms of the scope of  the variable anything allocated on the  heap  is not automatically deallocated when  the function completes like  on the stack and it does not live it  does not need to live  for the whole lifetime of the  application like a global variable  we can control when to free anything on  the heap when to deallocate anything on  the heap  if we wanted to store an array on the  heap like let’s say we wanted to store  an integer array  then all we do is make a call to the  malloc asking for  one block of memory equal to the total  size of the array in bytes  so if we want an integer array of  20 elements then we will make a call to  malloc  asking 20 into size of int which will be  4  number of bytes so what will happen now  is that one big contiguous block of  memory  for 20 integers will be allocated on the  heap  and we will get the starting address of  this block so we kind of get the base  address  of the array this p will point here  to the base address of this block and  then in our code we can use this  20 integers as p0 p1  p2 and so on as we know  p0 is same as saying value at address p  and p1 is same as saying value at  address p  plus 1 this is what it means  one more thing if malloc is not able to  find any free block of memory  is not able to allocate some memory on  the heap it returns  null so for error handling we need to  know this  and we need to write our code  appropriately  malloc and free the use of malloc and  free is c style code  if we want to write the same code same  logic in c plus plus then there is not  much difference  instead of using these two functions  malloc and free  we will use two operators new and delete  and write our code something like this  so instead of using malloc we are using  the new operator here  and instead of using free we are using  delete here  if we want to allocate an array we  use something like this where we put the  size in brackets here  and if we want to free an array we use  this particular operator delete  and two brackets sorry one bracket  with c plus plus we do not have to do  all these type castings  like malloc returns void and we need to  type cast it back to integer pointer  new and delete operators are type safe  what it means is that  they’re used with a type and return  pointers to  a particular type only so here we will  get a pointer to  integer only we will be talking about  dynamic memory allocation  and other library functions in more  detail in the coming lessons  so thanks for watching in our previous  lesson we learned the concept of  dynamic memory allocation we learnt  about  stack and heap in the context of  applications memory  in this lesson we will be looking at  various library functions available  in c for dynamic memory allocation we  will  look through these functions in some  code examples  we will be talking about three functions  that allocate  block of memory on the heap and these  functions are  malloc catalog and  reallock and we will also be talking  about one function that  d allocates a block of memory on the  heap  and this function is free now let us  first talk about malloc  this is the most frequently used library  function  for dynamic memory allocation and the  signature or the definition of this  function is  something like this this function as  argument asks you for the size of the  memory block in  bytes this data type size underscore t  if you are not aware of it is a data  type that stores  only positive integer values so you can  think of this particular data type as  unsigned  integer data type the size cannot be a  negative value it cannot  either be 0 or a positive value and  to force this kind of behavior we use  this particular type  and this function malloc returns a void  pointer  we have talked about void pointer in our  previous lessons  malloc returns a void pointer that gives  us the address of the first  byte in this block the block of memory  that it allocates  so using malloc you kind of say that hey  give me a block of  memory with these many bytes let us say  what we have here in the right is the  heap section of memory available to us  each of these partitions are one byte as  we know each byte in the memory has an  address  let us say this bottom most byte has the  address two zero zero  and the next byte is two zero one and we  go on increasing towards the top  i’ll mark these and mark the address of  some of these bytes  let’s say in our code we make a call to  malloc something like this  that hey give me a block of memory that  is  4 bytes let’s say we store the address  returned by malloc  in a void pointer variable now let’s  assume that this particular  rectangular block that we are showing  here in the red is what gets  allocated against this call to malloc  these are four bytes the starting  address is 208  so what will be the address in p if we  want to print  the address in p then what will be the  output the output will be 208  this is cool using malloc we are able to  allocate some amount of memory reserve  some amount of memory  but why do we reserve memory we reserve  our allocate memory because we want to  store some data there  so we do not want to just randomly  allocate some number of bytes  so all that is correct to write a  statement like this in practice we would  not do so  in practice we would first calculate how  much amount of memory  we need to store our data so let’s say  we want to store  an integer just one integer so i need  a memory block equal to the size of one  integer  so we typically use the function size  off  which returns us the size of a variable  in bytes  to figure out the size of the data type  and then we typically multiply this  particular value  returned by size off by the number of  units that we need  so if we need just one integer  if we need memory for just one integer  and this is good  if we need memory for 10 integers we  would write something like this  give me 10 into sizeof integer  integer is a primitive data type  sometimes you may know that i know that  size of integer is 4 bytes  so i can write something like 10 into 4  here but it’s not a good practice to do  so  size of a variable depends upon the  compiler and we would also be  using malloc to allocate memory for  complex data types  so we must use malloc like this  total number of bytes should be written  as number of elements into  size of one unit one unit of the data  let’s say we want to have space for  three integers  i have picked up three so that i have  enough enough space  to allocate memory in the figure that  i’m showing here  and let’s say and this block of 12 bytes  is allocated because size of integer is  four bytes  typically so this starting address would  be 201  now how do we fill in data here if you  see malloc returns a void pointer  and void pointer as such cannot be  dereferenced  you cannot write a statement something  like asterisk p is equal to 2  this is incorrect you cannot dereference  a void pointer white pointer in fact is  only used as a generic pointer type  which is normally type casted into a  pointer type of a particular  data type and then it is used because  malloc itself is a generic function to  allocate  some number of bytes in memory in heap  it does not care where whether you are  allocating this memory to store  character or  to store integer or to store any other  data type  it simply returns a void pointer to the  starting address  to be able to use this block of memory  we first need to typecast this void  pointer  into a pointer of some data type so here  we will write something like  in star p instead of picking up a void  pointer we pick up  a pointer to integer because we want to  operate with integers  so to d reference we need an integer  pointer type so  we do the type casting here of the void  pointer and now this statement is valid  if we want to assign some value to the  second element second integer in this  list  then we will do something like we will  de-difference the address p plus one  let’s say we write the value four here  and if we want to  access the third integer then we will  write something like this  let’s say the value of six here by  asking for a memory block  for three integers we are basically  creating an array of integers  with three elements we could also write  this asterisk p  as p zero and we could also write  asterisk p  plus one as p p1 and similarly asterisk  p plus 2 as p2  they mean the same all the manipulation  on dynamically allocated memory happens  through pointers  you have a pointer to the starting  address and then if you want to go to  the next  element in the array you increment the  pointer  and this is how things happen we have  two more functions that allocate block  of memory  let us now talk about calloc the  signature or definition of kellogg  is something like this kellogg also does  the same stuff as malloc  it is only a slightly different kellogg  also returns  a void pointer but kellogg takes two  arguments  instead of one argument it takes two  arguments the first argument is the  number of elements  of a particular data type and the second  argument is the size of the data type  so with malloc if we have to declare an  array of size three  an integer area of size 3 we would say 3  into size of  end with callout we would say something  like this  the first argument is how many units of  the data type you want  or the number of elements and the second  argument is the size of data type in  bytes there is one more difference  between malloc and calloc  when malloc allocates some amount of  memory it does not initialize the bytes  with  any value so if you do not fill in any  value into these  addresses allocated by malloc you would  have some garbage there  but if you allocate memory through  callock calloc  sets all byte positions with value  zero so it also initializes the memory  that it allocates  to zero the third function that we  want to talk about is reallock  if you have a block of memory  dynamically  allocated block of memory and if you  want to change the size of this block of  memory  then you can use real lock the  definition or the signature of this  particular function is  this function takes two arguments the  first argument is  pointed to the starting address of the  existing  block and the second argument is  the size of the new block there can be a  couple of cases in real lock  the size of the new block that we want  may be  larger than than the size of the  previous block in that case  machine may create an entirely new block  and copy the previous data  whatever bytes was written in the  previous block into the new block  if contiguous or consecutive memory is  already available  with the existing block and the existing  block may also be extended  let us now look at some code examples  and see what we can do  with these three functions and we will  discuss the  function free in our code itself  i’ll write some c code and look at some  of the use cases in which  we can use dynamic memory allocation the  first use case is  let us say we want to declare an array  and we want to first ask the user the  size of the array and then we want to  declare an array  exactly of this particular size entered  by the user so let’s say i have a  variable  n and i write a print statement like  enter size of array and then i input  this  number n from the console now i want to  declare an array of size  n only so can i do something like this  well no this particular value in the  braces  cannot be a variable this will give you  compilation error  we need to know the size of the array we  cannot know the size of the array during  runtime  in such a scenario we can allocate the  memory dynamically so we will write  something like  in star a is equal to and we will make a  call to malloc  to allocate a memory block  equal to the size of n integers  and this will again give a compilation  error unless we  type cast this particular return of  malloc to integer pointer  and now we have an array of size n and  we can  fill in some data into these dynamically  into the elements of this dynamically  allocated array  let’s say we want to put data something  like first element is  1 and the second element is 2 and so on  so we’ll write something like a i is  equal to i plus 1.  we can print the elements in the array  let’s say we want to pick up size of  array as  10 okay so the output is as expected  we have 10 elements from 1 to 10  if i give size of error as let’s say 25  then this is what we get we get all the  elements still 25  if we wanted to use catalog instead of  malloc here  the only change in this code would be  that we would use catalog here and we  would have two arguments  n would separate out as first argument  and the second argument would be size of  end  and this program will run seamlessly  there is one more difference between  malloc and callock  if we do not use this initialization  then with catalog as you can see all the  elements are being printed  as zero they are all initialized to zero  but if we were using malloc here  then these elements are not initialized  there is some garbage value at each of  these indices in the array  so this is one difference between malloc  and catalog calloc initializes  fills the value 0 into each byte while  malloc  doesn’t do this initialization i’ll  rewrite this initialization loop again  and now we will talk about free  any memory that is dynamically allocated  remains allocated till the lifetime of  the program  till the time the program is executing  unless you explicitly  de-allocate and to deallocate memory  allocated using malloc or catalog or  real lock  we have the function free and to the  function free you just pass  the starting address of the memory block  as argument  now what will happen if i free a if we  free a then the data from that memory  is erased it may or may not be erased it  actually depends upon your  compiler or machine but that memory will  be available for a location against  another call to malloc  let’s say let’s see what happens in this  case when we are printing after freeing  that particular memory block  i give error sizes 5 and as you can see  the elements being printed here  there is some garbage value being  printed if this free was not there  we would have printed elements 1 2 3 4 5  as initialized  now the obvious question would be even  though we are freeing the memory here  we are able to access that the value at  that particular memory location using  this statement  when we are using a i the element at  index i well that is one dangerous thing  about pointers  if you know the address you can look at  the value at that address  but you should read and write to that  address only if that address is  allocated to you  what if that address is not allocated to  you like in this case  well you do not know what you are  reading or what you are writing  and what behavior it will have it  actually depends upon the compiler and  the machine  in my case let’s say after freeing we  try to access  the third element a2 and try to push  some value there  let’s see what happens if we run this  program let’s give size of arrays 5  again  if you see even after free we are able  to modify  the value at this particular address a2  but on some machine  such a program may cause our program to  crash  we should always be sure to use the  memory that is allocated  otherwise it’s like shooting in the dark  we do not know what will happen  we will now talk about re-unlock if we  want to modify the size of a memory  block  let’s say we have a memory block to  store n elements in an array  and we want to extend it to maybe we  want to double the size of the array  or maybe we want to reduce the size of  the array to half  for such scenario we use real lock and  call to real lock will be something like  this  let’s say we take another pointer  variable b  then to reallock we pass the previous  pointer a  and size of the new block so the new  block is 2 into n  into sizeof hint and will of course to  of course do the  typecasting here ok now what this call  will do  is it will create a new memory block of  size 2n  and copy the values in the previous  block in the previous memory block a  into this new memory block how real lock  works  is that if the size of the new block is  greater than the size of the previous  block  then if it is possible to extend the  previous block find some consecutive  memory with the same block  then the previous block itself is  extended else  a new block is allocated and the  previous block the content from the  previous block is copied  and the previous block is deallocated  this will become further clear  if i write this print statement i’ll  print the previous block address  stored in a and the new address stored  in b and i’ll also print  all the 2n elements in b now  and i’ll print each element in the array  b in one single line  let’s say size of there is 5 again okay  so the previous block address is  9920128 and if you see the new address  is also same  so it was possible to extend the  previous block only  and in b the first five elements are  from a and rest five elements are  garbage value  if we wanted to reduce the array size to  let’s say half  ah then the same block the previous  block itself will be reduced  so let’s say i want to print the  previous block now the n elements  now as you can see the first two  elements are copied one and two  they’re not copied in fact they’re there  already the rest three are deallocated  when we divide five by two we take only  the integral part  so we kind of deallocate the space for  three elements here  in fact if we give the size to be zero  here  all that will happen is that the  complete block for a will be deallocated  so this statement will be equivalent to  using free upon a  in most cases we will put the return  address by real lock into the same  integer pointer  so we can write instead of writing b  here we can write a also  we can also pass the first argument to  real log as  null if the first argument is null and  the second argument is size  and let’s say we want to create  something like  a new block with address starting at a  store in b  then if the first argument is null then  this  is equivalent to calling a malloc  this only creates a new block does not  copy anything from the previous block  so real lock can be used with the right  arguments as substitute for free as well  as  as substitute for malloc this was all  about malloc  allocary unlock and free we will see  more code on dynamic memory allocation  in the coming lessons  so thanks for watching in this lesson we  will talk about  pointers as return types for functions  a pointer is just another data type  it’s just that a pointer stores the  address of another data type  so it is quite possible for a function  to return pointer  but we must understand the use cases in  which we may want to return a pointer  from a function  so let us try to understand this i’ll  get started by  writing some code now i want to write a  very simple c program initially  i want to write a function add that will  take  two integers as argument and sum these  two numbers and return the sum  so let’s say we declare another variable  c  and c is equal to a plus b and the  function returns c  now in the main method i’ll initialize  two variables let’s name these variables  x  and y let’s say x is equal to 2 and y is  equal to  4 and we will have another variable z  which will be the return of this  function add and we will pass  x and y as arguments to this function  and finally i’ll print something like  sum is equal to z no prices for guessing  the output here i’ll modify this code  slightly  but before that i want to talk about  this concept  once again that x y and z  are local variables to main function  and a b and c are local to add function  and what really happens when we call the  add function is that  value in this variable x of main is  copied to  variable a of add and value  in y of main is copied to b of add  and what if we name these variables in  main  a b and c instead of x y and z  if we run this code output will be the  same this time what we will say  is that the value in a of main is copied  to a of  add and the value in b of main is copied  to b of  add this a in main and this a in add  they are not the same you can verify  this by printing something like this  i’m printing the addresses of these two  a’s  in my code and as you can see address of  a  in main is something like 2883032 and  in add it is 288 2792 so they are not  the same  that means these variables are not the  same they are different memory addresses  the names of variables are local or  specific to a particular function  in our example here the method the  function main  can be called calling function and the  function  add can be called called function  in this particular call when we are  saying that c is equal to  add and passing a and b and this call  where a  and b in main are getting copied to a  and b in add  this is called a call by value  this can be called a call by value now  what i want to do is  instead of passing by value i want to  pass the addresses of these two  variables  so i want to say that i want to pass  address of a  and address of b to the add function so  the signature of add function should be  such that it should  receive the addresses so i’ll say that  okay it takes two pointer two integers  a and b and now we can  access the values at these addresses  by using this asterisk operator which is  used to dereference  an address now such a call is called  call by reference  a and b are integers local to main  function and in the function  add a and b are not integer variables a  and b  are pointer variables pointer to  integers  so uh their type is different they are  not int they are in  star but at the end of the day they are  also variables which are local to  the function add it’s just that they’re  not integers  and now i’m using these two variables  which are pointer to integers  to access these two variables a  and b in the main method and to do so we  use the asterisk operator and now this  code should also work  i’ll write a few more print statements  inside this function  add i have tried to print  a and i have tried to print asterisk a  and initially i was printing ampersand a  so now ampersand a should give us the  address of the pointer variable  a should give us the address of a in  main because that is what  this variable stores and asterisk a  should give us the value  of a in main let us see in the output  as you can see here the address of a in  main is 3537612  and address of a in add is something  else but the value in a of add  which is the address of a of main is  equal to three five three seven six two  so the first and the third line are same  and using the address we are printing  the value which is equal to two  i had a spell mistake here  now i’ll clean up some of these print  statements  coming back to our function add we are  returning this value c  and once again in the main method we are  collecting this values seeing another  variable which is c  of main why not do something like pass  the address of this c  in add function so what we will do now  is we will say that we want to return a  pointer to integer from this function  and here we will return ampersand c now  ampersand operator when it is put in  front of a variable it gives us the  address  now of course here we will have to  collect  this particular address so we will have  to define a pointer variable  now this would be okay and when we are  printing we will have to print the value  at address being pointed to by this  pointer variable  so what we just did was now what we just  did is we modified this  add function to return a pointer to  integer  there are two syntax we can say in and  then  put this asterisk sign or we can say int  and then put this asterisk sign in front  of the  function name add and both the syntax  are valid now this function is returning  pointer to  integer let us run this program and see  what happens  well let me also strike of this print  statement here  okay so the output seems to be all right  now have you got some logical error with  this code already  if you haven’t stay with me for some  time  now what i want to do is i want to write  another function  a simple function that will print hello  world so i’ll name this function print  hello world and then this function i’ll  write a simple print statement  and now before i print this sum what  i’ll do is  i’ll call this function print hello  world  and let’s see what happens now oops this  looks weird  some is not correct now i just saw that  it was coming fine in my last run when i  did not  call this print hello world what  happened  so let’s try to understand what really  happened here  i’ll come back to this familiar diagram  of various sections  of applications memory and the memory  that is allocated to a program is  typically  divided into these sections all the  local variables  and the information about function call  executions goes into  the stack so let us run through this  code let us simulate this code and see  what’s really happening in the memory  for each function call some part of the  memory from the stack  is allocated for its execution we call  this the stack frame of that method  or that function when the program starts  executing first  the main method is invoked so in the  stack frame  some memory will be allocated for main  function and all the local variables of  main function will live  inside this stack frame let’s say the  starting address of this stack frame is  100 and the end address of this stack  frame is  130 and we will have three local  variables created here  a b and pt are a and b are integers and  ptr is an  integer pointer let’s say is at address  100 b  is at address 112 and ptr is at address  120 i’m just making these assumptions  now when the main method will come at  this line will where it is calling  add function its execution will pause  and now memory will be allocated for the  execution of  add at any time whatever function is at  the top of stack  is executing main method will wait for  add function to complete and return so  here i should say a is equal to 2 b is  equal to 4  and now add comes here in the stack  let’s say add gets  memory from 130 to 160 and add also has  three local variables a b  and c a and b are pointers to integers  the value of a will be 100 and the value  of b  will be 112. let’s say their addresses  is  addresses are 130 140  and 144  once again these are just random  assumptions now c  is calculated as asterisk a plus  asterisk b  a is pointing to this location and b  is pointing to this location asterisk is  value at  address stored in a and asterisk b is  value at address stored in b so this c  will be  six here these two values will be added  now this add function will return the  address of its local variable c  which is 144 and finish its execution so  this ptr will be 144  and now the memory that is allocated to  add function  will be deallocated now this memory  above address 130  can be used for other function calls  and even though this variable pointer  ptr  stores the address 144 stores the  address of this particular block  it kind of points to this particular  block the data here is not guaranteed  because this memory has been deallocated  now we come here to this print hello  world and now  a memory from stack will be allocated  for print hello world  above this stack frame of main method  this is main  so let’s say that print hello world gets  this memory block  from address 130 to address 150.  now there is no local variable in this  print hello world function  but still function call execution  involves storage of some information so  now this section from 130 to 150  is for print hello world i’ll write phws  shortcut for print hello world  and it has been overwritten so this  block at 144  no more stores value six so when we come  here  at this print statement to print the  value  at this particular address we get some  garbage value now the obvious question  would be why did the  why did we get the right value when we  were not making a call to print hello  world  i would say that i just got lucky maybe  because i did not call any other  function  after making a call to add my machine  did not overwrite or erase the data at  that particular memory location  but when i made a call to print hello  world that memory got used  if you see we have passed the addresses  of these two variables a  and b of main to add function but that  is all right because  called function always comes above the  calling function in the stack so anytime  this called function is executing  calling function will be in the memory  so if add is executing  main is guaranteed to be in the memory  so addresses of variables in main will  be accessible to add  but if we try to return a local variable  from the called function  back to the calling function like if we  want to return a local variable from add  to main  then when that function finishes and the  control returns back to the calling  function  that memory has already been deallocated  so it is okay to pass something  from bottom to top in this call stack or  i should rather say that  it’s okay to pass a local variable the  address of a local variable  from bottom to top in this stack but it  is not okay to  return the address of a local variable  from top to bottom in the stack  in the call stack i hope this makes  sense so now the obvious question would  be what are the use cases in which  we may want to return pointers from  functions  well if we have address of some memory  block in the heap section or some memory  block in the global section  then we can safely return the address of  these blocks because  anything in the heap has to be  explicitly deallocated we control  its deallocation unlike stack and  anything which is in the global  section a global variable lives for the  entire lifetime of the program  i can use malloc or new operator in c  plus to get some memory on heap so if i  modify my code something like this  i will declare this c as a pointer to  integer  and get some space allocated on the  heap using a call to malloc  now malloc is a library function that  returns pointer  but it returns pointer to an address  which is on the heap  so we get a memory block and using this  pointer variable now  we can write this value asterisk a plus  asterisk  b at that particular memory block and  then we can return this address c  which is the same address that malloc  returned us  but we are safe now because we are  returning address of  a block which is on the heap and uh and  not on the stack  and this will work now now in this code  let’s say this call to malloc gives us  this block at address 500 in the heap  c now is only pointing to this block and  using c we have written this  data here this value 6 and now when add  finishes  the address returned by the add function  which is  address 500 is still valid and we still  have the data there  and it will not be deallocated anything  on the heap is explicitly has to be  explicitly deallocated  so while returning pointers from  functions we need to be careful about  the scope  we must be sure that the address is not  reused to store something else  or the data is not cleared from that  address in most cases we will be  returning pointers to memory that is  allocated on the heap  or memory that is in the global section  the global variable section  in our coming lessons one place where we  will be using  pointers as function returns in our code  is implementation of  linked list data structure so this was  pointers  as function returns thanks for watching  in this lesson we are going to talk  about function pointers  function pointers as the name suggests  are used to store address of functions  so far we have used pointers mostly as  variables that would store  address of other variables basically  pointers are data types that can be used  to  store the address of some data stored in  computers memory or in other words  to point to or refer to some data and it  doesn’t always have to be a variable  data could be stored as constant also  and we use pointers not just to store  the address  we can dereference and get the value at  whatever address the pointer is pointing  to  now we are saying that we can have  pointers that can store  address of functions or in other words  can point to functions  and we can use a pointer to function to  dereference  and execute the function and this is  really interesting  some basic questions would pop up what  really would be  the address of a function and even if we  can have pointers to functions  what are the use cases in which we may  want to have them  there are really interesting use cases  of function pointers but we will talk  about them later  let’s first try to understand the core  logic here  once again i have drawn this familiar  diagram the memory that is  allocated to an application or a program  can typically be divided into these four  segments  we have talked about this quite a bit in  our previous lessons  okay now a program is basically a set or  sequence of instructions  that you would give to the computer to  perform a task  we can write our program in a high level  language like c  or c plus plus but at lowest level in  its architecture  computer understands and executes only  binary  any instruction that has to be executed  by the computer has  to be encoded in binary of course there  will be some rules  for encoding so what we do is we  write our program or set of instructions  in a high level language like c  or c plus plus and we pass it to a  program  called compiler as input and  corresponding to  the source code compiler generates what  we call  machine code or executable code  which is instructions encoded in binary  something like what i’m trying to show  here compiler basically takes  one or more source files let’s say the  program that i have written here  is in a file named program.c  now a compiler for c language will take  this file as  input and create an executable file  that will have the machine code on a  windows machine executable file has  extension  exe an executable file will be stored in  disk drive  or some secondary storage device  whenever we say memory  just memory in context of programming we  mean  the random access memory or ram that we  also call the main memory  or primary storage so whatever  applications memory we are talking about  here will be  a chunk of main memory a program  or application gets a chunk of memory  only when it starts execution  when the application finishes execution  this memory is claimed  back what really happens is that when we  run a program when a program starts  execution  some amount of memory is allocated to it  and that is what we are calling  applications memory here the code or  text segment of applications memory  is basically the machine code or  instructions  copied from the executable file  instructions are not executed directly  from secondary storage  therefore they’re first copied to main  memory  and then only they can be executed  during program execution we need memory  not just to store  instructions to be executed but also to  store  a lot of data that we would work upon  in a program these other segments are  mostly about  storing and managing data what i’m going  to do now is i’m going to zoom in to the  code or text  segment let’s assume that each  instruction in machine language takes  4 bytes i’m trying to show the section  of memory storing the instructions here  each partition here is a block of 4  bytes and address is increasing from top  to bottom  so we have instruction 0 at address 200  and the next instruction is at address  204  and the next is at 208 and so on  instructions in a program are executed  sequentially  only exception will be when instruction  itself will say that hey  go to or jump to this other instruction  at this particular address which will  happen in case of  function calls for example if  instruction 0 1 at address 200 is  currently executing  by default the next instruction to be  executed  is instruction 0 2 at address 204  unless instruction 01 itself is  something like  go to instruction 05 at address 216  which will happen in case of function  calls a function  is nothing but a set of instructions  stored in one contiguous block of memory  let’s say this block containing  instructions five till  8 is a function i’ll name this function  fu and c1 basically a function is a set  of instructions to perform a subtask  in memory a function will be one  contiguous block  with some instructions the address of a  function what we also call  entry point of a function will be the  address of the first  instruction in the function in this  example here  address of function 1 is 216.  a function call in machine language will  basically be an instruction  to jump to entry point of some function  to jump to first instruction in a  function  now we will not go any deeper into  architecture now this is good enough to  understand function pointers  when we say function pointers store  address of functions  we basically mean that function pointers  stored  the starting address or entry point  of the block of memory containing all  the instructions in a function  let’s now see how we can create and use  function pointers in a c  or c plus program i am going to write a  simple c  program here the first thing that i’m  going to do is i’m going to write a  function  named add that will take two integers as  argument  and return the sum of these two integers  and now i’m going to create a function  pointer that should point to this  function  add the syntax to create function  pointer is  first type in the return type of the  function to which this pointer will  point  add will return int so i typed in int  then after space within parenthesis type  in  asterix and then name of the variable  so i’m creating a pointer named p and  now  once again within parenthesis type in  all the argument types of the function  to which this pointer will point  argument types and function declaration  should be  exactly same as in the function to which  this pointer will point  because both the arguments in add  function are int  we have two ends in the declaration of  function pointer also to initialize  function pointer and fill in the address  of a function we can  use a statement like this as we know  ampersand operator gives us the address  of something  the statement p equal ampersand add  will fill in the address of add in p  so p now points to add and using  p we can execute this function add what  i’m going to do here is i’m going to  declare  an integer variable named c and now  i’m going to write a statement like this  what i’ve done here is  first i have used the asterisk operator  to dereference and get the function  and then i have passed arguments  just like i would do with a function  name so i’ve passed two integers two and  three  and if everything is all right the  output of this printf statement here  should be integer value 5. when i run  the program this is what i get  so this is really cool we just used a  function pointer to refer to a function  and then execute the function one thing  about the syntax of function pointer  declaration  we are putting the identifier or name of  the pointer within this  parenthesis if we would not use the  parenthesis  then it will mean that we are declaring  a function that will return pointer to  integer in this case  if i would write something like this i  would write a declaration  something like this then this is  declaring a function that would return  pointer to integer we can have an  asterisk just before the function  name or we can have an asterisk just  after int  these two syntax are same but if i would  put this  within parenthesis then this is  declaring a function pointer  okay few more things in this  initialization here we are using this  ampersand operator  even if we do not use this ampersand  operator  it will mean the same just using the  function name will also return us  address of the function or in other  words an appropriate pointer  to data friends instead of using this  parenthesis  and asterisk operator with function  pointer name we can simply use  the function pointer name and this is  good enough  so we can use function pointer name or  identifier just like function name  as you can see the output here is as  expected  so we have two possible syntax for both  referencing and data referencing  you can use whichever you like the  second one is more famous  one final thing to be able to point to a  function  type of the function pointer must be  appropriate so  in this declaration of p here if i would  change  it something like this then this  function pointer is  meant to point to a function that should  take two integers as argument  and should return void add function  is returning int so p cannot point to  add this will give me compilation error  once again if i will change the  declaration something like this if i  will have only one argument in the  declaration  of function pointer then p cannot point  to add  okay now let’s use some more functions  with different signatures  and try to execute them through function  pointers i am writing this function  print hello  it will simply print hello on screen we  will have to declare  a function pointer like this  and then we can initialize the pointer  and fill in the address of this function  and now we can execute the function  through the pointer  let’s see what the output is this looks  all right  now let’s say we want to say hello to  someone  and i’ll change the signature of print  hello to take a string as argument  the declaration of a function pointer  will also change  and while calling we will have to pass a  string  upon running this program this is what i  get and this is also looking fine  so this is pretty much how we can create  and use function  pointers in c or c plus function  pointers are used in a program in  interesting scenarios they have  interesting use cases  we will talk about the use cases in next  lesson this is it for this lesson  thanks for watching in our previous  lesson we saw what function pointers are  and then we wrote a simple program to  understand how we can  create function pointers in a c or c  plus  program but we did not discuss the real  use cases  of function pointers the real scenarios  where function pointers can be useful  so in this lesson we are going to talk  about the use cases of function pointers  all the use cases of function pointers  are around this concept  that function pointers can be passed as  arguments to functions and then a  function that would receive a function  pointer as  argument can call back the function  that this pointer will point to to  explain this better i will have to write  some code  first of all i am going to write a  simple function named  a this function takes no argument  but it turns void and simply prints  hello  on screen now i will write another  function  named p this function takes a function  pointer as argument  ptr should point to a function that  should take no argument  and should return void a function like  a now in b i will simply use this  function pointer ptr  to call whatever function it’s pointing  to  or in other words i can say that i will  call back  the function pass to me or given to me  through ptr  in the main function i will declare a  function pointer  and this function pointer should also  point to a function  that should take no argument and should  return void i will initialize this  function pointer p with address of  a and now i will call this function b  passing it this function pointer p let’s  run this program and see what happens  hello is getting printed on screen so  basically function a  is getting executed a is getting  executed through this callback  in the main function instead of writing  these two statements i can simply write  a statement like this and this should be  good enough because  name of a function we had discussed this  earlier also  returns a pointer so this one statement  is same as previous two statements  when reference to a function is passed  to another function  then that particular function is called  a callback function so  a is a callback function here it can be  called  back by b through the reference through  the function pointer  this statement where we are calling the  function through function pointer is  a callback we are still not doing  something very meaningful here  what’s the point in calling a indirectly  through b  in this code this is not making much  sense  so let’s now look at a scenario where  using a function pointer and callback  can make our life easier i have a simple  scenario  i have a list of integers in an array  and i want to sort this list  in increasing order of the value of  integers  to do so i will write my own sort  function  i am writing a function named sort that  will take an array  and number of elements in the array  the function will take an integer array  here i can  write a and then brackets or  i can write asterisk a these two are  alternate syntax  i will use simple bubble sort algorithm  i have renamed this function as bubble  sort  in bubble sort we make multiple passes  on an array  and in each pass as we go from left to  right as we go from lower indices to  higher indices  we compare adjacent elements and if the  element at lower index  is greater than the element at higher  index while comparing adjacent elements  then we swap the elements this inner  loop  is a pass on array and  this outer loop is basically saying that  we will make n passes  after first pass the largest element in  the list  will bubble up to the highest index  and in the next pass the second largest  will bubble up to its appropriate  position  this will go on and it finally in n  passes  the complete list will be sorted if you  want to refresh bubble sort  there is a link to my code school’s  lesson on bubble sort in the description  of this video  in the main function i have called  bubble sort function passing it  array a and then i’m printing all the  elements in a and hopefully element  should be printed in  increasing order the output is as  expected we have a sorted list  here okay now let’s say i want to sort  my list in decreasing order of the value  of integers  so what change should go in my code here  think about it  the only change will be in this  comparison logic  in this if statement while comparing the  adjacent elements now i will say that  if the element in left is smaller if the  element at lower index is smaller  then swap or basically then push it  towards  higher index comparing adjacent elements  and swapping  is basically pushing smallest or largest  element  towards higher indices with this  condition  with this comparison we are pushing the  smaller  number towards higher index let’s see  the output now  as you can see i’m getting the numbers  in decreasing order now my list is  sorted  in decreasing order of the value of  integers  now let’s say i have a requirement like  this  sometimes in my program i want to sort a  list of integers  in increasing order and sometimes i want  to sort  a list in decreasing order of the value  of integers  so what all can i do think about it one  thing that i can do is i can write  two sort functions the first sort  function to sort  in increasing order and another sort  function to sort in decreasing order  but if we will do so there will be a lot  of duplicate code  the two functions will be same except  just one character this less than sign  or greater than sign  writing duplicate code has a lot of  disadvantages  so can we do something better another  thing that we can do is we can pass  one more parameter to the sort function  to say whether we want the list sorted  in  increasing order or decreasing order we  can have a flag  let’s say when flag is 1 we will sort in  increasing order and  when flag is zero we will sort in  decreasing order  using this approach we can avoid writing  a lot of duplicate code  what i’m going to do is i’m going to use  a function pointer  sorting of a list is always done on  basis of some ranking mechanism  so based on some property we should be  able to compare elements and say that  this should come first and this should  come later the core logic in sorting  will always be the same  only the ranking mechanism or comparison  logic will change  what i’m going to do is i’m going to  decide which element  is greater in rank and which element is  lesser  through a function basically i will  perform this comparison through a  function  my function will take a function pointer  as argument  my sort function will take function  pointer as argument  the callback function or the function  that this pointer should point to  must take two integers as argument  it should compare the two integers and  then it should  return back an integer it should return  1 if first element has higher rank  0 if the elements are equal and minus 1  if second element or second argument  has higher rank and let’s say the  element that has higher rank  will go towards the end in sorted array  towards higher indices  these are my assumptions while designing  this sort function  now i am going to use my callback  function for comparison  if aj and aj plus 1 are now passed as  arguments to this callback function  and we get 1 so this condition will be  true  we will swap in this condition because  aj will have to be higher in rank  for this comparison function to return  one  so we will try to push aj towards higher  indices  let’s now try to use this particular  implementation of bubble sort  i will have to write a callback function  first i have written a function like  this  now in main i can just use the name of  this function that will  return me a function pointer and pass it  in this call to bubble sort in this  comparison function  i have not written a statement to return  0 if elements are equal  equality doesn’t matter in the logic so  for equality also i will  return -1 let’s first  run this program and see the output this  is what i’m getting the numbers are  sorted in  increasing order now i will change the  comparison logic a bit  i will return minus 1 if a is greater  than b  so basically i have changed the ranking  mechanism  the element with lower value is now  ranked higher  and will go towards the end of the array  this is what i’m getting upon running  the program  the array is now sorted in decreasing  order of the value of integers  this is a really good design because now  our sort function can sort  a list of integers based on any ranking  mechanism  we can have one callback function for  each ranking mechanism  i will take one more example let’s say  we have a list of integers with  both positive and negative values in it  i have modified a here a now has both  positive and  negative values this time i want to sort  this  array a in increasing order of the  absolute value of integers  so the negative sign will not matter we  will just take  a mod and then compare this  array a upon sorting should rearrange  like  this to be able to sort i will have to  write a comparison function  last time we had modified the same  compare function  but actually we should be writing one  comparison function for each sorting  scenario  so i will write a new function this time  i will write a function name  named absolute compare i have included a  reference to math.h library and i will  use  abs function from this library that will  give me absolute value of an integer  if absolute value of a is greater than  absolute value of  b then it’s ranked higher i should  return one  else i should return minus one let’s now  use this function to sort this  array i have a minor spell error here  okay instead of passing this compare  function i will now pass  absolute compare in this call to bubble  sort  this basically is passing a pointer to  absolute compare function  let’s now run this program and see what  happens this is what i’m getting the  elements are sorted  in increasing order of their absolute  values the bubble sort function here  can take only an array of integers  but we have a library function that can  take  any array so it’s further generic  this library function is in std  lib dot h library and it’s named  q sort q sort for quick sort and to this  function you should pass  an array and it can be any array it can  be an array of integers or it can be  an array of characters or even a complex  data type  a structure first argument will be the  array second argument will be number of  elements in array  third argument will be size of the data  type  so if this is an array of integers i  need to pass  size of int size of data type in bytes  size of function gifs size of any data  type in  bytes last argument should be a function  pointer a pointer to compare  comparison function signature of the  comparison function should be like this  it should take two constant void  pointers as argument  and return an integer why word pointers  void pointers are generic pointers we  can type cast  them to a pointer of any data type  this is the specification of queue sort  function it should be passed a pointer  to such a function  so it will be able to call it back let’s  write the comparison function  you can think of this as a reference of  first element  passed as a void pointer to get the  element  if it’s a list of integers i’ll first  have to  type cast the void pointer to endpointer  and then i’ll have to use the asterix  operator  to dereference and get the value we will  do the same to get the value of  second element this function must return  any positive integer if a is ranked  higher  a negative integer if a is ranked lower  and 0 if both are ranked same we can  simply  return a minus b and it will mean the  same if  a is higher in value a minus b will be  positive  and i’m trying to create a simple  comparison function here  that would rank an integer with higher  value as high so basically  this comparison function can be used to  sort the array in  increasing order of value of integers so  like i said returning positive value  means  a is ranked higher returning negative  value means  b is ranked higher with this comparison  function if i would simply pass this to  q sort and after the call to queue sort  print the value  in this array this is what i will get  as you can see the list is sorted in  increasing order of the value of  integers  if i will change this comparison  function to return b minus a  so element with lesser value integer  with lesser value  will be ranked higher the list will be  sorted in decreasing order of the value  of integers  and if i will use abstract absolute  value of a minus absolute value of b  this is what i will get remember in this  comparison function  the two elements to be compared are  being passed  through reference their addresses are  being passed  through a pointer the const keyword here  means  you cannot modify the address in this  pointer variable  we are having to use void pointer  because of generic design of q sort  function  remember q sort can sort any array not  just  an integer array it’s just that you will  have to give the comparison logic  okay so we just discussed one of the use  cases of function  pointers this whole idea of call back  is used in a lot of interesting design  scenarios  one more thing where this concept of  callback makes our  life easier is something called event  handling  if you are curious you can check the  description of this video  for some resources on event handling  this is  it for this lesson thanks for watching  in our previous lessons we have learnt  the concept of dynamic memory allocation  we have understood what is stack and  what is heap  in applications memory now in this  lesson we are going to talk about one  situation which is  caused by improper use of dynamic memory  or the memory on the heap and this  situation is memory leak  a quick recap of some of the concepts  that we have discussed in our previous  lessons  the memory that is allocated for the  execution of an  of a program or what we can also call  applications memory is typically  divided into these four segments or  these four sections  one section stores the instructions in  the program  that need to be executed this section is  called the code segment or the text  segment another section is used to store  the global variables the variables that  are not  declared inside functions and have  lifetime of the whole application  another section of the memory is used to  execute the function calls  and store all the local variables this  section is called stack  the size of these three segments the  code segment the global variable segment  and the stack segment  are fixed and decided when the program  is compiling  that is at the compile time and the  fourth section  which is called heap or dynamic memory  does not have a fixed size heap can grow  as per our need as we know we get memory  from the heap  by making a call to malloc function in c  and when we are done using that memory  on the heap we  make a call to the free function to  deallocate or free that particular  memory  in c plus apart from malloc and free we  can also use  the operator new to get some memory and  the operator delete  to free that memory memory leak is a  situation when we  get some memory on the heap and do not  free  it when we are done using it so our  application  is actually holding on to some unused  memory on the heap  but why do we call this situation memory  leak and why does it happen  due to improper use of dynamic memory  only  due to improper use of heap only and not  some other sections of applications  memory  we will try to understand this through  one simple program so what i’ll do is  i’ll write one simple program and show  the simulation of its execution in the  memory  to explain these concepts in my c  program here i’m going to write a very  simple betting game  and the game is that we have three  positions and three cards  jack queen and king initially jack is at  the first position  queen is at the second position and king  is at the third position  and then computer shuffles these cards  so that the positions of these cards  is changed is randomized and now the  player has to guess the position  of the queen he has to bet some amount  of money let’s say it’s virtual cash  and if he wins if he predicts the  position if he guesses the position of  queen correctly  he takes away three times the amount  that he had bet  and if he loses he simply loses the bet  amount  let’s say the player initially has 100  of virtual cash  and he can play as many times as he  wants  until he runs out of cash so let us now  implement this game  the first thing that i want to do is i  want to declare a global variable  named cash that at any point will store  the  virtual cash available with the player  initially he has  100 of virtual cash and then in the main  method i will declare a variable named  bet and i will write code something like  this  while cash is greater than zero while  player still has some cash  we will ask him to bet something and we  will take this  input in this variable bet using  scanf uh for negative scenarios like bet  equals zero or  bet being greater than the cache  available let’s say we will break out of  this loop we will end our game  for all other conditions let’s say we  will make a call to play function  and of course now we will have to write  the play function  we will be passing bet to the play  function so  that will be an argument and now in the  play function i will declare  a character array of size 3 and  initially  we will have the character j at the  first position to say that  there is a jack at the first position j  is for jack and similarly  q is for queen and k is for king and now  the computer must perform a randomized  shuffling so we will write a print  statement like this now we need to find  a logic to make a random shuffle of  cards  one such logic is that we can make a  call to random number generator function  in c  to use the random number generator first  we will make a call to s  rand function and pass it an argument  something like this  i’ll come back to what i’m doing here in  s rand by making a call to strand  now let’s say we run a loop five times  and we will  choose any two random positions among 0  1  and 2 and swap the letters at these  positions in the array  let’s say these positions are x and y  now when we make a call to rand function  we will get a random number  but we want a number between 0 and 2 0  and 2 included  so we will take a modulo by 3 so that we  either get 0  or 1 or 2. so we will take two such  random positions  with statements like this and now  what we can do is we can swap the  characters at these positions  so we will use a temporary variable  first we will store the character at  position  x in temp and then we will do  something like this i’m short of space  here so i’m writing three  statements in the same line okay so now  the swapping is done  so we are swapping or shuffling  uh characters at two positions five  times each time we are picking up two  positions  x and y randomly by making call to rand  function and taking a modulo by 3  so this will guarantee us that x and y  is between 0  and 2 that will be valid positions  by making a call to rand function we  will get the  random numbers but we also use this s  rand once and pass this  time null the return of  time function in random number  generation  there is something there is one concept  of seeding  uh the random number generator so we are  passing seed to random number generator  we will not go into the details of  random number generation now  now what i’ll do in the play function is  i’ll have a variable  uh named players guess and  i’ll ask the player to guess the  position of queen  and then i will use scanf to take the  input  now if the player is correct then the  character at that particular position  in the character at a c and the position  will be  one minus what the player inputs  because the player is inputting one two  or three that will map to zero one and  two in the array  so if the character is queen he has one  so his overall cash will be incremented  by three times the bet amount  elsie has lost lost and his cash will be  decremented by the bit amount  so in the case of win we will write a  print statement like this  we will say that you have one and the  result is this and your total cash  right now is this remember cash is a  global variable  and we will print something similar if  the player loses  finally our play function is looking  something like this  and we have also moved this variable  cache at the top  in the main method i’ve added two more  print statements initially  now let’s now play this game and see  what happens what i have done  is i have compiled this code and created  an executable  named game.exe and now i’m going to run  that executable  so this is asking what’s your bet let’s  say we want to bet  five dollars on position one  and i lose my balance now is 95 dollars  let’s bet again this time again i lose  and i can go on playing so i’m losing  again and again  uh finally a win after long time uh i  can go on playing this game but i want  to show you something else  i have opened the task manager of  windows  and here as you can see this highlighted  row  is for game.exe the third column here is  the memory consumed by this  executable game.exe you will have to  see this in full screen now as i go on  playing  the memory consumption here the memory  that’s showing here  it’s not increasing it’s always 348k  now i’ll go ahead and make some changes  in my code what i’ll do here is  this particular character array that i’m  creating as a local variable in the play  function  right now it’s created as a local  variable  so it will go on the stack now i want to  create a character array on the heap  so what i’ll do is i’ll write statement  like this  i’ll declare a character pointer named c  and then i’ll use malloc to fetch memory  uh to store three character variables  in c plus plus we could have said  something like this we could have used  the new operator  and now i’ll set value at z  zeroth index as j one at index as q and  two with index as  k so we have created uh an array on the  heap and c is a pointer  to the base address of that array c is  still a local variable but now it is a  pointer to character and we can still  use it like array rest of the code will  just work fine let us run this code and  see what happens  i have opened the task manager and i’m  running the executable  watch for the memory consumption of  game.exe  i will make some bets  as you can see right now the memory  consumption is 348k  i just kept on playing and after some  time the memory consumption is 488k  it has shot up and if you will keep  playing this game further  after some time it will shoot up again  maybe after some time but it will shoot  up for sure  so why is it happening why was it not  shooting up when see  the character array was not on the stack  not on the heap and it was on the stack  let’s try to understand i have drawn  sections of applications memory here  and let us now see what really happens  in the memory  when we are playing our game as we know  from our previous lessons  all the information about function call  execution goes into  the stack section of the memory anytime  a function is called  some amount of memory from the stack is  allocated for its execution  when the program starts executing first  the main method is invoked or called  so let’s say some amount of memory is  allocated for the execution of  main this is what we call the stack  frame of the function  so this is stack frame of main and all  the local variables of main  will sit inside this stack frame in our  code we had a local variable named bet  so it will go here and we had a global  variable named cache  so initially let’s say main function is  executing  when we play our game main function  makes multiple calls to play function  what really happens when a function  makes call to another function is that  that particular function is paused and  memory is allocated for the execution of  the called function so main will pause  and play will start executing and play  will go on top of  main in the stack now we had a couple of  local variables in play all will go in  this stack frame  i x y players guess and  for the case one when we had the  character array c  on the stack itself so it was not  created using  a call to malloc the character array c  will also sit in this stack frame  now when the execution of play function  will finish control will return back to  main and the memory that was allocated  for the execution of play function will  be reclaimed  anytime a function call finishes the  memory that it is allocated on the stack  is reclaimed  so there is one stack frame  corresponding to each call  and as soon as that call finishes that  memory  is claimed back now main will make  another call to play because we will  play multiple rounds  so play will again come into the stack  and it will be cleared again when play  finishes  as you can see all the local variables  get cleared each time the function call  finishes  for anything on the stack we do not have  to worry about its d  allocation it happens automatically when  the function call finishes  now let’s talk about the second case  when character array is created on the  heap using a call to malloc function  once again we will make multiple calls  to play function now what will happen  this time  is that we will not create the array on  the stack  we will still have a variable named c a  local variable named c  but this variable will not be of type  character array of size 3.  this variable will be of type pointer to  character and we will make a call to  malloc function to create the array on  the heap  and this local variable which is a  pointer to character will only point to  this particular memory block  anything that is on the heap has to be  accessed through a pointer variable  so here we have created the array on the  heap and we have kept only a pointer  variable on the stack  now when the call to play function will  finish the memory  allocated for the execution of call to  play function  will be reclaimed so all the local  variables will go away  but this memory on the heap will lie  unused and unreferenced  and it will not get deallocated anything  on the heap has to be explicitly  deallocated by making a call to free  function  or by using delete operator and think  about it we will make multiple calls to  play function  as we play multiple rounds of our game  and  each time in each call to play we will  create one such memory block on the heap  that will lie unreferenced and unused  when call to play function will finish  if we will play our game hundred rounds  then we will have hundreds such  unreferenced and  unused memory blocks of three characters  in the heap  heap is not fixed in size and our  application can  claim can get more memory in the heap  section  as long as our system itself is not  running out of memory and if we are not  deallocating  this unused memory on the heap we are  depleting and  wasting memory which is an important  resource our application’s memory  consumption will only keep on growing  with time memory leaks are really nasty  bugs to have in your program  anything unused and unreferenced on the  heap is  garbage in c or c plus plus we have to  make sure as programmers  that garbage is not created on the heap  memory leak is nothing but growth of  garbage in the heap  in languages like java and c-sharp  garbage is automatically cleared from  the heap  so programmer does not have to worry  about freeing or deallocating the memory  on heap  which is a cool feature to have it  avoids memory leak  in this example we were creating an  array of three characters on the heap  what if we were creating an array of ten  thousand characters  and not freeing freeing the memory after  we were done using it  at the end of the function the memory  consumption would have shot up like  anything  coming back to my code here what i have  done is  i have created a character array of size  ten thousand  of ten thousand characters here uh my  logic would not change  i’ll just use first three positions in  the array  i’m just trying to show you something  and at the end of this particular  function when we are done using this  array  on the heap we are making a call to the  free function  passing it the address of this memory  block this rac  our program will just work like before  but let’s run this and monitor the  memory consumption once again  uh once again i’m showing you the task  manager and i’m playing the game  let’s make some bets now watch out the  memory consumption of game.exe  for however long you will play the game  the memory consumption won’t shoot up as  you can see it’s  356 k and it’s not shooting up for me  even after playing for a long time  and it is not shooting up because we had  used  free uh to deallocate  the memory when we were done using it at  the end of the function  remember we had created an array of size  10 000  and if we were not using free then the  memory would have  shot up like anything the memory  consumption would have shot up like  anything  but because we are freeing at the end of  the function it’s not going up there is  no memory leak so finally to summarize  it  memory leak is improper use of dynamic  memory or the heap section of memory  that causes the memory consumption of  our program  to increase over a period of time  remember memory leak always happens  because of unused and unreferenced  memory blocks in the heap  anything on the stack is deallocated  automatically and stack is always fixed  in size  at the most we can have an overflow in  stack  so this was memory leak in cc plus  thanks for watching  


Leave a Reply

Your email address will not be published. Required fields are marked *