2

かなり扱いにくいbashスクリプトをPythonに移植することを検討していますが、次の側面を処理する方法に固執しています。スクリプトのポイントは、動的にフェッチされたデータに応じてpng画像を生成することです。bashスクリプトはデータを取得し、convert多くのオプションを備えた非常に長いユーティリティの呼び出しを構築します。Pythonのテンプレート文字列は良い解決策のように見えましたが(共有ホスティングにデプロイするので、標準ライブラリ内にとどまるほうがはるかに好きです)、bashのように式を評価できないことがわかりました。

>>> from string import Template
>>> s = Template('The width times one is ${width}')
>>> s.substitute(width=45)
'The width times one is 45'
>>> t = Template('The width times two is ${width*2}')
>>> t.substitute(width=45)
# Raises ValueError

私のbashスクリプトはそのような算術にかなり依存しているので(そうでなければ、追跡する変数の数は指数関数的に増加します)、Pythonでこの動作をエミュレートする方法があるかどうか知りたいです。私は、ほぼ同じ質問をしているこの質問にコメントがあり、次のように読んでいるのを見ました。

直感に反するため、これは非常に非Python的です。文字列は単なる文字列であり、コードを実行するべきではありません。

この場合、この問題に取り組むためのより慣用的な方法は何でしょうか。上にリンクされた質問に対する提案された答えは、%構文またはformat()関数のいずれかで文字列フォーマットを使用することですが、それは私の文字列内の変数の数(約50)ではうまく機能しないと思います。

4

4 に答える 4

3

組み込みの文字列フォーマットを使用してみませんか?

width = 45
"Width times one is {width}".format(width=width)
"Width times two is {width}".format(width=2*width)

結果は

Width times one is 45
Width times two is 90
于 2012-05-28T22:55:20.403 に答える
2

この問題に対するPythonの解決策は、文字列のフォーマットを忘れて、引数のリストsubprocessを関数の1つに渡すことです。

# I have no idea about convert's command line usage,
# so here's an example using echo.
subprocess.call(["echo", str(1 + 1), "bla"])

そうすれば、単一の文字列を作成する必要も、引用符について心配する必要もありません。

于 2012-05-28T22:57:11.820 に答える
2

おそらく、より優れたテンプレートエンジンが必要です。Jinja2この種のものともっとたくさんをサポートします。標準ライブラリにこれほど強力なものはないと思いますが、私が考えたところ、ライブラリは純粋なPythonであるため、コピーするだけでアプリケーションに統合できます。

Jinjaが何らかの理由であなたに合わない場合は、Pythonwikiを見てください。Pythonwikiには、これらの種類のライブラリ専用のセクションがあります。その中には、非常に軽量なTempliteがあります。これは、たった1つのクラスであり、必要なことを正確に実行しているようです。

于 2012-05-28T23:01:38.100 に答える
2

仕事はそれほど難しくありません、なぜあなたはただ楽しみのためにいくつかのコーディングを作ってみませんか?そして、これがほぼあなたが望むことをする関数です。

import re
def TempEval(template,**kwargs):
    mark = re.compile('\${(.*?)}')
    for key in kwargs:
        exec('%s=%s'%(key,kwargs[key]))
    for item in mark.findall(template):
        template=template.replace('${%s}'%item,str(eval(item)))
    return template


print TempEval('The width times one is ${width}',width=5)
#The width times one is 5
print TempEval('The width times two is ${width*2}',width=5)
#The width times two is 10
于 2012-05-28T23:34:04.947 に答える