Topic #13b – More About Objects¶
Let’s make a slightly more complex object.
What if I want to make
It will basically just be an object that holds a list of my EnthusiasticStudents
It will also have the class name
But first… a convention¶
Let’s go look at out
EnthusiasticStudentobject and make one small change
1class EnthusiasticStudent: 2 ''' 3 Obv we'll include a nice comment at the top of the class to explain what it's for... right?! 4 5 This EnthusiasticStudent is being used to demonstrate how we can create our own Objects. 6 7 It's going to have a few attributes and some simple functions. 8 ''' 9 10 def __init__(self, first_name='John', last_name='Doe', student_num='000000000', current_avg=0): 11 self._first_name = first_name 12 self._last_name = last_name 13 self._student_num = student_num 14 self._current_avg = current_avg 15 16 def ask_for_higher_mark(self, howHigh): 17 print('Hello Professor,\n\nMy name is ' + self._first_name + ' and I am in your CSCI 161 class. I feel that I deserve a higher mark on the last assignment because I am the chosen one. I would really like it if you could just give me a ' + str(howHigh) + '%. \n\nThanks,\n' + self._first_name + ' ' + self._last_name) 18 19 def show_off(self): 20 print('I\'m going to ask a question about something really really really really advanced in an attempt to impress everyone and assume I\'m a wizard') 21 self._first_name = 'Wizard' 22 23 24 def work_too_hard_on_assignment(self): 25 # I left it blank. Add whatever code you want here. Be sure to delete the pass keyword when you do though 26 pass 27 28 29 def __repr__(self): 30 ''' 31 A method which will return some string representation of the object. This will he handy for debugging and stuff. 32 ''' 33 return 'First Name: ' + self._first_name + '\nlast_name: ' + self._last_name + '\nStudent Number: ' + self._student_num + '\nCurrent Average: ' + str(self._current_avg) 34 35 36 def __eq__(self, anotherThing): 37 ''' 38 A method to check if 2 EnthusiasticStudent are the same. What does it mean for 2 things to be the same? 39 Well, WE get to make that up! 40 (Although, we should pick something that makes sense...) 41 ''' 42 return self._student_num == anotherThing.get_student_num() 43 44 # just a getter (see below) 45 def get_first_name(self): 46 return self._first_name 47 48 # just another getter (see below) 49 def get_student_num(self): 50 return self._student_num
I added underscores to each of the attributes
- This makes them private
Long story short…
Public attributes/methods are visible outside the class
Private attribute/methods are NOT visible outside the class
- When we make something private, it’s like saying…
- This attribute/method cannot be called anywhere else other than from within the code in the class.
James will now show you an example
Why do we care?
It’s all about encapsulation and design
A well designed program will probably have public and private attribute/methods
In Python, the convention for our private variables is to put an underscore in front.
The idea is, if I’m using the object someone else wrote, I don’t need to know about what I don’t need to know about…
- Let me put it this way.
- You have all used lists
We know how to use them
We don’t know how they work
We don’t know what attributes they have
But that’s OK
- Or how about this?
Imagine a car
- Do you know how to drive a car?
gas, break, steer
Does the way you interface with the car matter if, say, the car is electric or gas?
A gas and electric car are built very different on the inside, but that didn’t really impact the way you interface with the object.
Don’t worry too much if the point is still a little lost on you, it will get cleared in CSCI 162.
So how do we interface with the attributes if we make them all private?
Getters and setters!
It’s so simple it’s silly really
Here is an example with getting/setting
1def get_student_num(self): 2 return self._student_num 3 4def set_student_num(self, student_num): 5 self._student_num = student_num
Does it feel silly doing this?
Yes, good, you’re normal
- But again, motivation for this will reallllly come next semester.
Teaser: We can control how the attributes are interacted with.
- We can enforce data integrity rules
Eg. Ensure all Student Numbers are 9 chars long.
Ok, we want an object to hold onto
- What attributes do we want?
List of the EnthusiasticStudents
1class MyStudents: 2 3 4 def __init__(self, name='DEFAULT_NAME'): 5 self._class_name = name 6 self._list_of_students = 
That was easy
Notice that we did not give the constructor a parameter for the
self._list_of_studentsattribute. We don’t need to!
Let’s write a method to add a student to the class
1def add_student(self, fN, lN, sN, avg): 2 a_student = EnthusiasticStudent(fN, lN, sN, avg) 3 self._list_of_students.append(a_student)
Let’s write a method to search the list of EnthusiasticStudents for a student with a specific first name. Return
Trueif it’s in the list,
1def find_student(self, fName): 2 for student in self._list_of_students: 3 if fName == student.get_first_name(): # this assumes we wrote a getter/setter 4 return True 5 return False
How should we convert the
MyStudentsobject into a string?
1 def __repr__(self): 2 s = self._class_name + '\n' 3 for student in self._list_of_students: 4 # Below we just convert the student to a string. 5 # the str(student) will automatically call the 6 # the student's __repr__ method. 7 s += str(student) + '\n\n' # Will work because we have a __repr__ for EnthusiasticStudent written 8 9 return s
Putting it Together¶
1# Only need these if using multiple files 2#from EnthusiasticStudent import * 3#from MyStudents import * 4 5some_class = MyStudents('CSCI 161') 6some_class.add_student('Greg', 'Allen', '54321', 98) 7some_class.add_student('Bob','Smith', '12345', 50) 8print(some_class.find_student('Bob')) 9 10print(some_class)