1 00:00:00,000 --> 00:00:02,460 Welcome to Object Oriented Programming. 2 00:00:02,760 --> 00:00:06,960 First things first, let's make a little mental note that 3 00:00:06,970 --> 00:00:10,750 most things in Python are considered objects, even files. 4 00:00:10,930 --> 00:00:15,220 We've actually seen this before when we have a string, and 5 00:00:15,230 --> 00:00:17,980 we can, I did one too far there, 6 00:00:17,980 --> 00:00:20,500 we have a string with a dot and then hit tab, and 7 00:00:20,500 --> 00:00:23,700 we have all these different things that we can do with it. 8 00:00:23,700 --> 00:00:27,800 And even as an example, we can do 'name = "Python"', 9 00:00:27,800 --> 00:00:30,200 and let's do 'print(name)', 10 00:00:30,200 --> 00:00:35,000 and then let's also 'print(type(name))', 11 00:00:35,030 --> 00:00:36,530 and you can see that it's a class. 12 00:00:36,530 --> 00:00:39,200 Anytime you see class, just think object. 13 00:00:39,200 --> 00:00:45,100 So what Object Oriented Programming does, or OOP, is it lets 14 00:00:45,160 --> 00:00:47,860 programmers create their own objects and have their own methods 15 00:00:47,860 --> 00:00:48,800 and attributes. 16 00:00:48,800 --> 00:00:54,800 So a lot like we have 'name.upper', we can create that. 17 00:00:54,830 --> 00:00:58,790 We can create this '.upper', and it looks a lot like a function, 18 00:00:58,800 --> 00:01:02,360 actually. And the reason for that is because behind the scenes, 19 00:01:02,360 --> 00:01:03,600 it is a function. 20 00:01:03,600 --> 00:01:08,000 It's just already pre associated with a particular object. 21 00:01:08,020 --> 00:01:11,170 So moving forward, whenever you see a function inside of 22 00:01:11,180 --> 00:01:13,510 a class, which we'll dive into shortly, 23 00:01:13,800 --> 00:01:17,400 but whenever you see a function inside of a class, we call 24 00:01:17,400 --> 00:01:19,200 that a method. So this is a method. 25 00:01:19,200 --> 00:01:22,500 And this way of calling a function, it's just called a function. 26 00:01:22,500 --> 00:01:27,910 Objects or classes can also have properties or attributes, 27 00:01:27,910 --> 00:01:32,800 and that's really just saying that there is an internal type of variable. 28 00:01:32,800 --> 00:01:37,100 Now, that variable itself could also be an object and likely will be. 29 00:01:37,580 --> 00:01:41,140 But the idea is that whenever you have an object, and you 30 00:01:41,150 --> 00:01:43,960 have some sort of internal variable, a property or an attribute, 31 00:01:44,120 --> 00:01:47,960 and you have a method, that method can easily access that 32 00:01:47,960 --> 00:01:49,200 internal variable. 33 00:01:49,200 --> 00:01:51,800 You don't have to worry about scope or assigning a variable 34 00:01:51,800 --> 00:01:52,800 or anything like that. 35 00:01:52,800 --> 00:01:56,000 It's already inside of that class or inside of that object. 36 00:01:56,020 --> 00:01:58,930 And so it's going to have instant access to it already. 37 00:01:59,100 --> 00:02:04,420 So basically, what OOP does, is it allows you to create your 38 00:02:04,430 --> 00:02:07,810 own methods, create your own internal variables, create a 39 00:02:07,820 --> 00:02:11,919 class, and just like how we have string or int or tuple, it 40 00:02:11,919 --> 00:02:15,700 allows us to create our own objects just like that. 41 00:02:15,700 --> 00:02:20,000 And so basically, we can extend Python to do anything we wanted to do. 42 00:02:20,030 --> 00:02:22,680 We don't just have to stick with just strings. 43 00:02:22,680 --> 00:02:27,600 We can create a new type of object called a person, or a pet, 44 00:02:27,600 --> 00:02:30,600 or a hobby, or anything really. 45 00:02:30,620 --> 00:02:32,240 Now, why would we ever do this? 46 00:02:32,250 --> 00:02:35,240 Well, because in Python, they already give us methods like 47 00:02:35,240 --> 00:02:39,200 this, and that's because we are likely to use these on pretty 48 00:02:39,200 --> 00:02:40,200 much any string. 49 00:02:41,200 --> 00:02:42,500 It's a very common thing, 50 00:02:42,560 --> 00:02:44,080 so they provide it for us. 51 00:02:44,090 --> 00:02:45,850 We would essentially do the same thing. 52 00:02:45,850 --> 00:02:48,800 So we could have, for example, a person. 53 00:02:48,800 --> 00:02:53,900 Now, for the most part, people are born with two legs and 54 00:02:53,900 --> 00:02:56,500 two arms and a head. 55 00:02:56,800 --> 00:02:59,200 But people are also different. 56 00:02:59,200 --> 00:03:02,770 We have different features, like different hair color, different 57 00:03:02,860 --> 00:03:04,420 shoe size, things like that. 58 00:03:04,630 --> 00:03:09,280 And Object Oriented Programming lets us create repeatable 59 00:03:09,290 --> 00:03:12,930 and organized code without actually having to write the same 60 00:03:12,940 --> 00:03:15,240 10 variables about a person over and over and over again. 61 00:03:15,340 --> 00:03:18,850 And so sort of how we created a dictionary a long time ago 62 00:03:18,850 --> 00:03:24,500 where we had 'person', 'name = "Kalob"', we would have 63 00:03:24,500 --> 00:03:26,700 pre-defined things like arms, 64 00:03:26,700 --> 00:03:33,900 I've got two arms, legs, two legs, head, one head, something like that. 65 00:03:33,990 --> 00:03:36,260 And those are sort of actually terrible examples, 66 00:03:36,260 --> 00:03:39,800 but I think you get the point here where I have a 'person', 67 00:03:39,820 --> 00:03:43,210 and I could create another person with pretty much the exact 68 00:03:43,210 --> 00:03:45,300 same attributes and then just change, like, the 'name'. 69 00:03:45,360 --> 00:03:50,050 And so that's really just setting up a template so that you 70 00:03:50,060 --> 00:03:51,250 can create multiple people. 71 00:03:51,260 --> 00:03:54,960 You can create an army of people that all have, for instance, 72 00:03:54,960 --> 00:04:00,600 a default of 2 arms, or 3 arms, or 8 arms, 5 legs, and 2 heads; 73 00:04:00,610 --> 00:04:03,870 and you could copy that over and over and over again with 74 00:04:03,870 --> 00:04:04,900 a single line of code. 75 00:04:04,900 --> 00:04:07,500 You just have to set the rules for that template. 76 00:04:07,500 --> 00:04:09,800 That's what Object Oriented Programming is. 77 00:04:09,800 --> 00:04:12,200 So now a lot of people at this point in time, they think, 78 00:04:12,200 --> 00:04:15,000 "Well, why would I ever want to use Object Oriented Programming 79 00:04:15,000 --> 00:04:16,800 when I can just use variables and functions?" 80 00:04:16,800 --> 00:04:20,000 And that is the key question here. 81 00:04:20,019 --> 00:04:23,410 So functions are really nice for small pieces of code. 82 00:04:23,420 --> 00:04:26,230 You know, typically, a function does just one thing. 83 00:04:26,240 --> 00:04:28,450 It should actually only really do just one thing. 84 00:04:28,840 --> 00:04:33,020 But functions by themselves aren't organized well enough 85 00:04:33,030 --> 00:04:35,870 in code, and sometimes they need to be used together. 86 00:04:36,040 --> 00:04:40,720 So essentially, what Object Oriented Programming does is 87 00:04:40,720 --> 00:04:44,500 it allows us to group our functions and our variables together 88 00:04:44,500 --> 00:04:47,650 so that we know that they're all supposed to work together. 89 00:04:48,100 --> 00:04:51,520 And inside of our object, it sort of has its own version 90 00:04:51,520 --> 00:04:53,700 of scope, is a way to think about that, at least. 91 00:04:53,720 --> 00:04:57,920 And once you have an internal variable inside of one of your 92 00:04:57,920 --> 00:05:00,800 objects, or one of your classes, you can access it from pretty 93 00:05:00,800 --> 00:05:04,400 much any other method, or a function inside of your object. 94 00:05:04,420 --> 00:05:07,390 So again, we're really just grouping things together here. 95 00:05:07,600 --> 00:05:13,630 So if my 'person' dictionary here also had a function, and it 96 00:05:13,640 --> 00:05:19,300 needed to be 'say_hello', or this needs to be basically some 97 00:05:19,300 --> 00:05:23,500 sort of function that basically just says, 'print("Hello")', 98 00:05:23,500 --> 00:05:25,600 and this gets a little bit harder with a dictionary. 99 00:05:25,630 --> 00:05:28,350 With Object Oriented Programming, we can do that. 100 00:05:28,360 --> 00:05:32,950 We can say, 'person.say_hello', just like 'name.upper', 101 00:05:32,960 --> 00:05:35,920 and it will print out "Hello" for us, or anything else we wanted 102 00:05:35,930 --> 00:05:39,150 to. So let's go ahead, and I'm going to stop talking about 103 00:05:39,160 --> 00:05:41,820 the theory, and let's actually look at some of the syntax 104 00:05:41,850 --> 00:05:46,510 here. So to create a new object in Python, we use the keyword 105 00:05:46,810 --> 00:05:50,120 'class', and then we just give it a name. 106 00:05:50,130 --> 00:05:54,050 Now, typically, in Python, variables have lowercase letters 107 00:05:54,240 --> 00:05:56,730 and use underscores to separate them. 108 00:05:56,730 --> 00:06:03,050 So a variable name like 'my_name = "Kalob"', lowercase, 109 00:06:03,050 --> 00:06:05,840 lowercase, underscore, lowercase, lowercase, lowercase. 110 00:06:05,920 --> 00:06:09,580 In an object, we tend to use a different naming convention. 111 00:06:09,590 --> 00:06:12,040 Now you don't have to follow this rule, but it is a good 112 00:06:12,050 --> 00:06:13,300 practice to follow this rule. 113 00:06:13,900 --> 00:06:18,000 So it starts with the keyword 'class', and it just has upper case 114 00:06:18,000 --> 00:06:18,900 or camel case 115 00:06:18,900 --> 00:06:23,300 rather, camel case naming, like this, 'MyClassName', and then 116 00:06:23,310 --> 00:06:27,620 ':', and then inside of here we have functions, and these look exactly 117 00:06:27,620 --> 00:06:28,800 like regular functions. 118 00:06:29,000 --> 00:06:33,300 So 'def say_hello(): print("Hello")'. 119 00:06:34,300 --> 00:06:38,000 Now the only difference here is because this is in a class, 120 00:06:38,000 --> 00:06:41,870 every single method that you write takes 'self' as its first 121 00:06:41,900 --> 00:06:43,800 parameter every single time. 122 00:06:44,800 --> 00:06:46,700 So let's go ahead and execute this, 123 00:06:46,700 --> 00:06:50,500 and let's, I don't know, call this 'person', I guess, 124 00:06:50,500 --> 00:06:54,800 and instantiate this with 'MyClassName()'. 125 00:06:54,800 --> 00:06:56,800 [no audio] 126 00:06:56,800 --> 00:07:00,500 And now we can do 'type(person)', and we're going to see that 127 00:07:00,500 --> 00:07:02,400 this is 'MyClassName' type. 128 00:07:02,440 --> 00:07:06,640 And if I do 'person.', and then hit, 'Enter', or not 'Enter', 129 00:07:06,700 --> 00:07:09,900 if I hit 'Tab', it automatically fills with the only option 130 00:07:09,900 --> 00:07:12,500 that there is, which says, 'say_hello', and I can just run 131 00:07:12,500 --> 00:07:14,000 this with parentheses. 132 00:07:14,900 --> 00:07:17,500 Now you don't need to specify 'self' in here. 133 00:07:17,590 --> 00:07:21,680 You don't need to say this. That's already in there, and Python 134 00:07:21,690 --> 00:07:22,790 will ignore it by default. 135 00:07:22,800 --> 00:07:25,190 It's basically just passing in the rest of the class data 136 00:07:25,190 --> 00:07:27,110 into here, so we have access to it. 137 00:07:27,110 --> 00:07:29,500 We'll dive into that in just a second. 138 00:07:29,540 --> 00:07:32,450 But now I can say, 'person.say_hello'. 139 00:07:32,600 --> 00:07:36,900 And this looks a lot like the same syntax as 'name.upper', 140 00:07:37,900 --> 00:07:40,500 'name.upper', 'person.say_hello'. 141 00:07:40,560 --> 00:07:43,770 Now a class can also take default parameters in here. 142 00:07:43,770 --> 00:07:48,800 And this takes a function, a magic function called 143 00:07:48,800 --> 00:07:53,500 '__init__()'. Because it's a function 144 00:07:53,500 --> 00:07:57,800 inside of a class, or in this case, it's actually called a method, 145 00:07:57,800 --> 00:08:00,230 it's going to take 'self' all the time, 146 00:08:00,230 --> 00:08:01,600 we never pass in 'self', 147 00:08:01,600 --> 00:08:03,000 Python does that for us. 148 00:08:03,900 --> 00:08:06,900 Then we could say the default 'name' is going to be "Person", 149 00:08:08,200 --> 00:08:11,200 and the default 'hobby' is going to be "Coding". 150 00:08:11,260 --> 00:08:15,550 And this again is pretty much the exact same as a regular 151 00:08:15,550 --> 00:08:19,500 function. Now at this point in time, we can say, 'print(name)', 152 00:08:20,500 --> 00:08:23,500 'print(hobby)'. And let's run that. 153 00:08:23,500 --> 00:08:25,500 And let's add this in here. 154 00:08:25,540 --> 00:08:27,460 We'll just run that once more. 155 00:08:27,460 --> 00:08:31,400 Now, because this was initially instantiated like this, the 156 00:08:31,400 --> 00:08:33,000 default 'name' was "Person", 157 00:08:33,000 --> 00:08:34,700 default 'hobby' was "Coding", 158 00:08:34,799 --> 00:08:37,169 it said, "Person", and "Coding", but we could actually change this. 159 00:08:37,179 --> 00:08:41,640 We could say the 'name = "Henry", and his default 160 00:08:41,640 --> 00:08:45,200 'hobby = "Being adorbs"'. 161 00:08:45,200 --> 00:08:46,400 He's super adorable. 162 00:08:47,200 --> 00:08:48,700 And we can see that that changes in here. 163 00:08:49,480 --> 00:08:50,770 That's not going to change. 164 00:08:50,780 --> 00:08:52,059 That's not going to change. 165 00:08:52,070 --> 00:08:57,030 But now, because we have this little variable in here, we 166 00:08:57,040 --> 00:08:58,500 might actually want to access that. 167 00:08:58,580 --> 00:09:02,480 So ideally we would just say 'person.name', just like a 168 00:09:02,480 --> 00:09:05,200 regular attribute on a string, for instance. 169 00:09:05,240 --> 00:09:07,670 But this isn't necessarily going to work yet. 170 00:09:07,680 --> 00:09:10,860 And the reason for that is because, "AttributeError: 171 00:09:10,860 --> 00:09:13,100 'MyClassName' object has no attribute 'name'." 172 00:09:13,140 --> 00:09:18,710 So this attribute here, even though we set it when we initially 173 00:09:18,720 --> 00:09:23,110 created this object, it says it doesn't exist, and that's 174 00:09:23,110 --> 00:09:24,200 because of scoping. 175 00:09:24,200 --> 00:09:25,700 That's why we learned about scoping. 176 00:09:25,700 --> 00:09:30,600 'name' is a scoped variable, only exists in here, does not exist 177 00:09:30,600 --> 00:09:32,300 anywhere else, cannot exist anywhere else. 178 00:09:32,300 --> 00:09:33,400 Not yet anyways. 179 00:09:33,400 --> 00:09:37,800 So what we can say is 'self.name = name', 180 00:09:37,800 --> 00:09:41,600 'self.hobby = hobby'. 181 00:09:42,000 --> 00:09:45,500 And now you notice how we are using 'self' here. 182 00:09:46,500 --> 00:09:48,100 What we're saying is, 'MyClassName 183 00:09:48,100 --> 00:09:51,500 .name =', whatever this is going to be. 184 00:09:51,500 --> 00:09:53,800 So by default, it will be "Person", 185 00:09:53,860 --> 00:09:57,100 but we're saying it's going to be "Henry". And we can create 186 00:09:57,110 --> 00:09:57,940 a new function in here. 187 00:09:57,940 --> 00:10:01,800 'def get_name(self)', 188 00:10:01,800 --> 00:10:06,400 and that 'self' is really just it's attaching itself to the rest of this class. 189 00:10:06,400 --> 00:10:08,400 So without it, it doesn't know about 'self'. 190 00:10:08,400 --> 00:10:10,600 It doesn't know about 'self.name', or 'self.hobby'. 191 00:10:10,680 --> 00:10:13,800 But we can say 'print(self.name)' now. 192 00:10:14,020 --> 00:10:17,740 And as a better example, let's go ahead and run this with 193 00:10:17,740 --> 00:10:21,100 'name'. Let's comment this out as if that never happened. 194 00:10:21,100 --> 00:10:23,000 'name' is set as "Person". 195 00:10:23,000 --> 00:10:25,000 It's printed out immediately. 196 00:10:25,000 --> 00:10:28,600 And when we run 'get_name', do we actually get that 'name'? 197 00:10:28,600 --> 00:10:30,900 We're going to see that this is a scoping issue here. 198 00:10:30,950 --> 00:10:32,140 So let's go ahead and save this. 199 00:10:32,300 --> 00:10:35,800 We'll rerun that, rerun that, that, 200 00:10:35,890 --> 00:10:40,010 and in here we could say 'person.get_name', is what I called 201 00:10:40,010 --> 00:10:41,800 it, right? 'get_name'. 202 00:10:41,800 --> 00:10:43,900 [no audio] 203 00:10:43,900 --> 00:10:45,900 Oh, and it's Python. 204 00:10:47,100 --> 00:10:50,400 Now, the reason I did that, very interesting, 205 00:10:50,400 --> 00:10:52,300 I probably should have used a different variable name. 206 00:10:52,300 --> 00:10:57,400 But scoping again. Scoping, looked for a 'name' in here, didn't exist, 207 00:10:57,400 --> 00:10:59,600 looked for a name in the object, doesn't exist, 208 00:10:59,600 --> 00:11:02,200 looks for a name in the global scope, which is up here, 209 00:11:02,200 --> 00:11:03,400 and that was "Python". 210 00:11:04,100 --> 00:11:08,900 So let's go ahead and 'del name' from our script here. 211 00:11:08,900 --> 00:11:11,000 So we're just going to delete that variable entirely, 212 00:11:11,000 --> 00:11:12,000 rerun these. 213 00:11:12,000 --> 00:11:14,000 [no audio] 214 00:11:14,040 --> 00:11:17,010 and now we get a "NameError:", it says "'name' is not defined". 215 00:11:17,010 --> 00:11:19,000 It says the variable does not exist. 216 00:11:19,000 --> 00:11:22,400 And that's because in here it technically doesn't. 217 00:11:22,400 --> 00:11:25,800 What we are looking for is 'self.name'. 218 00:11:26,500 --> 00:11:28,900 Now that doesn't exist because we haven't set it yet. 219 00:11:28,900 --> 00:11:35,300 'self' is a special keyword that refers to the object itself. 220 00:11:35,320 --> 00:11:38,380 So whatever this object is called, that's what 'self' refers 221 00:11:38,390 --> 00:11:43,110 to. Just like, "My name is Kalob", when I refer to 'myself', 'myself' 222 00:11:43,110 --> 00:11:46,800 is "Kalob", in this case, 'self' is 'MyClassName'. 223 00:11:46,860 --> 00:11:48,630 We'll, uncomment that one as well. 224 00:11:48,630 --> 00:11:49,900 And let's rerun these. 225 00:11:49,920 --> 00:11:52,680 And now we're going to see that 'self = 'name', and 226 00:11:52,690 --> 00:11:55,910 we can access that because 'self' is always passed in automatically 227 00:11:55,910 --> 00:11:59,900 in an object. 'print(self.name)' is going to be "Henry". 228 00:11:59,900 --> 00:12:02,600 [no audio] 229 00:12:02,600 --> 00:12:03,900 So let's rerun all these. 230 00:12:04,200 --> 00:12:05,700 'get_name'. There it is. 231 00:12:05,770 --> 00:12:10,230 "Henry". So that is a crash course into Object Oriented Programming. 232 00:12:10,240 --> 00:12:12,300 There's a lot of different things we can do with this. 233 00:12:12,440 --> 00:12:15,800 But really, all we did was we bundled a couple of functions 234 00:12:15,800 --> 00:12:17,500 together, 'say_hello', and 'get_name', 235 00:12:17,500 --> 00:12:23,100 and we made a couple variables accessible only inside of this class. 236 00:12:24,200 --> 00:12:28,500 We can also do 'person.name' now, and we can see that it's 237 00:12:28,500 --> 00:12:32,000 "Henry". 'person.hobby' is also "Being adorbs". 238 00:12:32,000 --> 00:12:33,900 [no audio] 239 00:12:33,900 --> 00:12:36,300 And so by grouping all of this together, we're getting the 240 00:12:36,300 --> 00:12:37,300 power of a dictionary, 241 00:12:37,300 --> 00:12:41,000 but we're also getting the power of functions, and scope is 242 00:12:41,000 --> 00:12:43,200 actually going to start working in our favor now. 243 00:12:43,220 --> 00:12:45,980 So this was a crash course into Object Oriented Programming. 244 00:12:45,990 --> 00:12:48,560 By no means do you need to understand all of us. 245 00:12:48,570 --> 00:12:51,230 We are going to go through a lot more examples of Object 246 00:12:51,230 --> 00:12:53,500 Oriented Programming in the coming videos. 247 00:12:53,500 --> 00:12:54,700 [no audio]