WEBVTT 0 00:00.810 --> 00:02.080 Welcome back. 1 00:02.100 --> 00:06.450 You've learned what happens when a method receives a value. 2 00:06.450 --> 00:09.780 But what happens when it receives a pointer instead. 3 00:13.200 --> 00:17.840 First of all I'm going to reorganize this code a little bit more. 4 00:18.000 --> 00:25.080 I'm going to group and put each variable on a single line so I can show you more code without scrolling 5 00:25.200 --> 00:30.570 up and down OK better before talking about pointer receivers. 6 00:30.750 --> 00:32.780 Let's take a look at an example. 7 00:32.850 --> 00:40.350 As you can see you can run methods using a value for example you can print a book value using the print 8 00:40.350 --> 00:41.740 method here. 9 00:41.790 --> 00:46.770 Go automatically passes the book value to the print method. 10 00:46.770 --> 00:52.900 There is one more way to run a method since a method belongs to a type. 11 00:52.920 --> 00:55.830 You can also run it using its type. 12 00:55.830 --> 01:00.470 Remember game is not a value but a type. Voila! 13 01:00.600 --> 01:02.970 The print method is here. 14 01:02.970 --> 01:04.640 Let's run it. 15 01:04.690 --> 01:05.460 Hold on. 16 01:05.470 --> 01:12.870 It doesn't work because now the print method doesn't know which game value that it should use. 17 01:12.880 --> 01:21.280 When you run a method to using a type you need to send a value of that type to the method as the first 18 01:21.370 --> 01:22.250 argument. 19 01:22.300 --> 01:28.840 For example I can say use minecraft or I can say use Tetris. 20 01:28.840 --> 01:33.360 Let's run the print method through the book type with a book value. 21 01:33.490 --> 01:36.690 I'm going to say use Moby Dick. 22 01:36.760 --> 01:42.010 You run a method through a type it is called a method expression. 23 01:42.010 --> 01:45.220 So these are called Method expressions. 24 01:45.400 --> 01:49.320 Anyway let's try it it works. 25 01:49.390 --> 01:58.060 But why does it work? To understand that you need to learn how a method really works behind the scenes 26 01:58.370 --> 02:02.770 and method exactly looks and works like a function. 27 02:02.770 --> 02:10.680 For example the print method looks like this as you can see receivers are not magical entities. 28 02:10.990 --> 02:18.100 So you can run the print method on a book value like so you don't usually see this happening but behind 29 02:18.100 --> 02:20.580 the scenes go automatically passes 30 02:20.590 --> 02:28.480 Moby Dick variable to the method as the first argument or you can also manually sent the receiver value 31 02:28.570 --> 02:36.250 using the book type as you can see in this case you need to provide the book value as an argument by 32 02:36.250 --> 02:37.190 yourself. 33 02:37.330 --> 02:44.530 Therefore in both cases the printing method receives a copy of Moby Dick. 34 02:44.530 --> 02:52.840 You can run a method either way but we usually run it using a value I explained you this because 35 02:52.990 --> 03:01.870 I want you to deeply understand how a method really works in summary a method is a function that takes 36 03:01.870 --> 03:04.360 a receiver as the first argument. 37 03:04.480 --> 03:11.440 Technically there is only one difference between a method and a function. A method belongs to a type. 38 03:11.950 --> 03:20.570 However a function belongs to a package now that you understand what a method really is. 39 03:20.580 --> 03:22.280 I can remove this code. 40 03:22.880 --> 03:26.690 OK now we can talk about pointer receivers. 41 03:26.970 --> 03:31.500 Let's say you want to make a discount on game prices. 42 03:31.650 --> 03:35.680 To do that I'm going to add a discount method to the game type. 43 03:35.760 --> 03:44.520 It takes a discount ratio let's discount the game price like so as you can see I can use the game value 44 03:44.580 --> 03:48.560 inside the method because I've got it as a receiver. 45 03:48.570 --> 03:53.030 OK let's go to the main function and use the discount method there. 46 03:53.280 --> 03:57.910 Here I'm going to discount the Minecraft by 50 percent. 47 03:57.990 --> 03:59.850 Let's run it. 48 04:00.030 --> 04:01.850 Let's check out the Minecraft. 49 04:01.860 --> 04:04.170 The price hasn't changed. 50 04:04.170 --> 04:07.370 It is still 20 dollars not 10 dollars. 51 04:07.380 --> 04:09.240 Let's see what's going on. 52 04:09.270 --> 04:13.520 Let's go back to the game type here. 53 04:13.550 --> 04:18.740 We assume that we can access to the minecraft variable through the receiver. 54 04:19.280 --> 04:27.930 So let's print it and understand what's going on let's run it after 50 percent discount the game price 55 04:27.960 --> 04:29.720 becomes 10 dollars. 56 04:29.760 --> 04:33.340 However the discount is only applied here. 57 04:33.420 --> 04:39.560 It's because the receiver is a copy of the original Minecraft variable. 58 04:39.560 --> 04:42.130 Let me remove the debugging code from here. 59 04:45.560 --> 04:48.900 This is the discount method we wrote earlier. 60 04:48.950 --> 04:57.890 It has a value receiver let's run it using the Minecraft the Minecraft becomes a receiver in the discount 61 04:57.890 --> 04:59.050 method. 62 04:59.060 --> 05:01.280 The problem is that the variable G. 63 05:01.280 --> 05:02.870 Here is a copy. 64 05:03.470 --> 05:12.320 So changing the price of the copy won't change the price of the original Minecraft variable here is 65 05:12.320 --> 05:13.100 a quick question. 66 05:14.470 --> 05:21.870 What would you do if you want to change an input parameter inside a function you would use a pointer. 67 05:21.870 --> 05:22.710 Right? 68 05:22.770 --> 05:25.570 You learned that a method is just a function. 69 05:25.650 --> 05:31.490 Therefore I can fix the problem by changing the receiver type to a pointer. 70 05:31.650 --> 05:34.440 Let's rerun the discount method. 71 05:34.890 --> 05:42.870 Now the receiver is a pointer to the original Minecraft so the receiver variable G becomes a pointer 72 05:42.900 --> 05:51.970 to Minecraft changing the price field of the receiver will change the original Minecraft variable as 73 05:51.970 --> 05:53.860 well. 74 05:54.080 --> 06:03.880 Okay let's start by changing the discount method to a pointer receiver as you can see G is a pointer 75 06:04.000 --> 06:06.110 to a game value now. 76 06:06.250 --> 06:10.930 Okay let's try it nice now it works. 77 06:12.900 --> 06:20.140 But I didn't send a pointer to the discount method. So, how could it change the original Minecraft? 78 06:20.220 --> 06:22.920 How could it receive a pointer? 79 06:22.920 --> 06:24.260 Let me explain. 80 06:24.270 --> 06:31.950 Here Go sees that the discount method has a pointer receiver so it automatically takes the address 81 06:32.010 --> 06:36.930 of the Minecraft variable like so let me run it. 82 06:36.930 --> 06:44.700 So this is what happens behind the scenes when a method has a pointer receiver Go takes its address 83 06:44.790 --> 06:46.330 automatically. 84 06:46.350 --> 06:47.510 Let me take it back. 85 06:48.400 --> 06:51.350 Let me tell you one more thing here. 86 06:51.580 --> 06:59.310 When one of the methods takes a pointer a receiver it is better to convert all the methods to pointer 87 06:59.320 --> 07:00.610 receivers. 88 07:00.610 --> 07:05.030 It doesn't matter whether they need to change the original value or not. 89 07:05.190 --> 07:08.290 You will see why this is necessary to do so. 90 07:08.290 --> 07:15.250 When I talk about interfaces later in this section. So I'm going to change the print method to a pointer 91 07:15.250 --> 07:16.390 receiver as well. 92 07:19.900 --> 07:21.100 for the book type. 93 07:21.130 --> 07:27.520 You don't need to do anything else it doesn't change the book value so the print method doesn't have 94 07:27.520 --> 07:30.040 to be a pointer receiver. 95 07:30.040 --> 07:33.730 There is one more reason for using a pointer receiver. 96 07:33.760 --> 07:42.390 You learned that a method with a value receiver always copy is the receiver when it executes let me show 97 07:42.390 --> 07:46.320 you what happens when you receive a large value. 98 07:46.470 --> 07:48.690 First I'm going to create a new file 99 07:51.800 --> 07:54.760 and I'm going to create a new struct here. 100 07:55.070 --> 08:06.180 It will hold an array with 10 million games this data roughly corresponds to 200 megabytes let's create 101 08:06.240 --> 08:10.170 a method that gives us the address of the receiver. 102 08:10.200 --> 08:15.490 I'm just gonna print the address of the receiver. 103 08:15.530 --> 08:18.640 Let's go back to the main function here. 104 08:18.650 --> 08:25.490 I'm going to create a variable of the huge type this variable occupies around two hundred megabytes 105 08:25.490 --> 08:26.810 of memory. 106 08:26.810 --> 08:32.630 Now I'm going to make the situation more difficult by calling the addr method 10 times 107 08:36.400 --> 08:37.960 let's try it. 108 08:37.990 --> 08:45.580 I don't know whether it exists on your operating system but there is a program called the time it returns 109 08:45.580 --> 08:48.330 the total execution time of a command. 110 08:48.790 --> 08:55.880 So I'm going to run the program with the time tool. As you can see it is very slow. 111 08:55.880 --> 08:58.050 It takes seconds. 112 08:58.100 --> 09:05.060 Also note that each time I call the addr method it copies the h variable. 113 09:05.060 --> 09:11.120 Remember a method with a value receiver copies the received value. 114 09:11.120 --> 09:19.610 That's why the receiver's memory address changes 200 megabytes of data are being copied each time I call 115 09:19.610 --> 09:21.020 the method. 116 09:21.080 --> 09:25.490 Now let's change the value receiver to a pointer receiver. 117 09:25.700 --> 09:29.030 Now the age variable becomes a pointer. 118 09:29.120 --> 09:32.360 I don't have to take its address anymore. 119 09:32.390 --> 09:35.630 OK let's try it. 120 09:35.680 --> 09:36.340 Wow. 121 09:36.340 --> 09:39.340 Now it runs in a couple of milliseconds. 122 09:39.520 --> 09:43.300 It is way faster than the value receiver version. 123 09:43.300 --> 09:49.810 It's because every time it is called it only copies a tiny pointer data. 124 09:50.020 --> 09:56.430 As you can see the receiver address always points to the same memory location. 125 09:56.670 --> 10:05.100 In summary: Use a pointer receiver when you want to change the receiver variable or use a pointer receiver 126 10:05.220 --> 10:09.090 when the received value is very large. 127 10:09.090 --> 10:13.210 Picking the right receiver type confuses beginners. 128 10:13.470 --> 10:21.020 Most of the time they cannot decide whether to use a pointer receiver or a value receiver. 129 10:21.060 --> 10:27.570 Fortunately now you understand when the use a pointer receiver see you in the next lecture.