少しのコードで、私が尋ねている理由と、これが重複していない理由を説明します。(私は願います)
>>> def foo():
... return 1
...
>>> bar=foo
>>> bar.__name__
'foo'
「バー」を取得するにはどうすればよいですか?
検査とフレームを試しましたが、これまでに見つけたものはすべてこのテストに失敗します。
少しのコードで、私が尋ねている理由と、これが重複していない理由を説明します。(私は願います)
>>> def foo():
... return 1
...
>>> bar=foo
>>> bar.__name__
'foo'
「バー」を取得するにはどうすればよいですか?
検査とフレームを試しましたが、これまでに見つけたものはすべてこのテストに失敗します。
bar
foo
は、すでに作成されたobject( )への単なる参照bar=foo
です。つまり、同じオブジェクトへの別の参照を作成したことを意味します。
In [62]: def foo():pass
In [63]: bar=foo
In [64]: spam=bar #another reference to foo function object
In [65]: spam.__name__,bar.__name__
Out[65]: ('foo', 'foo')
In [66]: spam is foo,bar is foo
Out[66]: (True, True)
In [67]: import sys
In [68]: sys.getrefcount(foo) # no of variable pointing to that object
Out[68]: 4 #3+1, 1 added by default by getrefcount()
を割り当てるbar = foo
と、まったく同じ値を参照する2つの名前が作成されます。Pythonにはそれらを区別する方法はありません。Pythonでの代入はデータをコピーすることはなく、名前が値を参照するようにするだけであり、関数は他の値と同じです。関数は1つだけで、は1つだけ__name__
です。
知っている場合は、他の関数がその関数に割り当てられているかどうfoo
かを確認できます。これにより、他のすべての参照globals()
が取得されることに注意してください。
>>> function_reference_names = [k for k, v in globals().iteritems() if hasattr(globals()[k], "func_name") and globals()[k].func_name == bar.__name__ and k != bar.__name__]
>>> function_reference_names
['bar']
しかし、他の人が指摘しているように、これを実行したい場合は、おそらく間違った質問をします。
興味深い質問ですが、関数はそれがどのような名前で呼ばれているかを知ることができますか?私の知る限り、この情報はスタックやその他の場所に保存されていないため、それをフェッチするには、ソース自体の情報を操作するために、より高い次元に移動するか、メタに移動する必要があります。
結果は役に立たないかもしれませんが、それは面白いです:)
以下は不器用なコードです:
import inspect
import io
import re
def get_my_name(func_obj):
caller_frame = inspect.currentframe().f_back.f_back
caller_mod = inspect.getmodule(caller_frame)
mod_src = inspect.getsource(caller_mod)
call_lineno = caller_frame.f_lineno
stream = io.StringIO(mod_src)
for i in range(0, call_lineno):
line = stream.readline()
m = re.findall('[_a-zA-Z0-9]+(?=\()', line)
m = [fname for fname in m if caller_frame.f_locals[fname] == func_obj]
return m
def some_func(n):
print(get_my_name(some_func))
return n*n
def caller():
f = some_func
return f(2)
caller()