翻訳者から :
Pythonを学び始めたばかりです。 最初の知り合いから、言語は素敵なデザインに満足し、構文の読みやすさとコードの理解を保証しました。
マスタリングの過程で、自分のコードを書くとき、Pythonの観点から選択したメソッドの正確性を疑うことがあります( PEP 8-必要に応じて、 Pythonコードのスタイルガイド )。 プログラミングのイデオロギーを理解するために、Pythonコミュニティでは、すべての人の喜びに加えて、徹底的なドキュメントに加えて、 Pythonヒント、トリック、およびハックという記事など、多くのサポート資料が既に蓄積されています。
私はDavid Goodgerの記事「 本物のPitonistのようなコードを書く:Python Idiomatic」( David Goodgerの「Codeista a a Pythonista:Idiomatic Python」 )が好きでした 。 最高の同化のために、(スキルのおかげで)本格的な翻訳を作成することにしました。それから、Habrと共有するのは賢明なアイデアに思えました。
翻訳作業中に、記事がオリジナルで読んだときよりもはるかに大きいことに気付いたので、Habr記事の形式から外れないように、部分的に投稿します。
翻訳の継続と完了 。
本物のPythonistのようなコードを書く:Pythonイディオム
デビッド・グッドガー
goodger@python.org
http://python.net/~goodger
このインタラクティブなチュートリアルでは、ツールキットを確実に拡張する多くの重要なPythonのイディオムと高度なテクニックを取り上げます。
このプレゼンテーションには3つのバージョンがあります。
クリエイティブコモンズ
アトリビューション/ Share-Alike(BY-SA)ライセンス。
私について:
- 私はモントリオールに住んでいます
- 二人の子供の父親、一人の女性の夫
- Pythonフルタイムプログラマー(フルタイムPythonプログラマー)、
- DocutilsプロジェクトおよびreStructuredTextの作成者 、
- Python Enhancement Proposals(またはPEP)エディター、
- PyCon 2007の主催者、およびPyCon 2008の議長、
- Python Software Foundationのメンバー、
- 昨年はファンドディレクター、今年は秘書。
このチュートリアルをPyCon 2006カンファレンス(Text&Data Processingと呼ばれる)で発表しましたが、使用したいくつかの方法に対する反応に驚き、よく知られていると考えました。 しかし、多くのリスナーは、Pythonプログラマーが考えずに使用しているメソッドを知らなかった。
あなたの多くは、以前にいくつかのイディオムとメソッドを見ることができました。 また、これまでに見たことのないいくつかのコツを学び、おそらく既に知っているものについて何か新しいことを学ぶと信じています。
Zen Python(1)
これらはPythonの基本原則ですが、拡張解釈です。 ユーモアのセンスは、彼らの正しい理解のために必要なだけです。
コメディスケッチ団にちなんで名付けられたプログラミング言語を使用する場合、ユーモアのセンスがあることが最善です。
いよりも美しい。
明示的は暗黙的よりも優れています。
単純なものは複雑なものよりも優れています。
複雑さは混乱するよりも優れています。
ネスティングよりフラットの方が優れています。
スパースは、デンスよりも優れています。
読みやすさが重要です。
例外は、規則を破るほど例外的ではありません。
実用性は美しさよりも重要ですが。
間違いは黙って通過するべきではありません。
明確にdrれていなければ。
...
Zen Python(2)
あいまいな場合は、推測する誘惑をあきらめます。この「詩」は冗談として作成されましたが、実際にはPythonの哲学に関する多くの真実が含まれています。
これを行うには、1つ、できれば1つだけの明白な方法が必要です。
この道は最初は明らかではないかもしれませんが、オランダ出身でない限り(明らかに、Guido van Rossum-およそTransl。、ありがとうsgtpepを意味します )。
今までよりも良い。
しばしば今より良いことはありませんが。
実装を説明するのが難しい場合、これは悪い考えです。
実装の説明が簡単な場合、これはおそらく良い考えです。
名前空間は素晴らしいアイデアなので、さらに名前空間を作りましょう!
—ティムピーターズ
時間の経過とともに、Pythoneer Tim PetersはBDFLガイドの原則を20の短い格言に翻訳しましたが、そのうち19のみが記録されました。
http://www.python.org/dev/peps/pep-0020/
あなたは自分が誰であるかを決めることができます:PythoneerまたはPythonista。 これらの単語には関連する意味があります。
疑わしい場合:
import this <br/>
インタラクティブなPythonインタープリターでこれを試してください:
>>> import this <br/>
別のイースターエッグは次のとおりです。
>>> from __future__ import braces<br/>
File "<stdin></stdin>" , line 1 <br/>
SyntaxError : not a chance<br/>
たくさんのコメディアン! :-)
コーディングスタイル:可読性カウント(コーディングスタイル:可読性カウント)
プログラムは、人が読むために、また機械による実行のために偶然にのみ書かれるべきです。
—Abelson&Sussman、 コンピュータープログラムの構造と解釈(「コンピュータープログラムの構造と解釈」)
プログラムを読みやすく、明確にするようにしてください。
PEP 8:Pythonコードスタイルガイド
読む価値あり:
http://www.python.org/dev/peps/pep-0008/
PEP = Python拡張提案(Python開発の提案)
PEPは、Pythonコミュニティに情報を紹介するドキュメントであり、Pythonの新機能、そのプロセスまたは環境について説明しています。
Pythonコミュニティには、PEP 8でソースコードがどのように見えるかを記述する独自の標準があります。これらの標準は、C、C ++、C#、Java、VisualBasicなど、他の標準とは異なります。
Pythonではインデントとスペースが非常に重要であるため、Pythonコードのスタイルガイドでは標準インデントを使用しています。 リーダーシップがリーダーシップを堅持するのは賢明です!..ほとんどのオープンソースプロジェクトと(できれば)ホームプロジェクトもガイドラインに厳密に従います。
スペース1
- 1レベルのインデントに4つのスペース。
- タブはありません。
- タブとスペースを混在させないでください 。
これは、IDLEおよびEmacs Pythonモードで正確にサポートされています。 他の編集者もこれを行うことができます。
- 関数間の空行。
- クラス間の2つの空行。
スペース2
- 辞書、リスト、タプル、引数リストの「、」の後にスペースを追加し、辞書の「:」の後にスペースを追加します。
- 割り当てと比較の周りにスペースを挿入します(引数リストを除く)。
- 括弧内または引数リストの前にスペースはありません。
- ドキュメントの行の先頭と末尾にスペースはありません。
def make_squares (key, value = 0 ):<br/>
"""Return a dictionary and a list...""" <br/>
d = {key: value}<br/>
l = [key, value]<br/>
return d, l<br/>
命名
- 関数、メソッド、属性の単一行
- 定数のjoined_lowerまたはALL_CAPSOM
- クラスのStudlyCaps
- camelCase は事前に定義された規則に一致する場合のみ
- 属性:interface、_internal、__ private
__privateフォームを避けるようにしてください。 私はこれを決して使用しません。 信じて 使用した場合、 後悔します。
説明
C ++ / Javaの後に来る人々は、最初はこの「機能」を誤って過度に使用する傾向があります。 __private名は、JavaまたはC ++のようには機能しません。 名前マングリングメカニズムを「起動」するだけで、サブクラスでの名前空間の偶発的な衝突を防ぐことができます。MyClass.__ privateはMyClass._MyClass__privateになります。 (これは、たとえば、別のモジュールで定義されたサブクラスなど、スーパークラスと同じ名前のサブクラスでも機能することに注意してください。)したがって、クラス外の__private名へのアクセスは可能ですが、不便で壊れやすい(これは正確な名前への依存性を追加しますスーパークラス)。
問題は、クラスの作成者が「この属性/メソッド名はプライベートで、このクラス定義内でのみアクセス可能でなければならない」と自然に考え、__ private宣言を使用できることです。 ただし、後でこのクラスのユーザーは、この名前へのアクセスを正当に必要とするサブクラスを作成できます。 これを行うには、スーパークラスを変更する(これは困難または不可能になる可能性があります)か、サブクラスコードで名前変換(マングル名)を適用します(せいぜいくて壊れやすい)。
これがPythonの概念です。「私たちはここにいる大人です」。
__privateフォームを使用する場合、誰から属性を保護しますか? スーパークラスの属性を正しく使用するのはサブクラスの責任であり、スーパークラスの属性を正しく文書化するのはスーパークラスの責任です。
これらの目的には、単一の下線_internalで始まる宣言を使用することをお勧めします。 名前は翻訳しません。 他の人に「これに注意してください。これは内部メカニズムの実装です。 完全に理解しない限り、触らないでください。」 しかし、これは単なる合意です。
ここの答えにはいくつかの良い説明があります:
- http://stackoverflow.com/questions/70528/why-are-pythons-private-methods-not-actually-private
- http://stackoverflow.com/questions/1641219/does-python-have-private-variables-in-classes
長いコード行(行)とその継続
コードの行の長さは80文字以内にしてください。
括弧内の暗黙的な行拡張を使用します。
def __init__ ( self , first, second, third,<br/>
fourth, fifth, sixth):<br/>
output = (first + second + third<br/>
+ fourth + fifth + sixth)<br/>
バックスラッシュを使用:
VeryLong . left_hand_side \<br/>
= even_longer . right_hand_side()<br/>
バックスラッシュは慎重に使用してください。 それらが含まれる行を終了する必要があります。 バックスラッシュの後にスペースを追加すると、機能しなくなります。 したがって、コードが多少汚染されています。
長い弦
隣接するリテラル文字列(文字)は、パーサーによって連結されます。
>>> print 'o' 'n' "e" <br/>
one<br/>
文字間のスペースは必要ありませんが、コードを読みやすくするのに役立ちます。 任意のタイプの引用符を使用できます。
>>> print 't' r'\/\/' """o""" <br/>
t\ / \ / o<br/>
「r」で始まる行は「生」です。 バックスラッシュは、生の行のエスケープ文字とは見なされません。 これらは、Windowsファイルシステムの正規表現とパスに使用されます。
名前付き文字列オブジェクトは連結しないことに注意してください。
>>> a = 'three' <br/>
>>> b = 'four' <br/>
>>> a b<br/>
File "<stdin>" , line 1 <br/>
a b<br/>
^ <br/>
SyntaxError : invalid syntax<br/>
これは、自動連結がPythonパーサー(パーサー)の機能であり、インタープリターの機能ではないためです。 実行時に行を連結するには、+演算子を使用する必要があります。
text = ( 'Long strings can be made up ' <br/>
'of several shorter strings.' )<br/>
括弧を使用すると、コード行を暗黙的に連結できます。
複数行の文字列値を指定するには、三重引用符を使用します。
"""Triple<br/>
double<br/>
quotes""" <br/>
'''\<br/>
Triple<br/>
single<br/>
quotes\<br/>
''' <br/>
最後の例(単一引用符)では、バックスラッシュを使用して行終了文字をエスケープする方法に注目してください。 これにより、左マージンに揃えられたテキストと引用符を保存するときに、不要な行終了文字がなくなります。 バックスラッシュは、このような各行の最後にある必要があります。
複合ステートメント
良い:
if foo == 'blah' :<br/>
do_something()<br/>
do_one()<br/>
do_two()<br/>
do_three()<br/>
悪い:
if foo == 'blah' : do_something()<br/>
do_one(); do_two(); do_three()<br/>
スペースとインデントは、プログラムフローの便利な視覚的インジケータです。 上記の「Good」コードの2行目のインデントは、条件による何かの実行を読者に示し、「Bad」にインデントが存在しないことは「if」条件を隠します。
1行のコードに関する多くのステートメントは重大な罪です。 Pythonでは、 読みやすさが重要です。
ドキュメントの行とコメント
ドキュメント行=コードの使用方法
コメント= 理由 (合理的な正当化)とコードの仕組み
ドキュメント行では、コードの使用方法とコードのユーザー向けに説明しています。 ドキュメント行の使用:
- たとえ誰にも明らかでない場合でも、関数の目的を後で説明してください。
- 予想されるパラメーター、戻り値、およびスローされる例外を説明します。
- メソッドが単一の呼び出しに密結合している場合は、呼び出し元のステートメントと何らかの接続を作成します(ただし、呼び出し元のステートメントは後で変更される可能性があるため注意してください)。
コメントはその理由を説明し、コードのメンテナーに必要です。 例には、次のような自分用のメモが含まれます。
# !!! BUG: ... <br/>
<br/>
# !!! FIX: This is a hack <br/>
<br/>
# ??? Why is this here? <br/>
これらのグループにはどちらもあなたが含まれているので、適切なドキュメント行とコメントを書いてください !
ドキュメント行は、インタラクティブに(help())および自動ドキュメントシステムに使用されます。
誤ったコメントとドキュメンテーション行は、まったくないよりも悪いです。 すぐに保存してください! 変更を行うときは、コメントとドキュメント行がコードと一致し、矛盾しないことを確認してください。
PEPには、ドキュメンテーションラインの規則全体、PEP 257、「Docstringの規則」があります。
http://www.python.org/dev/peps/pep-0257/
実用性が清潔さを獲得
愚かな一貫性は、心に近い小さな怪物です(愚かな一貫性は、小さな心のホブゴブリンです)。
—ラルフ・ウォルド・エマーソン
( hobgoblin :迷信的なもの)
(注:transl。:私が理解しているように、意味は「神に祈るために愚か者を教える-彼は額を折る」)
常に例外があります。 PEP 8から:
矛盾が生じた場合、それは非常に重要です-マニュアルに従うことが単に受け入れられないことが起こります。 疑わしい場合は、あなたの意見に最適なソリューションを使用してください。 他の例を見て、どちらの視点が良いかを決めてください。 お気軽にお問い合わせください!
受け入れられているルールを破る2つの理由:
- ルールに従うと、ルールに従うことに慣れている人でも、コードは読みにくくなります。
- 周囲のコードに準拠するために、違反することも可能です(これは歴史的な理由による可能性があります)-混乱を招く可能性があります(本当のXPスタイル(eXtreme Programming-注:Transl。))。
...しかし、実用性は常に清潔さを妨げるべきではありません!
イディオムのポプリ
小さくて便利なイディオムの選択。
次に、チュートリアルの主要部分である多くのイディオムに進みます。
簡単なものから始めて、徐々にレベルを上げていきます。
価値の交換
他の言語で:
temp = a<br/>
a = b<br/>
b = temp<br/>
Pythonの場合:
b, a = a, b<br/>
これを見たことがあるかもしれません。 しかし、これがどのように機能するか知っていますか?
- コンマは、タプルコンストラクターの構文です。
- タプルが右側に作成されます(タプルのパッケージ化)。
- 左側のタプルは割り当てターゲットです(タプルの展開)。
右側は、左側のタプルの名前で展開されます。
その他の開梱例:
>>> l = [ 'David' , 'Pythonista' , '+1-514-555-1234' ]<br/>
>>> name, title, phone = l<br/>
>>> name<br/>
'David' <br/>
>>> title<br/>
'Pythonista' <br/>
>>> phone<br/>
'+1-514-555-1234' <br/>
構造化データの処理に役立つループ:
上記でリストを作成しました(Davidの情報)。 people-2つの要素を含む人々のリスト。各要素は3つの要素のリストです。
>>> people = [l, [ 'Guido' , 'BDFL' , 'unlisted' ]]<br/>
>>> for (name, title, phone) in people:<br/>
... print name, phone<br/>
... <br/>
David + 1 - 514 - 555 - 1234 <br/>
Guido unlisted<br/>
各people要素は、フォーム(名前、役職、電話番号)のタプルに展開されました。
構造を左右に一致させることを忘れないでください!
>>> david, (gname, gtitle, gphone) = people<br/>
>>> gname<br/>
'Guido' <br/>
>>> gtitle<br/>
'BDFL' <br/>
>>> gphone<br/>
'unlisted' <br/>
>>> david<br/>
[ 'David' , 'Pythonista' , '+1-514-555-1234' ]<br/>
タプルの詳細
カンマがかっこなしのタプルコンストラクタである方法を確認しました。 例:
>>> 1 ,<br/>
( 1 ,)<br/>
Pythonインタープリターは、わかりやすくするために括弧を示しています。これらも使用することをお勧めします。
>>> ( 1 ,)<br/>
( 1 ,)<br/>
コンマを忘れないでください!
>>> ( 1 )<br/>
1 <br/>
単一要素のタプルには、末尾のコンマが必要です。 2+タプルでは、末尾のコンマはオプションです。 0タプルまたは空のタプルでは、一対の括弧は短縮構文です。
>>> ()<br/>
()<br/>
>>> tuple ()<br/>
()<br/>
一般的なタイプミスは、タプルを作成したくない場合でも、コードにカンマを残すことです。 コードで簡単にスキップできます:
>>> value = 1 ,<br/>
>>> value<br/>
( 1 ,)<br/>
したがって、待機していないタプルが表示された場合は、コンマを探してください!
インタラクティブな「_」
これは本当に便利な機能であり、それを知っている人がほとんどいないことは驚くべきことです。
インタプリタのインタラクティブモードでは、式または関数呼び出しを試みるたびに、結果は一時変数_(アンダースコア)に保存されます。
>>> 1 + 1 <br/>
2 <br/>
>>> _<br/>
2 <br/>
_は、 printコマンドによって最後に印刷された式を保存します。 便利です!
ただし、インタープリターの対話モードでのみ機能し、モジュールでは機能しません。
タスクをインタラクティブに操作していて、次のステップのために結果を保存したい場合に特に便利です。
>>> import math <br/>
>>> math . pi / 3 <br/>
1.0471975511965976 <br/>
>>> angle = _<br/>
>>> math . cos(angle)<br/>
0.50000000000000011 <br/>
>>> _<br/>
0.50000000000000011 <br/>
部分文字列から文字列を作成する
行のリストから始めましょう:
colors = [ 'red' , 'blue' , 'green' , 'yellow' ]<br/>
すべての行を1つの大きな行に結合します。 特に部分文字列が多い場合...
これをしないでください:
result = '' <br/>
for s in colors:<br/>
result += s<br/>
非常に非効率的です。
これはひどくメモリを消費し、パフォーマンスを低下させます。 合計は、各中間ステップでオブジェクトを計算、保存、および破棄します。
代わりに、これを行います:
result = '' . join(colors)<br/>
join()文字列メソッドは、1回のパスですべてのコピーを実行します。
数十行または数百行を扱う場合、これは目立った違いをもたらしません。 しかし、回線を効率的に収集することに慣れてください。何千もの回線を使用して、ループで作業しているときに勝つことができるからです。
弦楽器の構成、バリエーション1
join()メソッドを使用するいくつかの方法を以下に示します。
サブストリング間にスペースを入れたい場合:
result = ' ' . join(colors)<br/>
またはコンマとスペース:
result = ', ' . join(colors)<br/>
一般的な場合:
colors = [ 'red' , 'blue' , 'green' , 'yellow' ]<br/>
print 'Choose' , ', ' . join(colors[: - 1 ]), \<br/>
'or' , colors[ - 1 ]<br/>
文法的に正しい文を作成するには、すべての値の間にコンマを入れ、最後の単語の前に「または」という単語を置きます。 ここでは、スライスの構文が役立ちます。 「Slice to -1」([:-1])は、最後から2番目の要素のインデックスを提供します。これは、コンマで区切ってスペースでアタッチします。
もちろん、リストの長さが0または1の場合、このコードは機能しません。
結論:
Choose red, blue, green or yellow<br/>
弦の構成、バリエーション2
サブストリングを生成する関数を適用する必要がある場合:
result = '' . join(fn(i) for i in items)<br/>
これはジェネレータ式を使用します。これについては後で説明します。
部分文字列を段階的に計算する必要がある場合は、まずリストでそれらを収集します。
items = []<br/>
... <br/>
items . append(item) # many times <br/>
... <br/>
# items is now complete <br/>
result = '' . join(fn(i) for i in items)<br/>
結合文字列メソッドを適用できるように、パーツをリストに入れます
より効率的に。
翻訳の第二部