Python Forum
Thread Rating:
  • 0 Vote(s) - 0 Average
  • 1
  • 2
  • 3
  • 4
  • 5
OOP behaviour problem
#1
With the help of the many tutorials available I am teaching myself OOP. Or at least in the offset, discovering what OOP is all about and how it can structure coding and organises data. I have in general grasped the idea of instantiating classes and writing methods to manipulate data etc. The tutorials go something like this.

class Members:
    def __init__(self,lastname,firstname,age,):
        self.lastname = lastname
        self.firstname = firstname
        self.age = age

    def memdetails(self):
        return f"{self.firstname} {self.lastname} is {self.age} years old"

Lst = ["Smith","John",40,]
Mem1 = Members(Lst[0],Lst[1],Lst[2])
print (Mem1.memdetails())
This works fine and prints out "John Smith is 40 years old" as expected. But what occurs to me is that I need to know that John Smith is instantiated as Mem1 to get those details. I could of course change the code to
Smith = Members(Lst[0],Lst[1],Lst[2])
print (Smith.memdetails())
but I don't want to re-code every time I have a new member. I could try
Lst = ["Smith","John",40,]
Lst[0] = Members(Lst[0],Lst[1],Lst[2])
print (Lst[0].memdetails())
This works but if Lst[0] is changed in any way, then that instance of John Smith would be lost. For example
Lst = ["Smith","John",40,]
Lst[0] = Members(Lst[0],Lst[1],Lst[2])
print (Lst[0].memdetails())
Lst[0]="Smith"
print (Lst[0].memdetails())
gives an error on executing the second print (Lst[0].memdetails())statement

AttributeError: 'str' object has no attribute 'memdetails'

because when Lst[0] was instantiated it was changed from a string variable into an object of the Member class, but Lst[0]= "Smith" changed it back into a mere string variable again.

My question was going to be how to generate an instance name from a string variable, but writing this post has brought me to the conclusion that it is not possible, after all you can't name a List or a Tuple or any other object for that matter using a string. I guess instantiating a class is not designed to be used in that way. To get John Smiths details I'm going to have to loop around all the instance names until lastname = Smith is found. And adding or deleting a member would mean code changes.

That can't be right!!

Am I missing something Huh .
Reply
#2
(Aug-17-2020, 06:33 PM)JohnB Wrote: But what occurs to me is that I need to know that John Smith is instantiated as Mem1 to get those details.

As your initial class, that's absolutely correct. Imagine someone handed you 200 tuples you had to keep track of. You'd have to put them in some data structure (list or dict) and use that structure to find them in the future. At the moment your class is the same way. The instances don't do anything but hold the data for now.

But you could extend your class over time. You could make the instance initializer store any new instances in a global class structure (or probably an instance of another class). Then you could have a method that searches through that structure for you and returns the instances that match. Those just aren't in your class yet.

You've created a class for the Members and each instances stores information about one member. You need to have something like a class for the organization, and that class will create/delete Members, store them in an appropriate structure, and potentially search through them for the correct Member.
Reply
#3
The way you are creating objects is really odd. Why are you making a list? I understand if you want a list of members, but that is not what you are doing. This is how you would make a list of Members:
members = [
    Members('Smith, 'John', 40),
    Members('Doe', 'Jane', 21),
    Members('e', 'f', 3),
    Members('g', 'h', 4)
    ]
Forgive the single letter names but I dislike typing.

The idea of having a list of members is that you do not care which member is John Smith and which is Jane Doe. By putting them in a collection you are saying they are all the same, or at least that they can be treated generically. This is the beauty of collections, you don't have to know what they contain for them to be useful. If I wanted to print out a list of Members it is a simple as:
for member in members:
    print(member.memdetails)
Adding or deleting members is as simple as adding or deleting items from the collection. Deleting an item would require some sort of query that would return the Member object. You could the del member to delete the member or use list.remove(member) to remove the member from the list.

If you want to find a particular member by name you would search the list for an entry with a first and last name. Maybe you could add a method to Members that returns True if the member matches some characteristic.
def isme(lastname=None, firstname=None, age=None):
   if lastname and lastname != self.lastname:
        return False
   if firstname and firstname != self.firstname:
        return False
   if age and age != self.age
        return False
   return True

for member in members:
    if member.isme(age=40):
        print(member.memdetails)
This is where the myth of object oriented programming is often exposed. A database would be a much better tool for saving information about Members. A database may be object oriented, but many of them aren't, and that should not matter to you. The queries available in a database are going to be more powerful than are easily achieved using methods.

Nearly all introductions to OOP use examples that don't get much benefit from OOP. They want to introduce the ideas of inheritance and modularity and class and instance and variables and methods. They use contrived ideas like a Member is a subclass of Person and that a Person has a name and age and birthday and that a Member adds a fee and a billing data and a membership level. And then they will introduce the idea of a PersonList which has methods for organizing people, maybe saving and restoring them from memory or doing a search. And there will be a MemberList which is a subclass of PersonList which adds finding out who is tardy paying their fees.

OOP is a fine thing to learn. Just don't expect to be blown away by its amazing power. It is tool.
Reply
#4
Thanks for your replies.

I can see that I was treating objects more like a database that would take the place of Lists in a more structured way, which would be able to be accessed using a keyword. The type of object I posted seemed to lead in this direction, but not so.
I'm beginning to see that it's a way to make your own object and write your own methods to solve your own particular problems in a reusable and structured way. It would be used as all the other builtin object.methods but would execute your own unique code As deanhystad said: It's a tool

Onwards and upwards. Smile
Reply


Possibly Related Threads…
Thread Author Replies Views Last Post
  logger behaviour setdetnet 1 884 Apr-15-2023, 05:20 AM
Last Post: Gribouillis
  can someone explain this __del__ behaviour? rjdegraff42 1 716 Apr-12-2023, 03:25 PM
Last Post: deanhystad
  Asyncio weird behaviour vugz 2 1,250 Apr-09-2023, 01:48 AM
Last Post: vugz
  Weird behaviour using if statement in python 3.10.8 mikepy 23 3,592 Jan-18-2023, 04:51 PM
Last Post: mikepy
  Generator behaviour bla123bla 2 1,097 Jul-26-2022, 07:30 PM
Last Post: bla123bla
  Inconsistent behaviour in output - web scraping Steve 6 2,541 Sep-20-2021, 01:54 AM
Last Post: Larz60+
  Adding to the dictionary inside the for-loop - weird behaviour InputOutput007 5 2,701 Jan-21-2021, 02:21 PM
Last Post: InputOutput007
  Behaviour of 2D array SimonB 6 2,810 Jan-21-2021, 01:29 PM
Last Post: SimonB
  strange behaviour- plotting nathan_Blanc_Haifa 0 1,494 Dec-27-2020, 01:37 PM
Last Post: nathan_Blanc_Haifa
  understanding basic loop behaviour vinci 5 2,877 Feb-11-2020, 09:53 PM
Last Post: vinci

Forum Jump:

User Panel Messages

Announcements
Announcement #1 8/1/2020
Announcement #2 8/2/2020
Announcement #3 8/6/2020