You can use Alex Martelli's venerable Bunch class. My favourite variety of it looks like
class Bunch(dict):
def __init__(self, **kwds):
self.update(kwds)
self.__dict__ = self
By comparison to the other answers here, this solution allows you to construct such a class inline, as an expression:
map_data = Bunch(
directions=[d for d in parsed_data.directions],
connections={c.start: Bunch(L=c.left, R=c.right) for c in parsed_data.connections})
print(map_data)
Also, because Bunch is a dict, this prints something nice!
{'directions': ['R', 'L'], 'connections': {'AAA': {'L': 'BBB', 'R': 'CCC'}, 'BBB': {'L': 'DDD', 'R': 'EEE'}, 'CCC': {'L': 'ZZZ', 'R': 'GGG'}, 'DDD': {'L': 'DDD', 'R': 'DDD'}, 'EEE': {'L': 'EEE', 'R': 'EEE'}, 'GGG': {'L': 'GGG', 'R': 'GGG'}, 'ZZZ': {'L': 'ZZZ', 'R': 'ZZZ'}}}
By comparison, a custom Object class (such as the current top answer), prints something not as nice:
<__main__.Object object at 0x7025cae62b90>
The fact that you can use Bunch as an expression also allows you to use it part of a list or dictionary comprehension, as above:
connections={c.start: Bunch(L=c.left, R=c.right) for c in parsed_data.connections})`
This would be quite difficult to do with any of the other solutions posted here.
You can also construct such an object directly from a dictionary:
my_dict = {'directions': 'LRLRLL', 'connections': []}
map_data = Bunch(**my_dict)
print(map_data)
Another big advantage of this solution over any of the other posted solutions is that your object is a dictionary, as well as an object. This means:
- If your existing code is using dictionary syntax (
map_data['directions']), you can migrate over to Bunch, and update the existing code gradually.
- Debugging is awesome! You can print, pretty print, iterate over keys / values, everything you would want to do with a dict!
a = object()and you needobj.a = object(). Again I am talking about the example, in your actual code an object inside an object might be useful.