1

我编写了一个小的 python 包,它通过一些额外的方法扩展了 pandas 数据框。

目前,我的包中有以下代码:

def init():
    @pd.api.extensions.register_dataframe_accessor("test")
    class _:
        def __init__(self, pandas_obj):
            self._obj = pandas_obj

        def myMethod(self):
            pass

然后我在python中执行以下操作:

import pandas as pd
import mypackage as mp
mp.init()
test = pd.Dataframe(<define data frame>)
test.mp.myMethod()

我的问题是,是否可以__init__.py在 mypackage 中进行 pandas 导入和注册访问器,这样一旦 mypackage 被导入,我就可以在没有 init() 步骤的情况下自动访问 mymethod?我目前的方法感觉有点笨拙......

4

1 回答 1

2

我可能在你的问题中遗漏了一些东西,但我认为你可能是在吠叫错误的树。在这方面没有什么特别__init__.py的——你写的任何东西__init__.py都是在你导入包时执行的,所以我认为你根本不需要那个init()函数。如果您的文件包含:

# mypackage/__init__.py
import pandas as pd


@pd.api.extensions.register_dataframe_accessor("test")
class _:
    def __init__(self, pandas_obj):
        self._obj = pandas_obj

    def myMethod(self):
        print(self._obj)

现在你可以通过导入来使用它mypackage

>>> import pandas as pd
>>> import mypackage
>>> df = pd.DataFrame({'a': [1, 2, 3]})
>>> df.test.myMethod()
   a
0  1
1  2
2  3

顺便说一句,您可能明确想要类似您的init()函数的一个原因是最不意外的原则:由于为所有用户(包括其他库)register_dataframe_accessor修改实例的命名空间,因此您的仅通过导入您的包可能会覆盖DataFrame的可能性很小register_dataframe_accessor如果它们碰巧共享相同的名称,则其他包的数据帧访问器。

如果名称相当独特,那么这可能不是问题。它也可能根本不是您的包裹的问题,具体取决于它的使用方式。

于 2019-11-06T11:52:04.600 回答