Pandas is an extension of NumPy with useful column-based operations, suitable for this. While I could've customized my own library, it'll be too much of a liability of maintenance.
It provides excellent functions, on top of its indexing, with good performance on correct usage.
Item Prop Decorators
The custom Property decorators grabs the class' attribute _props and generates the functions.
For example, @item_props() uses _props and generates the following functions.
from reamber.base import item_props
from reamber.osu import OsuTimingPointMeta
from reamber.base.Timed import Timed
@item_props()
class OsuSv(OsuTimingPointMeta, Timed):
_props = dict(multiplier=['float', 1.0])
from reamber.osu import OsuTimingPointMeta
from reamber.base.Timed import Timed
import pandas as pd
class OsuSv(OsuTimingPointMeta, Timed):
@property
def multiplier(self) -> pd.Series:
return self.data['multiplier']
@multiplier.setter
def multiplier(self, val) -> None:
self.data['multiplier'] = val
As shown, the dictionary automatically creates the property functions.
List Prop Decorators
Similar to Item Prop Decorators, this affects lists
from reamber.base.Property import list_props
from reamber.osu.OsuSv import OsuSv
from reamber.base.lists.TimedList import TimedList
@list_props(OsuSv)
class OsuSvList(TimedList[OsuSv]):
...
from reamber.base.lists.TimedList import TimedList
from reamber.osu.OsuSv import OsuSv
import pandas as pd
class OsuSvList(TimedList[OsuSv]):
@property
def multiplier(self) -> pd.Series:
return self.df['multiplier']
@multiplier.setter
def multiplier(self, val) -> None:
self.df['multiplier'] = val
As shown, it uses the OsuSv class' dictionary to generate the property functions.