Reputation: 97
I want to make a for
loop where I search all the class objects' self.name
values to match a user input. Here's the code:
import json
class Planets(object):
def __init__(self, name, radius, sgp, soi, atmo_height, moons=()):
self.name = name
self.radius = radius
self.sgp = sgp
self.soi = soi
self.atmo_height = atmo_height
self.moons = moons
def __repr__(self):
return f"{self.name}, {self.radius} m, {self.sgp}, {self.soi}, {self.atmo_height}, Moons: {', '.join([moon['name'] for moon in self.moons])}"
class Moons(Planets):
def __init__(self, name, radius, sgp, soi, atmo_height, apoapsis, periapsis):
super().__init__(name, radius, sgp, soi, atmo_height)
self.apoapsis = apoapsis
self.periapsis = periapsis
def __repr__(self):
return f"{self.name}, {self.radius} m, {self.sgp}, {self.soi}, {self.atmo_height}, {self.apoapsis}, {self.periapsis}"
with open('Planets.json', 'r') as p:
planets = json.load(p)
with open('Moons.json', 'r') as m:
moons = json.load(m)
# Planet Objects
moho = Planets(**planets["Planets"]["Moho"])
eve = Planets(**planets["Planets"]["Eve"])
kerbin = Planets(**planets["Planets"]["Kerbin"])
duna = Planets(**planets["Planets"]["Duna"])
dres = Planets(**planets["Planets"]["Dres"])
jool = Planets(**planets["Planets"]["Jool"])
#Moon Objects
gilly = Moons(**moons["Moons"]["Gilly"])
mun = Moons(**moons["Moons"]["Mun"])
minmus = Moons(**moons["Moons"]["Minmus"])
ike = Moons(**moons["Moons"]["Ike"])
laythe = Moons(**moons["Moons"]["Laythe"])
vall = Moons(**moons["Moons"]["Vall"])
tylo = Moons(**moons["Moons"]["Tylo"])
bop = Moons(**moons["Moons"]["Bop"])
pol = Moons(**moons["Moons"]["Pol"])
So, basically, the idea would be something like, user inputs the name "Jool", the for
loop iterates through all objects in the Planets
and Moons
classes until they find an object with the value "Jool"
for the "name"
key.
How can I do this?
Upvotes: 1
Views: 1877
Reputation: 110166
Ordinarily, taking note of all instances of a class is not done automatically by Python or other languages.
However, you can do that by adding code in the __init__
method to register each instance as it is created in a "registry"of your choice.
This "registry" is any data structure which will track your instances - a simple dictionary can be enough for most cases. You can then just keep this dictionary at the module level, or as a class attribute: an attribute that is present on the class and shared across all instances.
If one is not doing some "production level code" which would have to handle all sorts of random events and misuses (for example, if one creates a Planet with a name that is already registered), the code can be quite simple.
Since the code would be common across Planets
and Moons
, it is a case for using class inheritance, and share the common functionality, without the functionality getting in the way of what you want to handle in Planets
class Registerable:
registry = {}
def __init__(self, name):
cls = self.__class__ # optional for readability
cls.registry[name] = self
super().__init__()
class Planets(Registerable):
registry = {}
def __init__(self, name, radius, sgp, soi, atmo_height, moons=()):
super().__init__(name)
self.name = name
self.radius = radius
self.sgp = sgp
self.soi = soi
self.atmo_height = atmo_height
self.moons = moons
...
class Moons(Planeys):
registry = {} # each class have to declare its own registry, otherwise they are all shared with the base class
And then you can iterate on your instances using Planets.registry and Moons.registry as normal Python dictionaries.
Upvotes: 1
Reputation: 248
You put all your Moons and Planets in a list.
for item in moons_planets_list:
if item.name == user_input:
#Do sth
Upvotes: 1