Pandas DataFrame наследование объекта или использование объекта?

Я создаю библиотеку для работы с очень конкретными структурированными данными, и я строю свою инфраструктуру поверх панд. В настоящее время я пишу кучу разных контейнеров данных для разных случаев использования, таких как CTMatrix для данных времени страны x и т. д. для размещения методов, подходящих для всех структурированных данных CountryxTime.

в настоящее время я обсуждаю между

Вариант 1: Объект Наследования

class CTMatrix(pd.DataFrame):
    methods etc. here

или 2: Объект

class CTMatrix(object):
    _data = pd.DataFrame

    then use getter, setter methods to control access to _data etc. 

С точки зрения разработки программного обеспечения есть ли очевидный выбор здесь?

мои мысли до сих пор:

Вариант 1:

  1. можно использовать методы DataFrame непосредственно в классе CTMatrix (например,CTmatrix.sort()) без необходимости поддерживать их с помощью методов на инкапсулированном _data объект в опции #2
  2. обновления и новые методы в панд наследуются, за исключением методов, которые могут быть перезаписаны локальными методами класса

но

  1. осложнения с некоторыми методами, такими как __init__() и необходимость передавать атрибуты до суперкласса super(MyDF, self).__init__(*args, **kw)

Вариант 2:

  1. больше контроля над классом и его поведение
  2. возможно, более устойчивы к обновлениям в панд?

но

  1. использование getter () или не скрытый атрибут для использования объекта как фрейма данных, например (CTMatrix.data.sort())

есть ли какие-либо дополнительные недостатки для принятия подхода в варианте № 1?

2 ответов


Я бы избегал подклассов DataFrame, потому что многие DataFrame методы возвращают новый DataFrame, а не другой экземпляр CTMatrix "объект".

есть несколько открытых проблем на GitHub вокруг этого, например:

в более общем плане, это вопрос композиция против наследования. Я бы особенно опасался выгоды №2. Это может показаться отличным сейчас, но если вы не следите за обновлениями панд (и это быстро движущаяся цель), вы можете легко закончить с неожиданными последствиями, и ваш код будет в конечном итоге переплетен с пандами.


из-за подобных вопросов и ответа Матти Джона я написал _pandas_wrapper класс для моего проекта, потому что я также хотел унаследовать от pandas Dataframe.

https://github.com/mcocdawc/chemcoord/blob/bdfc186f54926ef356d0b4830959c51bb92d5583/src/chemcoord/_generic_classes/_pandas_wrapper.py

единственная цель этого класса-дать Pandas DataFrame lookalike, который является безопасным для наследования.

Если ваш проект LGPL лицензию вы можете использовать его без проблем.