Locked learning resources

Join us and get access to thousands of tutorials and a community of expert Pythonistas.

Unlock This Lesson

Locked learning resources

This lesson is for members only. Join us and get access to thousands of tutorials and a community of expert Pythonistas.

Unlock This Lesson

Getting Class and Object Info

00:00 In the previous lesson, I showed you how to dynamically manipulate attributes on objects. In this lesson, I’ll show you how to get more information about classes and objects.

00:10 There are three built-in methods for determining information about class and object types. type() does two things. The simple one is it tells you the type of an object.

00:20 The complex one is it can be used to construct new classes. The isinstance() and issubclass() functions tell you whether an object is an instance of a class or whether a class is part of an inheritance hierarchy.

00:34 Let’s go be classy.

00:37 I’m going to start with the simpler and more common use of the type() function. It tells you what kind of thing an object is. Everything in Python is an object.

00:50 I know, I’ve done it once, but it’s not like I’m doing it every time. Even built-in types like integers are instances, so when you ask for the type of 42, you see the int class.

01:02 The type of a string is the str class. Like I said, everything’s an object. The built-in data types are available as classes for use, so you can actually use them to do comparisons. The type of 42 is an int,

01:18 but not a float. This isn’t usually how you do these kinds of comparisons, though. Instead, you typically use the isinstance() function.

01:31 isinstance() takes two arguments, the object you’re checking and the class you want to check it against. Since the type of 42 is an int, isinstance() returns True.

01:42 Why would you do it this way rather than that comparison I just showed you earlier? Well, because this is actually more comprehensive.

01:50 If you pass in a tuple as the second argument, isinstance() will check if the object is an instance of any of those things. If you’re using Python 3.10 or newer, you can also express this as a union of types using the pipe operator.

02:09 Same idea, just slightly clearer syntax. In addition to checking against multiple types, isinstance() is also aware of the inheritance hierarchy.

02:22 That might seem strange, but Booleans in Python are actually a subclass of int, so this evaluates to True.

02:35 And that’s why you use isinstance(). The type of False is a bool. It’s not specifically an int, but it inherits from int.

02:44 So if I do a direct comparison, it will say False, whereas isinstance() gives me True.

02:50 isinstance() checks if an object is of a class and is aware of subclasses. But if you want to check whether one class is a subclass of another without an instance, you use issubclass() instead.

03:06 This function takes two arguments. The first is the class you’re checking, and the second is the class you’re validating against. My example here shows the relationship I was just talking about, that the bool class is a subclass of the int class. Since I’ve been showing you a lot of trues, let’s do a false, just for completionist’s sake.

03:28 Ints and floats are different kinds of numeric storage, but they aren’t related. Well, that’s a little white lie. They’re sort of related, because everything in Python is an object.

03:43 So ints and floats are kind of cousins, just not descendants of the other. Python is one big happy family, with object as the single common ancestor of everything.

03:55 I mentioned that the type() function actually has two uses. The first, you saw already, giving you the type of the object passed in. The second is more complicated than that, and quite frankly, it’s never been clear to me why Python didn’t separate this into a different thing, but so be it.

04:10 This form of type() takes three arguments. The first is a string containing the name of the class being constructed. That’s Vehicle in this case.

04:25 The second is a tuple containing any base classes to inherit from, which I’m not using yet. And the third is a dictionary of any attributes or methods, which in this case, I’m also not using yet.

04:38 Essentially, what type() does is allow you to dynamically create a class. Once you’ve got it, you can use it like any other class. You can instantiate it, and when you examine its type, you see that it is class Vehicle.

04:52 The extra __main__ in front of it is the module the class belongs in. __main__ is the root module of your script or the REPL. This is the same __main__ in your if __name__ == "__main__" thing that you do in a script to see whether it got loaded as a module or run.

05:11 Let’s try something a little more complicated.

05:20 Methods are just functions that are attached to classes, which of course are all objects. I meant it when I said everything. So in order to dynamically create a new class that has a method, I need a function to attach to it.

05:34 Notice how I’ve written the function with an argument self. That’s because I’m going to turn it into a method.

05:47 This time, I’m using those other arguments to type(). The first tuple says Car will inherit from Vehicle.

05:55 The dictionary contains anything that I want to attach to the class, which in this case is my drive() method. Remember, it’s a reference to the function, so there’s no parentheses. I’m not invoking it, I’m just pointing to it.

06:08 Once it’s constructed, I can get an instance.

06:11 And then, of course, I can call its drive() method. And there’s a little proof about the inheritance. The type() function in this more complex format can also optionally take more arguments.

06:27 Anything else passed in gets used as keyword arguments to the metaclass. A metaclass is an abstraction mechanism in Python that’s called when you construct classes.

06:37 To get an object, you instantiate a class. To get a class, you invoke the metaclass. This is a deeply magical hook that is rare to come across, but it’s what enables powerful tools like the ORM framework inside of Django to be so dynamic.

06:53 The dynamic nature of objects and classes in Python is part of the duck typing philosophy. You can learn more about that in this video course or tutorial.

07:02 If my brief mention of metaclasses got you curious, well, there’s a course and tutorial for that as well. I warn you, though, it isn’t for the faint of heart.

07:12 Next up, I’ll lift the hood on functions a bit and show you the more general concept of a callable.

Become a Member to join the conversation.