2

evalコード内の別の場所からのコンテキストを使用して、基本的に遅くする方法を見つけようとしています。例として、クラスFriendがあり、次のように使用できます。

>>> class A:
...     friend = Friend('B')
...
>>> class B:
...     friend = Friend('A')
...
>>> A.friend.getobject()
<class '__main__.B'>

ただし、Friendコード内の別の場所、別のライブラリで定義されており、次のようになります。

class Friend:

    def __init__(self, objname):
        self.objname = objname

    def getobject(self):
        return eval(self.objname, original_context)

sqlalchemy ORM には、列を定義するための同様のパターンがありますが、セッション内のすべての所有クラス (テーブルなど) を追跡することによって実装されています。必要に応じて同様のことを行うことができますが、これを行う別の方法があるかどうかを知りたいです。私はフレームとインタープリタースタックを見てきました。関連するフレームのローカルに のようなものを使用してアクセスできると思いますが、オブジェクトが定義される前に呼び出されるinspect.stack()[1][0].f_localsこれを行う必要があります。Frame.__init__

私の質問は を見つける方法original_contextですが、必要なときにのみです。Friendこれは 2 つの問題に帰着します: 1.インスタンス化された環境 (またはフレーム?) にアクセスする方法。getobject2.呼び出された時のアクセス方法。

4

1 に答える 1

2

完全修飾クラス名を使用する必要があります。つまり、次のようになります。

 class A:
     friend = Friend('themodule.B')

そして、その文字列を取り出し、モジュールを抽出して B クラスをインポートし、このように生成します。

ただし、一般に、より良い方法は次のとおりです。

 class A:
     friend = Friend(B)

この場合、 B はその時点では定義されていませんが、簡単に実行できます。

class A:
    pass

class B:
    pass

A.friend = Friend(B)
B.friend = Friend(A)
于 2012-04-20T07:02:19.557 に答える