JavaScript:関数の名前を取得する

Function オブジェクトの name プロパティで関数名を文字列として取得できることを知った。

Node.js の REPL で試してみるよ。

> function func1() {}
undefined
> func1.name
'func1'

ほんとだ。

アロー関数ではどうだろう?

> const func2 = () => {}
undefined
> func2.name
'func2'

ほうほう。代入先の変数名が返ってくるとな。

なら、これを別の変数に代入したら?

> func3 = func2
[Function: func2]
> func3.name
'func2'

えー??

ところで、関数の名前を文字列で取得して何に使えるのかと思ったら eval() があるのね。

でも「使うな」って書いてある。

Python: あるかどうかわからないメソッドを呼び出す

 んー、タイトルが何をいってるのかよくわからないけれども。

先日使った Lark の lark.Transformer や lark.Interpreter というクラスでは、構文木をたどりながら文法要素の名前をもつメソッドを呼び出していた。「文法要素の名前」はユーザが定義するので、ライブラリである Lark が予め知っているはずがない。でもちゃんと動いていた。ということは何らかの方法があるわけで、Ruby だったら Object#send を使えばいいんだけど Python ではどうやるんだろう、というわけで調べてみた。

こたえ: getattr() でクラスの持つメソッド(存在すれば)を取得できる

試しにこんなクラスを書いた。

>>> class User:
...     def name(self):
...         return 'Andy'
...     def age(self):
...         return 32
...     def info(self, key):
...         f = getattr(self, key)
...         return f()         

試してみよう。

>>> andy = User()
>>> andy.name()
'Andy'
>>> andy.age()
32         

ここまでは普通のメソッド呼び出し。次の User.info() が getattr() を使っている。

>>> andy.info('name')
'Andy'
>>> andy.info('age')
32         

存在しないメソッド名を指定すると AttributeError になる。

>>> andy.info('job')
Traceback (most recent call last):
  File "<stdin>", line 1, in 
  File "<stdin>", line 7, in info
AttributeError: 'User' object has no attribute 'job'         

なるほど。あとは必要に応じて AttributeError の処理をすればいいわけだな。理解した。