Python Classes and Objects
Table of Contents + β
In the last lesson you learned Introduction to OOP. There we talked about thinking in objects instead of loose variables and functions. Now we get to the part where you actually build one. So the big question is this. How do you create your own kind of thing in Python, like a Dog or a User or a BankAccount? That is what classes and objects are for.
π€ Why Classes and Objects?
Say you are building an app that has many dogs in it. Each dog has a name. Each dog can bark. Without a way to group this, you end up with loose variables floating around. You get dog1_name, dog2_name, dog1_sound, and so on. It gets messy fast. And nothing ties a dogβs name to its bark.
A class fixes this. It lets you design one βshapeβ for a dog. Then you create as many dogs as you want from that one design. Each one carries its own name and knows how to bark.
ποΈ Blueprint vs Real Thing
Here is the idea in plain words.
- A class is a blueprint. It describes what something looks like and what it can do. It is not a real thing yet.
- An object is a real thing made from that blueprint. We also call an object an instance.
Think of a house. The architect draws one blueprint. From that single blueprint, the builder puts up many real houses on the street. Each house is real. You can live in it. And they were all made from the same drawing.
The blueprint is the class. Each real house is an object.
So you write the class once. Then you create many objects from it. Each object lives on its own.
π οΈ Defining a Class
You create a class with the class keyword. By habit, class names start with a capital letter, like Dog or User. Inside the class you put methods. A method is just a function that belongs to the class.
Here is the smallest useful Dog class. It has one method called bark.
class Dog: def bark(self): print("Woof!")Letβs read it line by line.
class Dog:starts the blueprint and names itDog.def bark(self):defines a method, which is a function that lives inside the class.print("Woof!")is what that method does when you call it.
Right now nothing happens. We have only drawn the blueprint. No real dog exists yet. To get a real dog, we have to make an object.
π Creating Objects from the Class
To create an object, you write the class name followed by parentheses, like calling a function. This gives you back one real object. We store it in a variable.
This creates one dog and makes it bark.
class Dog: def bark(self): print("Woof!")
my_dog = Dog()my_dog.bark()Running this prints:
Output
Woof!Here is what each new line does.
my_dog = Dog()creates a realDogobject and stores it inmy_dog. This is the instance.my_dog.bark()calls thebarkmethod on that object using a dot.
The dot is how you reach into an object and use what it can do. You read my_dog.bark() as βask my_dog to barkβ.
The real value shows up when you make more than one. Each call to Dog() gives you a separate object.
This creates two dogs from the same blueprint.
class Dog: def bark(self): print("Woof!")
rex = Dog()buddy = Dog()
rex.bark()buddy.bark()It prints:
Output
Woof!Woof!rex and buddy are two different objects. They came from the same Dog class. But they are separate things in memory. That is the whole point of a blueprint. You write it once and create many.
π What Is self?
You probably noticed self sitting in def bark(self):. This confuses a lot of people, so let me say it plainly.
self is the object itself. When you call rex.bark(), Python quietly passes rex into the method as self. So inside the method, self means βthe exact object this was called onβ.
You do not pass it yourself. Look closely. You write rex.bark() with empty parentheses, yet the method header says bark(self). Python fills in self for you, automatically.
self becomes useful when each object holds its own data. Here each dog has a name. And bark uses self to read that name.
class Dog: def bark(self): print(f"{self.name} says Woof!")
rex = Dog()rex.name = "Rex"
buddy = Dog()buddy.name = "Buddy"
rex.bark()buddy.bark()This prints:
Output
Rex says Woof!Buddy says Woof!See what happened there.
rex.name = "Rex"stores a name on therexobject.buddy.name = "Buddy"stores a different name on thebuddyobject.- Inside
bark,self.namereads the name of whichever object you called it on.
So when you run rex.bark(), self is rex, and self.name is "Rex". When you run buddy.bark(), self is buddy. Same method, different object, different result.
Tip
Setting names from outside like rex.name = "Rex" works, but it is not the clean way. In the next lesson you will learn the constructor, which gives each object its data the moment it is created.
π Class vs Object at a Glance
This table lines up the two ideas side by side.
| Class | Object (Instance) |
|---|---|
| The blueprint | A real thing made from it |
| Written once | Created many times |
class Dog: | rex = Dog() |
| Describes what a dog can do | Has its own name and barks on its own |
β οΈ Common Mistakes
A few things tend to cause problems early on.
- Forgetting the parentheses when creating an object.
Dogis the blueprint.Dog()is a real object.
# β Avoid: this points at the class itself, not an objectmy_dog = Dog# β
Good: the parentheses actually build an objectmy_dog = Dog()- Leaving out
selfin a method. Every method that works on the object needsselfas its first parameter.
# β Avoid: no self, so the method cannot reach the object's dataclass Dog: def bark(): print("Woof!")
# β
Good: self is there, so bark can use the objectclass Dog: def bark(self): print("Woof!")- Calling a method without the parentheses.
rex.barkjust refers to the method.rex.bark()actually runs it.
β Best Practices
Keep these habits and your classes stay easy to read.
- Name classes with a capital first letter:
Dog,User,BankAccount. This is the common style and other developers expect it. - Give classes and methods clear, real-world names.
barkandDogtell the reader exactly what they are. - Always make
selfthe first parameter of a method, even before you fully understand it. It needs to be there. - Keep one class focused on one kind of thing. A
Dogclass should describe a dog, not also handle the whole app.
π§© What Youβve Learned
A quick recap of what you can now do.
- β A class is a blueprint, and an object (instance) is a real thing made from it.
- β
You define a class with the
classkeyword and put methods inside it. - β
You create an object by calling the class name with parentheses, like
Dog(). - β
You call a method on an object with a dot, like
rex.bark(). - β
selfis the object itself, and Python passes it in for you automatically.
Check Your Knowledge
Test what you learned. Pick an answer for each question, then click Check.
- 1
What is the difference between a class and an object?
Why: A class describes the shape; an object (instance) is an actual thing built from that class.
- 2
How do you create an object from a class named Dog?
Why: You call the class name with parentheses, so Dog() builds and returns a new object.
- 3
What does self refer to inside a method?
Why: self is the exact object the method runs on, and Python passes it in automatically.
- 4
When you call rex.bark(), how does self get its value?
Why: Writing rex.bark() tells Python to pass rex in as self for you, so the parentheses stay empty.
π Whatβs Next?
You can make objects now, but setting each oneβs data by hand quickly becomes tedious. Next you will learn how to give an object its data the moment it is born.