WEBVTT

00:00:00.740 --> 00:00:03.650
I will start this lesson with a simple experiment.

00:00:04.040 --> 00:00:07.520
I declared an array with three integers, and I'm wondering

00:00:07.530 --> 00:00:10.790
what will be the output of this sizeof operator when I

00:00:10.790 --> 00:00:12.650
pass it the name of the array.

00:00:13.040 --> 00:00:16.550
Since we said that the name of the array works like a pointer,

00:00:16.560 --> 00:00:20.170
this should probably return 8, because on this system

00:00:20.170 --> 00:00:22.660
we need 8 bytes to store a pointer.

00:00:23.040 --> 00:00:27.150
However, as you can see, the result is not 8, it is 12.

00:00:27.540 --> 00:00:29.080
Like we mentioned before,

00:00:29.090 --> 00:00:33.010
array names can be used like pointers in certain situations,

00:00:33.010 --> 00:00:34.950
but this is not one of them.

00:00:35.340 --> 00:00:39.820
When you declare an array, C++ will add a little bit of magic,

00:00:39.830 --> 00:00:44.530
a little bit of syntactic sugar to it. Compiler will actually know that

00:00:44.530 --> 00:00:49.960
this name is assigned to an array and it will return 12 bytes, because

00:00:49.970 --> 00:00:52.760
that is the actual size of the whole array.

00:00:53.140 --> 00:00:58.150
Each integer needs 4 bytes, so 3 integers make an array of 12 bytes.

00:00:58.740 --> 00:01:02.210
This is the size of the array in memory, but you may have

00:01:02.210 --> 00:01:04.599
also noticed that in the previous lesson,

00:01:04.610 --> 00:01:08.720
I used the word size to refer to the number of elements.

00:01:08.720 --> 00:01:11.490
Terminology for this is not consistent,

00:01:11.490 --> 00:01:15.050
but I guess I could have said that the number of elements is the

00:01:15.050 --> 00:01:19.110
length of the array. But since I'm only going to use the sizeof

00:01:19.110 --> 00:01:21.610
operator with arrays in this lesson,

00:01:21.620 --> 00:01:24.760
I will keep referring to the array length as size.

00:01:25.140 --> 00:01:29.760
Now, let's say that I want to pass this array to a function as an argument.

00:01:30.140 --> 00:01:33.280
The name of the function will be printArray and the

00:01:33.280 --> 00:01:35.560
purpose of the function is obvious.

00:01:35.940 --> 00:01:40.140
The function will print the elements from the given array, but

00:01:40.140 --> 00:01:43.850
notice the syntax for using the array as a parameter.

00:01:44.240 --> 00:01:47.360
This is the correct way to do this and it will work.

00:01:47.740 --> 00:01:52.060
The parameter will accept the array of integers of any size,

00:01:52.440 --> 00:01:56.070
but we still need to know the size of the array, because we will need

00:01:56.070 --> 00:01:58.860
it to create a for loop inside of the function.

00:01:59.240 --> 00:02:02.910
Since this expression gives us the size of the whole array,

00:02:02.920 --> 00:02:08.259
maybe we can divide it by the size of one integer to get the number of elements.

00:02:08.840 --> 00:02:14.200
Let's try to compile this, and it works. Now, let's do the

00:02:14.200 --> 00:02:16.660
same thing from inside of the function.

00:02:17.840 --> 00:02:22.830
I will pass this parameter to the sizeof operator, compile

00:02:22.830 --> 00:02:27.490
this to make sure that it's still working, and it seems that

00:02:27.490 --> 00:02:32.160
it's not, because we get 2. But why?

00:02:33.140 --> 00:02:37.840
Also, it's hard not to notice this big warning message which says that the

00:02:37.840 --> 00:02:42.050
sizeof operator will return the sizeof a pointer to an integer.

00:02:42.440 --> 00:02:45.750
This is because of a somewhat dangerous and really common

00:02:45.750 --> 00:02:49.610
occurrence of something called a pointer decay. Whenever

00:02:49.610 --> 00:02:51.440
you pass an array to a function,

00:02:51.450 --> 00:02:54.610
the parameter that should accept the array will decay

00:02:54.610 --> 00:02:57.260
from an array to a simple pointer.

00:02:57.640 --> 00:03:01.050
This is known as decay because a little bit information

00:03:01.050 --> 00:03:03.940
has been lost. Inside of this function,

00:03:03.950 --> 00:03:07.920
the compiler no longer adds that syntactic sugar to our array

00:03:07.920 --> 00:03:10.660
that lets us get the size of all elements.

00:03:12.040 --> 00:03:15.110
So this is the same as defining this parameter as a

00:03:15.110 --> 00:03:17.050
simple pointer to an integer.

00:03:17.440 --> 00:03:21.480
The square bracket syntax is allowed because of programmers, so that we

00:03:21.480 --> 00:03:25.150
can be more explicit about our intentions in the code.

00:03:25.540 --> 00:03:27.050
If you use square brackets,

00:03:27.050 --> 00:03:30.680
compiler will figure out that your intention is to pass an

00:03:30.680 --> 00:03:34.690
array, so, that is why we got that big warning message that

00:03:34.690 --> 00:03:36.550
warns us about pointer decay.

00:03:36.940 --> 00:03:40.810
You can also use a simple pointer to pass an array, but

00:03:40.820 --> 00:03:42.660
only if you know what you're doing.

00:03:43.040 --> 00:03:46.410
So, using this sizeof operator to get the number of

00:03:46.410 --> 00:03:49.660
elements inside of a function is not possible.

00:03:50.040 --> 00:03:51.790
Whenever you want to pass an array,

00:03:51.800 --> 00:03:55.460
you also need to pass another argument which will inform the function

00:03:55.470 --> 00:03:58.560
about the number of elements inside of that array.

00:03:58.940 --> 00:04:02.340
I will continue referring to this as size, so that's

00:04:02.340 --> 00:04:04.060
how I will name the parameter.

00:04:04.440 --> 00:04:06.180
So now that we know the size,

00:04:06.180 --> 00:04:09.660
we can print all of the elements by looping through the array.

00:04:10.540 --> 00:04:13.920
I use the pointer arithmetic to do this, just like we

00:04:13.920 --> 00:04:16.360
learned in one of the previous lessons.

00:04:16.740 --> 00:04:17.390
However,

00:04:17.399 --> 00:04:21.990
if you know that this decayed pointer will always represent an array, you can

00:04:21.990 --> 00:04:25.560
use the square brackets operator just like you normally would.

00:04:25.940 --> 00:04:30.330
So, other than passing this size explicitly, everything else works in

00:04:30.330 --> 00:04:34.310
the same way. You could have also put the expected size here in the

00:04:34.310 --> 00:04:37.260
square brackets, but this wouldn't do anything.

00:04:37.270 --> 00:04:39.360
This would still be just a pointer.

00:04:39.740 --> 00:04:43.130
I also need to mention that you should not use this approach for

00:04:43.130 --> 00:04:47.890
calculating size, even in the main function, It is not reliable,

00:04:47.890 --> 00:04:50.180
and once we learn about dynamic arrays,

00:04:50.180 --> 00:04:53.860
you will see that this will only work with static arrays like this one.

00:04:54.240 --> 00:04:57.550
You should always personally keep track of the size and pass it

00:04:57.550 --> 00:05:00.750
to functions that require array arguments.

00:05:01.140 --> 00:05:04.760
Now, let's implement this new concept in our calculator.

00:05:06.140 --> 00:05:12.220
I will create a special function for each operation, sum function will add all

00:05:12.220 --> 00:05:16.960
of the elements, and multiply will, of course, multiply them.

00:05:17.340 --> 00:05:22.160
The first argument is the array of numbers, and the second one is the

00:05:22.160 --> 00:05:27.210
size of the array, just like we learned. The function logic is the same

00:05:27.210 --> 00:05:32.170
as before, we just need to define the result in each function and then

00:05:32.170 --> 00:05:33.760
print it out to the terminal.

00:05:34.740 --> 00:05:38.350
Now I can remove the result variable from the main function

00:05:38.360 --> 00:05:41.360
and delete the logic from every case.

00:05:41.740 --> 00:05:43.360
We don't need this anymore.

00:05:44.140 --> 00:05:48.520
Instead, I will just call our two new functions and pass

00:05:48.520 --> 00:05:51.360
them the numbers array and its size.

00:05:52.240 --> 00:05:55.840
This will make our main function more readable, but we will

00:05:55.840 --> 00:05:58.560
continue to optimize it in the next lesson.
