'Python: how to create list of objects that are subset from another

I have a class called Reader which is composed as follows:

class Reader:
    name = None
    id = None

reader1 = Reader(name='Entrance', id=1)
reader2 = Reader(name='Exit', id=2)
reader3 = Reader(name='Hallway', id=3)
reader4 = Reader(name='Reception', id=4)

Then I have another class called Doorgroup which is composed of Reader objects

class Doorgroup:
    name = None
    readers = []

doorgroup1 = Doorgroup(name='Borders', readers=[reader1, reader2])
doorgroup2 = Doorgroup(name='Insides', readers=[reader3, reader4])
doorgroup3 = Doorgroup(name='Admin', readers=[reader1, reader2, reader3, reader4])
doorgroup4 = Doorgroup(name='IN', readers=[reader1, reader3, reader4])
doorgroup5 = Doorgroup(name='OUT', readers=[reader2])

Now I have arrays of int representing the reader ids that I want to convert to Doorgroup instances.

For example: [1, 2] would return [doorgroup1, doorgroup3, doorgroup5] since [1, 2] are a part of readers of doorgroup1, doorgroup3 and [2] is part of doorgroup5

I am new to python but Is there a way where I can implement this logic?



Solution 1:[1]

If you want to create Reader objects in that way, then you will need to create an __init__ method with name and id as arguments (as well as self). Similarly for Doorgroup objects. See the below class definitions.

Rather than having reader1, reader2, and so on as separate variables, it would be easier to create a dictionary (a container of key: value pairs) whereby each key denotes the number of the reader (e.g. 1 or 2 or 3 and so on) and value is the corresponding Reader instance. Similarly for Doorgroup objects.

The following code makes the above changes. If I have interpreted your question correctly, it also achieves your desired translation from a list of ids to a list of Doorgroup objects. In my implementation, the final 'list' of Doorgroup objects is in fact a set but you can easily convert it to a list via list() if you need a list instead. The reason that we use a set (a container of distinct hashable objects) is because it guarantees that a Doorgroup object will not be added if it is already inside the set.

Please let me know if there are any questions! I hope that this helps.

class Reader:
    def __init__(self, name = None, id = None):
        self.name = name
        self.id = id

class Doorgroup:
    def __init__(self, name = None, readers = []):
        self.name = name
        self.readers = readers

# create instances of Reader, store them in dict where a key is an id
# and the associated value is a Reader instance
readers = {}
readers[1] = Reader(name = 'Entrance', id = 1)
readers[2] = Reader(name = 'Exit', id = 2)
readers[3] = Reader(name = 'Hallway', id = 3)
readers[4] = Reader(name = 'Reception', id = 4)

# create instances of Doorgroup, store them in a dict where a key is the
# Doorgroup instance number and the value is a Doorgroup instance
dgroups = {}
dgroups[1] = Doorgroup(name = 'Borders', readers = [readers[1], readers[2]])
dgroups[2] = Doorgroup(name = 'Insides', readers = [readers[3], readers[4]])
dgroups[3] = Doorgroup(name = 'Admin', readers = [readers[1], readers[2],
    readers[3], readers[4]])
dgroups[4] = Doorgroup(name = 'IN', readers = [readers[1], readers[3],
    readers[4]])
dgroups[5] = Doorgroup(name = 'OUT', readers = [readers[2]])

# Convert list of ids to set of Doorgroup instances
ids = [1, 2]
result = set()

for key in dgroups:
    for i in ids:
        if readers[i] in dgroups[key].readers:
            result.add((key, dgroups[key]))

print(result)

Output

{(4, <__main__.Doorgroup object at 0x7fabe5857ca0>), (5, <__main__.Doorgroup object at 0x7fabe5857c40>), (3, <__main__.Doorgroup object at 0x7fabe5857d00>), (1, <__main__.Doorgroup object at 0x7fabe5857dc0>)}

The output set has elements that are 2-tuples whereby the 1st element of each 2-tuple denotes the number of the Doorgroup instance. You didn't ask for this number but I have included it as it is useful for verifying that the code works.

Sources

This article follows the attribution requirements of Stack Overflow and is licensed under CC BY-SA 3.0.

Source: Stack Overflow

Solution Source
Solution 1