Welcome.
Now, let's take a look at an example in the coding editor.
Now, I'm going to declare an int pointer variable. As you can see, I just need to type a star before
the int type.
This is what makes it an int pointer type. The zero value of a pointer is nil.
Let me show you.
I'm going to check whether it is nil or not,
by comparing it to nil. If so, I'm going to print its address like so.
P is nil, and its address is Person p, new line. You need to use %p verb here to print a memory address
of the P variable. As you can see it says the pointer is nil and its address is zero.
So far, you've seen the memory addresses as bare integer numbers. But normally, memory addresses are represented
with hex numbers. It's because the addressable memory space is very large so it is easier to represent
them with fewer digits.
Let's store an address of a variable in this pointer variable. To do that,
I'm going to declare an int variable because P is an int pointer.
OK, now I'm going to assign the counter's address to the variable P. By the way,
you can check whether an address is equal to another one.
For example let me compare the pointer variable with the counter's address. If they are equal, let's print
a message with their addresses. Person p equals Person p new line and I'm going to pass the pointer
variable p and the address of the counter variable as you can see it doesn't print the pointer is nil
message anymore because the pointer P variable is not nil now it contains the address of the counter.
Here it says both addresses are the same.
This means that variable p points to the counter variable's address.
Okay I'm going to remove these messages and let me set the counter to 100,
as an example. Now I'm going to print the value and address of the counter variable like so. I'm going
to pass the counter variable and the address of the counter variable.
Let me also print the pointer variable first.
I'm going to print the memory address that it points to. So I can simply say P.
Then I'm going to print its address using the address operator like so.
As I said, a pointer variable also has an address because it's a variable.
Lastly, I'm going to print the value that it points to like so. As you can see, there are three values that
you can get from a pointer variable. Where the pointer variable points. The pointer variable's memory address.
And the actual value of the variable that the pointer variable points to.
This is the counter's address, and this is where the pointer points to.
As you can see, they are equal because the "P" pointer points to the counter.
Also notice that, indirection operator returns 100.
This is the value of the counter variable.
And lastly, let's take a look at the memory address of the pointer variable. The pointer variable is stored
in this memory address.
Now let's introduce another int variable like so. Down below,
I'm going to set its value through the pointer like so.
Let me also print it.
As you can see the address of the variable v is different than the counter variable('s address). It's because they
are different variables.
Right now, the value of the variable "V" is the same as the counter variable. Let me print a
header here to separate the messages that I'm going to print. Okay. Now I'm going to change the counter
variable to 10.
Like so.
Let me also copy and paste the messages from above.
As you can see only the counter changes but the V variable holds the counters previous value.
This happens because there are two different variables.
Let me print another header here.
Now I'm going to show you what happens when you pass a variable to a function without using a pointer.
Let me also print the counter.
Now let's go ahead and declare the passVal function. It takes an int value, inside I'm going to set "n"
to 50, and I'm going to print the value and address of the n variable.
All right.
Ready. As you can see, only the n changes but the counter stays the same.
Let's take a look at the address of the variable n. It is different than the counter's address.
This means that there are different variables.
That is why the counter doesn't change when I change the variable n.
As you will see that is why I need to return the local variables of a function.
Now I'm going to return the local variable n to the caller like so. Right above, in the main function,
I'm going to assign the returned value to the counter like this.
Now the values of counter and n variables are the same.
Let me add another header here.
Now I'm going to show you what happens when you send a pointer to a function.
I'm going to send the address of counter to the pastPtrVal
function, like so. Ptr is short for a pointer by the way.
Let me also print the counter.
OK let's go down and declare the function there.
Here I'm going to declare an int pointer parameter like so. Remember when you type a star before a type it
becomes a pointer type.
So please do not confuse this with the indirection operator OK.
Inside I'm going to print the input parameter pn. Here,
I'm going to print the value of pn,
this is what it stores. And I'm going to print its address.
This is where the pn lives in memory.
And lastly, I'm going to print the value that it points to.
This will be the counter variable's value. Let me duplicate it. Between them
I'm going to use the indirection operator to get the counter's value then I'm going to increment the
counter like so. By the way, I don't need to type the parentheses here.
Go automatically does that for us. As you can see the address of pn is different than the previous variables
that you have seen above. pn is a different variable.
This means that whenever a function runs it creates a set of new variables that is local to that function.
Now let's take a look at the value of pn.
It points to the counter's address.
The interesting thing here is that the counter variable doesn't belong to the pastPtrVal function.
But it can still see the counter's address.
This means that the pastPtrVal function can change the counter value using the pointer as well. So a
function can change a value indirectly using a pointer.
Actually this is exactly what happens here.
At first, pn returns the counter's value as 50. Then inside the function, I increment the counter
through the pointer. In the end, pn says that the counter is 51 and it is right.
Doing so changes the main function's counter variable. It's because both functions work on the same variable,
through the pointer. Let me tell you one last thing. Pointers are copied too.
So every time a program calls a function, Go creates a new pointer variable.
For example let's say whenever this function pulses please assume that the program calls it with the
address of the counter variable.
Here is the first call to the function.
As you can see it creates a new pointer variable.
Here is the second call so it creates another pointer variable.
Both of these pointer variables point to the same memory location.
It's because the program passes the address of the counter to the function so it copies the address
into a new int pointer variable.
Of course, when the function returns the runtime will delete the allocated pointer variables from memory
automatically.
Let's say the first call to the function returns.
Here goes the first one and the second function returns,
the other one will be collected as well.
However, when you return pointer variables from a function the runtime won't clean them up.
It will clean them up only when they are not being used anymore.
Let me call the pastPtrVal function a few times.
These are the addresses of pointer variables inside the pastPtrVal
function. As you can see, each time I call it, it prints a different address.
It's because it's a pointer variable (pn). Although all of these pointer variables point to the same memory
location, their addresses are different.
For example, if I set the pointer variable to nil here, it won't affect the caller.
As you can see the output is the same.
It's because here I am only setting the local pointer valuable to nil which is a copy all right.
This was why you might want to use pointers.
It's because they can work across functions or even across packages.
There is only a single memory so every function can see it. If you share an address with a function,
it can retrieve and change the value that is stored in that address.
This is also why pointers can be dangerous because any part of the code can change any value,
if they can get their addresses. However, Go is not that dangerous as the other languages that support
pointers because Go automatically manages the memory.
Alright that's all for now.
See you in the next lecture.