web-dev-qa-db-ja.com

文字列にlocals()およびformat()メソッドを使用する:警告はありますか?

次のパターンの使用について、不利な点、警告、または悪い習慣の警告はありますか?

_def buildString(user, name = 'john', age=22):
    userId = user.getUserId()
    return "Name: {name}, age: {age}, userid:{userId}".format(**locals())
_

非常に反復的な文字列生成コードを記述していたので、これを使いたくなりましたが、locals()の使用について何か不快に感じました。これで予期しない動作の危険はありますか?

編集:コンテキスト

私は常に次のようなものを書いていることに気づきました:

_"{name} {age} {userId} {etc}...".format(name=name, age=age, userId=userId, etc=etc)
_
47

Python 3.6.0: formatted string literals のように、これを行う公式の方法があります。

それはこのように動作します:

f'normal string text {local_variable_name}'

例えば。これらの代わりに:

"hello %(name)s you are %(age)s years old" % locals()
"hello {name}s you are {age}s years old".format(**locals())
"hello {name}s you are {age}s years old".format(name=name, age=age)

これを行うだけです:

f"hello {name}s you are {age}s years old"

これが公式の例です:

>>> name = "Fred"
>>> f"He said his name is {name}."
'He said his name is Fred.'
>>> width = 10
>>> precision = 4
>>> value = decimal.Decimal("12.34567")
>>> f"result: {value:{width}.{precision}}"  # nested fields
'result:      12.35'

参照:

26
Jacktose

書式文字列がユーザー指定でない場合、この使用法は問題ありません。

formatは、文字列置換に古い%を使用するよりも優先されます。
locals はPythonに組み込まれており、その動作は信頼できます。

localsはまさにあなたが必要としていることをしていると思います。
ローカルの辞書を変更しないでください。かなり良い解決策があると思います。

書式文字列がユーザーが指定した場合、あらゆる種類の悪意の注入攻撃を受けやすくなります。

29
Prashant Kumar

前Python 3.6回答

これは非常に古いですが、.format渡すことで遭遇した1つの警告**localsは、その変数がどこにも定義されていない場合、壊れるということです。渡される変数を明示的に指定すると、ほとんどの最新のIDEでこれを回避できます。

foo = "bar"
"{foo} and {baz} are pair programming".format(**locals())
<exception occurs>
2
Pureferret