1 00:00:05,250 --> 00:00:05,610 Okay. 2 00:00:05,610 --> 00:00:06,280 Welcome back. 3 00:00:06,300 --> 00:00:09,630 In this video, we'll finish off what we started in the previous video. 4 00:00:09,630 --> 00:00:12,480 So let's get a little bit more complicated now. 5 00:00:12,520 --> 00:00:14,280 Look at a couple more examples. 6 00:00:14,280 --> 00:00:17,100 I'm going to reduce this a little bit here. 7 00:00:18,310 --> 00:00:23,590 All right, so here's test four and I've got two pieces to test for it and expand them both and I'll 8 00:00:23,770 --> 00:00:24,550 walk through them. 9 00:00:24,760 --> 00:00:31,300 The first one I've written a function and that function is called filter vector. 10 00:00:31,480 --> 00:00:32,800 It's right here. 11 00:00:33,520 --> 00:00:34,810 It returns nothing. 12 00:00:34,990 --> 00:00:36,220 And what does it expect? 13 00:00:36,250 --> 00:00:40,660 It expects a stood vector of integers and its const. 14 00:00:40,660 --> 00:00:42,670 So I cannot modify it from in here. 15 00:00:43,510 --> 00:00:47,980 It's called VEC and a function that's a function object. 16 00:00:48,100 --> 00:00:49,330 What does that function object? 17 00:00:49,330 --> 00:00:51,020 Expect an integer. 18 00:00:51,040 --> 00:00:52,140 What does it return? 19 00:00:52,150 --> 00:00:53,060 A boolean? 20 00:00:53,080 --> 00:00:54,800 That's what the syntax says. 21 00:00:54,820 --> 00:00:58,950 I know the syntax may look a little wonky, but it's just a matter of getting used to it. 22 00:00:58,960 --> 00:01:00,130 It's not complicated. 23 00:01:00,430 --> 00:01:03,170 And what is the name of that parameter func? 24 00:01:03,190 --> 00:01:05,019 This is a function object. 25 00:01:05,019 --> 00:01:10,690 So I can call that function object simply by saying func and passing an integer into it. 26 00:01:11,440 --> 00:01:14,560 Any kind of integer, whether it's a literal or a variable name. 27 00:01:14,740 --> 00:01:18,430 And this guy will return a boolean that I can use. 28 00:01:18,520 --> 00:01:20,290 So that's what's really happening here. 29 00:01:20,440 --> 00:01:26,230 I'm displaying the left bracket and then I've got a range based for loop here that's looping over this 30 00:01:26,230 --> 00:01:26,950 vector. 31 00:01:27,730 --> 00:01:34,000 And for each integer I in the vector, I'm calling func and passing it in. 32 00:01:34,030 --> 00:01:35,340 What does this func do? 33 00:01:35,350 --> 00:01:36,340 I have no idea. 34 00:01:36,340 --> 00:01:37,870 That's the real power here. 35 00:01:37,900 --> 00:01:41,110 I could care less what is happening in that function. 36 00:01:41,590 --> 00:01:46,540 All I know is that I'm a filter vector function and I get a function. 37 00:01:46,540 --> 00:01:47,560 I'm calling that function. 38 00:01:47,560 --> 00:01:48,700 I really don't know what it does. 39 00:01:48,700 --> 00:01:49,900 I don't care what it does. 40 00:01:50,320 --> 00:01:53,800 The only thing that's important is that it expects an INT and returns a boom. 41 00:01:54,130 --> 00:02:00,790 So in this case, if it returns true, I'm going to display that value and then I'm just closing this 42 00:02:00,790 --> 00:02:01,600 with a bracket. 43 00:02:02,440 --> 00:02:04,360 So it'll make sense now when you see when I call it. 44 00:02:04,360 --> 00:02:07,080 So let me scroll up just a little bit. 45 00:02:07,090 --> 00:02:11,620 I'm right here on test four, so I'm saying that's four. 46 00:02:11,650 --> 00:02:12,790 That's right here. 47 00:02:12,790 --> 00:02:19,270 Here's my vector of numbers called nums and I'm going to call filter vector and I'm going to pass in 48 00:02:19,270 --> 00:02:20,020 nums. 49 00:02:20,020 --> 00:02:20,380 Right. 50 00:02:20,380 --> 00:02:21,670 That's this guy. 51 00:02:22,900 --> 00:02:26,900 And now I'm going to pass in the function that I want called every time in here. 52 00:02:26,920 --> 00:02:30,830 Well, I'm going to pass in a lambda expression, stateless. 53 00:02:30,850 --> 00:02:33,770 It expects an INT and it returns a boolean. 54 00:02:33,790 --> 00:02:35,680 That's exactly what we set up here. 55 00:02:36,430 --> 00:02:38,200 So what is this guy going to do? 56 00:02:38,380 --> 00:02:42,150 It's going to return true when X is greater than 50. 57 00:02:42,160 --> 00:02:47,460 And this guy here will be true only whenever each one of those eyes is greater than 50. 58 00:02:47,470 --> 00:02:48,520 So what does this do? 59 00:02:48,790 --> 00:02:53,380 This only prints out values that are greater than 50 right there. 60 00:02:53,770 --> 00:02:55,930 60, 70, 89, 80, 100. 61 00:02:56,440 --> 00:02:59,260 In this example, I'm just using a different lambda. 62 00:02:59,260 --> 00:03:02,870 I'm only going to display values that are less than or equal to 30. 63 00:03:02,870 --> 00:03:04,540 And you can see them display right here. 64 00:03:04,930 --> 00:03:09,820 And in this case, I'm only displaying values that are greater than or equal to 30 and less than or 65 00:03:09,820 --> 00:03:10,540 equal to 60. 66 00:03:10,570 --> 00:03:13,270 So we're displaying 30, 40, 50, 60. 67 00:03:13,510 --> 00:03:14,580 This is pretty cool. 68 00:03:14,590 --> 00:03:18,550 I think you can really wrap your head around this and see how powerful these lambdas are. 69 00:03:18,790 --> 00:03:27,310 Also, it's very important to understand is the programmer that wrote this function doesn't really care 70 00:03:27,310 --> 00:03:33,290 what this function does right here, for example, only greater than 50, less than or equal to 30. 71 00:03:33,310 --> 00:03:40,060 It's up to perhaps another programmer that's using this filter vector function to decide what's the 72 00:03:40,060 --> 00:03:41,020 logic here? 73 00:03:41,890 --> 00:03:46,150 Now, this guy right here is called a predicate Lambda. 74 00:03:46,180 --> 00:03:49,600 And I mentioned that in the slides in the previous lecture. 75 00:03:49,870 --> 00:03:57,360 This is a predicate, Lambda, because it expects one or more parameters and returns a boolean. 76 00:03:57,370 --> 00:04:01,570 That's the definition of a predicate lambda or a predicate function, if you will. 77 00:04:01,600 --> 00:04:07,420 So again, walk through this example and try them out and change these lambdas to do different things. 78 00:04:07,420 --> 00:04:09,960 And you can see just how powerful this really is. 79 00:04:09,970 --> 00:04:15,310 There are so many algorithms in the standard template library that use these predicate lambdas just 80 00:04:15,310 --> 00:04:15,970 like this. 81 00:04:15,970 --> 00:04:20,350 So from a programmers perspective, we're working in here, right? 82 00:04:20,350 --> 00:04:26,800 But the person or the team that wrote those algorithms are expecting this kind of thing and they could 83 00:04:26,800 --> 00:04:29,980 care less how we want to sort something or how we want to compare something. 84 00:04:29,980 --> 00:04:31,210 That's for our logic. 85 00:04:31,210 --> 00:04:31,860 Determine. 86 00:04:31,870 --> 00:04:32,830 Try one more. 87 00:04:32,860 --> 00:04:42,460 Oh, and by the way, I should mention this line 95 right here, we use this in C++ 14 or higher in 88 00:04:42,460 --> 00:04:52,300 C++ 20, we can replace this with just this auto func and let the compiler figure out that it returns 89 00:04:52,300 --> 00:04:54,010 a boolean and expects an integer parameter. 90 00:04:54,010 --> 00:04:57,430 So that's pretty cool too, but that's what that would be in C++ 20. 91 00:04:58,150 --> 00:04:59,440 Scroll this up as well. 92 00:05:01,420 --> 00:05:05,380 So now we're in test five and it's these two pieces right here. 93 00:05:05,410 --> 00:05:05,710 All right. 94 00:05:05,710 --> 00:05:07,240 So what's going on in test five? 95 00:05:07,270 --> 00:05:10,030 Well, test five is a little bit different as well. 96 00:05:10,030 --> 00:05:15,100 And you'll see this make more sense when we talk about stateful lambdas in the next couple of sections. 97 00:05:15,100 --> 00:05:16,630 But in this case, look what I've got. 98 00:05:16,630 --> 00:05:19,390 I've got a function called make lambda. 99 00:05:19,960 --> 00:05:22,390 And what does it return auto? 100 00:05:22,840 --> 00:05:24,970 Let the compiler figure it out. 101 00:05:24,970 --> 00:05:26,350 It's returning a lambda. 102 00:05:26,380 --> 00:05:28,510 You can see right here it's return. 103 00:05:28,510 --> 00:05:33,660 There's my capture list, no parameters and there's the body of the a c statement. 104 00:05:33,940 --> 00:05:34,390 Wow. 105 00:05:34,390 --> 00:05:37,110 You know, you wrap your head around this thing and you're going, well, what's going on here? 106 00:05:37,120 --> 00:05:40,450 Well, I'm calling a function that's returning a lambda. 107 00:05:40,990 --> 00:05:44,770 It's not executing that lambda, it's just returning the lambda later on. 108 00:05:44,770 --> 00:05:46,570 I can execute that lambda if I want. 109 00:05:46,570 --> 00:05:48,160 And that's what I'm doing right here. 110 00:05:48,160 --> 00:05:51,880 You can see right here I'm displaying test five right there. 111 00:05:52,450 --> 00:05:55,210 Then I'm calling make lambda right. 112 00:05:55,300 --> 00:06:01,210 That's my function and I'm assigning whatever it's returning, which is a lambda in this case to this 113 00:06:01,210 --> 00:06:08,320 lambda right here called L five and now I'm calling it and when I call it it instantiate the lambda 114 00:06:08,320 --> 00:06:13,420 executes that lambda that's being returned and you can see what displays this lambda was made using 115 00:06:13,420 --> 00:06:14,230 make lambda. 116 00:06:14,230 --> 00:06:17,110 We could pass parameters, we could do all kinds of things. 117 00:06:17,110 --> 00:06:21,490 And again, it makes more sense to see this in the stateful context. 118 00:06:21,490 --> 00:06:24,610 So I'll leave those examples for the next couple of videos. 119 00:06:24,610 --> 00:06:29,680 But you can see it's pretty cool, right, that a lambda that's sorry that a function can return a lambda 120 00:06:29,680 --> 00:06:33,310 and those lambda that we return can be pretty complicated as well. 121 00:06:33,340 --> 00:06:39,640 Let's move over to Test six and there's just a couple left, couple of examples and this one's pretty 122 00:06:39,640 --> 00:06:41,320 easy example to understand. 123 00:06:41,410 --> 00:06:44,200 And we're over here in Test six. 124 00:06:44,860 --> 00:06:45,790 So what do we do here? 125 00:06:45,790 --> 00:06:48,700 Well, this is using auto in the Lambda Parameter list. 126 00:06:48,700 --> 00:06:51,100 I mentioned this in the slides in the previous lecture. 127 00:06:51,370 --> 00:06:53,830 Notice now I'm saying auto and auto. 128 00:06:54,340 --> 00:06:57,760 So I'm telling the compiler, hey, compiler, you figure out what's going on. 129 00:06:57,910 --> 00:07:02,170 This is pretty cool because we're not trying to create some generic template function here. 130 00:07:02,170 --> 00:07:03,400 We're just doing it this way. 131 00:07:03,400 --> 00:07:06,520 So again, l six is the variable. 132 00:07:06,820 --> 00:07:08,920 Let the compiler figure out the type. 133 00:07:09,340 --> 00:07:11,410 And what are we assigning to this variable? 134 00:07:11,560 --> 00:07:14,890 Lambda no captur to parameters. 135 00:07:14,890 --> 00:07:15,940 What are their types? 136 00:07:15,940 --> 00:07:16,450 I don't know. 137 00:07:16,450 --> 00:07:18,040 Let the compiler figure it out. 138 00:07:18,580 --> 00:07:22,150 And within the body of that lambda, all we're doing is we're displaying. 139 00:07:22,860 --> 00:07:24,200 And we're displaying why? 140 00:07:24,210 --> 00:07:26,040 What's the type of X and Y? 141 00:07:26,070 --> 00:07:27,090 Again, I don't know. 142 00:07:27,090 --> 00:07:28,470 The compiler will figure it out. 143 00:07:28,620 --> 00:07:35,070 So now that I've got my lambda my lambda expression in the variable L six, I can call it right here. 144 00:07:35,070 --> 00:07:36,630 I'm calling it with two integers. 145 00:07:36,630 --> 00:07:39,940 So the compiler sees this and says, oh that's it, that's in it. 146 00:07:39,980 --> 00:07:40,360 Aha. 147 00:07:40,380 --> 00:07:43,230 Intent 1020 is being displayed now. 148 00:07:43,230 --> 00:07:46,350 I'm displaying it, I'm calling it with a double and an integer. 149 00:07:46,380 --> 00:07:49,620 So it's displaying 100.3 and 200, right? 150 00:07:49,620 --> 00:07:50,760 The double and the integer. 151 00:07:50,910 --> 00:07:52,380 Here's two doubles. 152 00:07:52,620 --> 00:07:53,870 That works too. 153 00:07:53,880 --> 00:07:55,560 But this is where it's really neat. 154 00:07:55,560 --> 00:08:00,090 I'm calling L six now and I'm passing in two person objects. 155 00:08:00,810 --> 00:08:03,330 Larry 18, Curly 22. 156 00:08:03,720 --> 00:08:07,020 These guys, the compiler is going to say, Oh, those are person objects. 157 00:08:07,020 --> 00:08:10,560 Remember, I created that person class up at the top of this file. 158 00:08:10,800 --> 00:08:14,580 So it's going to pass those things into this lambda. 159 00:08:14,580 --> 00:08:22,650 Execute the lambda and it's going to display person Larry 18 person curly 22 Same thing we passed in 160 00:08:22,650 --> 00:08:23,070 here. 161 00:08:24,060 --> 00:08:25,320 Now, that's pretty cool. 162 00:08:25,890 --> 00:08:28,500 Now, a couple of things that are happening here. 163 00:08:29,430 --> 00:08:35,850 It's very important that whatever you pass in to this must overload this operator. 164 00:08:35,850 --> 00:08:35,990 Right. 165 00:08:36,000 --> 00:08:39,030 I mean, we're displaying these guys using this operator right here. 166 00:08:39,570 --> 00:08:45,390 I've I have overloaded the insertion operator in that person class that I've already created up there. 167 00:08:45,390 --> 00:08:47,000 So this is really important. 168 00:08:47,010 --> 00:08:51,390 Otherwise you're going to get a compiler error that may not be too easy to read and it's going to say 169 00:08:51,390 --> 00:08:55,740 something about operator less than less than not defined somehow. 170 00:08:55,860 --> 00:09:01,670 It's not a problem here because the floats in the ints and the doubles all support the overloaded insertion 171 00:09:01,680 --> 00:09:02,280 operator. 172 00:09:02,610 --> 00:09:03,780 Last example. 173 00:09:04,110 --> 00:09:06,300 This example right here is Test seven. 174 00:09:06,300 --> 00:09:09,510 Also really straightforward example what we're doing here. 175 00:09:09,510 --> 00:09:12,390 And let me scroll this up just a little so we can see it a little bit better. 176 00:09:12,390 --> 00:09:14,460 I'm right here in Test seven. 177 00:09:15,030 --> 00:09:20,100 What I've done is I've created a vector of person objects called stooges. 178 00:09:20,100 --> 00:09:21,690 So there are Larry, Moe and Curly. 179 00:09:21,690 --> 00:09:22,680 Larry's 18. 180 00:09:22,680 --> 00:09:23,670 Moe is 30 Curl. 181 00:09:23,670 --> 00:09:24,530 He's 25. 182 00:09:24,540 --> 00:09:29,580 Now, what I'm doing is I'm calling some of the standard template library algorithm functions. 183 00:09:30,120 --> 00:09:30,960 I'm going to use two of them. 184 00:09:30,960 --> 00:09:37,680 I'm going to use stewed sort and stewed for each they take in lambda expressions, right, or function 185 00:09:37,680 --> 00:09:38,430 objects. 186 00:09:38,430 --> 00:09:45,660 In this case I'm using lambdas, so I'm calling Stuart sort and basically it says, well, what do you 187 00:09:45,660 --> 00:09:46,350 want to sort? 188 00:09:46,350 --> 00:09:47,040 Where does it start? 189 00:09:47,040 --> 00:09:47,880 Where does it end? 190 00:09:47,880 --> 00:09:50,580 So begin stooges and stooges. 191 00:09:50,580 --> 00:09:51,930 Right, there's my vector. 192 00:09:52,320 --> 00:09:53,760 I want to start at the beginning. 193 00:09:53,760 --> 00:09:54,390 Go to the end. 194 00:09:54,390 --> 00:09:58,050 Remember, this is just an alternate syntax for stooges. 195 00:09:59,310 --> 00:10:01,700 Begin and end. 196 00:10:01,710 --> 00:10:03,720 We could do it like begin like this or like this. 197 00:10:03,720 --> 00:10:04,590 Either way it works. 198 00:10:04,830 --> 00:10:06,960 And here is the lambda expression. 199 00:10:08,130 --> 00:10:10,950 Remember stood sorte is expecting a function object. 200 00:10:10,950 --> 00:10:12,210 So that's why I'm going to send it. 201 00:10:13,340 --> 00:10:18,170 No capture list two parameters by Konst reference. 202 00:10:19,100 --> 00:10:21,270 The first one is one person. 203 00:10:21,290 --> 00:10:22,710 The other is the other person. 204 00:10:22,730 --> 00:10:23,510 It's sorting. 205 00:10:23,510 --> 00:10:26,000 So when you're sorting, you're comparing two things, right? 206 00:10:26,000 --> 00:10:27,180 And moving them around. 207 00:10:27,200 --> 00:10:31,370 Well, how does this guy know where to move things around? 208 00:10:31,500 --> 00:10:33,330 Well, you need to tell it which one is bigger. 209 00:10:33,350 --> 00:10:37,150 So in this case, I'm returning p one. 210 00:10:37,160 --> 00:10:38,120 Get the name. 211 00:10:38,120 --> 00:10:41,540 And if it's less than P two's name, I'm going to return. 212 00:10:41,540 --> 00:10:43,820 True or false, depending on this condition. 213 00:10:43,910 --> 00:10:49,430 Based on that condition, these two sort algorithm knows which one is greater, which one is less than, 214 00:10:49,430 --> 00:10:50,720 and it can do what it's doing. 215 00:10:51,080 --> 00:10:52,400 Now, this is pretty powerful. 216 00:10:52,400 --> 00:10:55,370 This is, again, a predicate lambda right here. 217 00:10:55,370 --> 00:10:58,100 You can see that this is a predicate lambda right here. 218 00:10:58,250 --> 00:11:02,450 You're passing in some parameters and it's returning a boolean. 219 00:11:02,900 --> 00:11:07,100 So that's exactly what's happening here and that's exactly what stood sort expects. 220 00:11:07,100 --> 00:11:08,510 So what's going on? 221 00:11:08,510 --> 00:11:13,040 I'm sorting the Stooges vector by name. 222 00:11:13,040 --> 00:11:18,430 Now, when I finished this, this stood vector right here will be sorted. 223 00:11:18,440 --> 00:11:20,990 Now I just want to display each element in there. 224 00:11:20,990 --> 00:11:26,060 And to do that, I'm going to use another standard template library algorithm called for each. 225 00:11:26,870 --> 00:11:27,110 Okay. 226 00:11:27,110 --> 00:11:27,980 Now, what does this do? 227 00:11:28,010 --> 00:11:29,630 Well, where do you want to start? 228 00:11:29,660 --> 00:11:31,010 Where do you want to end? 229 00:11:31,010 --> 00:11:32,420 And what do you want to do? 230 00:11:32,450 --> 00:11:33,010 Right. 231 00:11:33,020 --> 00:11:35,810 So it's going to loop through that vector. 232 00:11:36,260 --> 00:11:38,660 That's what it's doing for each element in the vector. 233 00:11:38,750 --> 00:11:40,310 It's going to loop through that vector. 234 00:11:40,310 --> 00:11:45,050 And for each one of those elements, it's going to call this lambda function right here. 235 00:11:46,130 --> 00:11:47,930 It's going to take that element in here. 236 00:11:48,110 --> 00:11:51,670 Larry, Moe, Curly, pass it into here and I'm just going to display it. 237 00:11:51,680 --> 00:11:54,440 So when I call this, look what happened right here. 238 00:11:57,140 --> 00:11:58,470 Curly Larry Moe. 239 00:11:58,490 --> 00:12:00,640 Notice it's sorted alphabetically. 240 00:12:00,680 --> 00:12:02,100 Clem Right. 241 00:12:02,120 --> 00:12:02,910 Curly Larry. 242 00:12:02,930 --> 00:12:05,110 Moe It used to be Larry. 243 00:12:05,120 --> 00:12:06,110 Moe Curly. 244 00:12:06,380 --> 00:12:14,090 So this function right here that we called absolutely sorted that vector based on the condition in our 245 00:12:14,090 --> 00:12:14,970 predicate lambda. 246 00:12:14,990 --> 00:12:15,380 All right. 247 00:12:15,380 --> 00:12:18,500 So one more example and we're right here now. 248 00:12:18,560 --> 00:12:20,600 I'm calling stooge sort again. 249 00:12:20,840 --> 00:12:23,630 This time I'm sorting based on age. 250 00:12:23,630 --> 00:12:25,280 I want to sort based on age. 251 00:12:25,280 --> 00:12:26,360 Same idea, right? 252 00:12:26,360 --> 00:12:33,710 Give me the two parameters and return p ones age less than p two's age now stood sought knows which 253 00:12:33,710 --> 00:12:34,880 one to put ahead of the other. 254 00:12:35,240 --> 00:12:39,230 And once we do that, we're going to do this for each again in this code. 255 00:12:39,230 --> 00:12:41,140 And this code are exactly the same. 256 00:12:41,150 --> 00:12:42,920 But look what happens over here. 257 00:12:43,430 --> 00:12:48,770 Now we're going to display Larry, Curly and Moe, but now they're sorted by age. 258 00:12:49,010 --> 00:12:49,640 There you go. 259 00:12:49,820 --> 00:12:54,770 This gives you a, I think, a pretty good introduction to different kinds of stateless lambdas using 260 00:12:54,770 --> 00:12:57,680 references by value objects and so forth. 261 00:12:57,830 --> 00:13:03,020 In the next video, we'll switch over and we'll start talking about stateful lambda expressions. 262 00:13:03,020 --> 00:13:04,400 So I'll see you in that one.