2012-01-18 14 views
1

まあ、私はPythonが大好きですが、主に次の2つの厄介なものを見つけます:selfとdocstringsは宣言の下にあります。Pythonコードのドキュメント文字列の位置を変更します

私が知りたいのは、コード内の宣言の前にドキュメントストリングを作成するにはどうしたらよいですか?次のようなもの:

"""Class docstring""" 
class MyClass(object): 
    "Method documentation" 
    def my_method(self): 
     pass 

おそらく何らかの形式のデコレータを使用していますか?

+2

確かに: '#' ;-)を使用してください – Tim

+0

ドキュメントを正しく抽出するツールがある場合は有効な答えです。 :) –

+7

あなたは、Pythonの穀粒を使って作業し、そのデザインと戦わないように自分自身を援助しています。ちょうだい;-) –

答えて

3

__doc__プロパティを設定するデコレータを書くことが可能です:

def doc(docstr): 
    def deco(f): 
     f.__doc__ = docstr 
     return f 
    return deco 

これは__doc__属性以来、機能や古いスタイルのクラスのためではなく、新しい形式のクラスのために動作します新しいスタイルのクラスは、読み取り専用です(メタクラスを使用しない限り、ほとんど利益を得ずにさらに複雑になります)。

とにかくこのようなデコレータを使用しないことをおすすめします。通常の規則に従うだけです。こうすることで、他の開発者がすぐにドキュメンテーション文字列のためのソースコードを解析するツールが正常に動作しますが、ドキュメンテーション文字列何を理解するなど

編集:

def doc(docstr): 
    def deco(f): 
     if isinstance(f, type): 
      d = vars(f).copy() 
      d["__doc__"] = docstr 
      return type(f.__name__, f.__bases__, d) 
     f.__doc__ = docstr 
     return f 
    return deco 
また、新しいスタイルのクラスをカバーするために、あなたはこの実装を使用することができます

__doc__は読み取り専用なので、目的のドキュメントを使用して新しいタイプのオブジェクトを作成する必要があります。簡単にするために、私はカスタムメタクラスを考慮しません(望むなら、上記のコードのf.__class__によってtypeを置き換えてください)。

また、このデコレータの使用はお勧めできません。

+1

非常に良い。簡単な解決策が可能であれば私は興味があったが、誰もが言ったようにコミュニケーションを損なうだろう。私はコミュニケーションのための慣習に従おうとします。ありがとう。 –

+0

python 2.7.2で新しいスタイルのクラス '__doc__'を私に割り当てても問題ありません。 – Marcin

+0

@SvenMarnach:どうやらDjangoクラスは、新しいスタイルのクラスでも '__doc__'を持つことができます。私はこれがルールの例外だとは気付かなかった。 – Marcin

1

これは動作しません。 docstringは定義上、宣言に続く行の文字列です。

本当にデコレータでこれを行う場合は、ラップされた関数(またはクラス)の__doc__プロパティを設定するデコレータを作成できます。

+1

+1これはうまくいくでしょう。 –

-1

本当にしたい場合は、確かに。

def doc(text): 
    def w(f): 
    f.__doc__ = text 
    return f 
    return w 
+0

素敵でシンプルですが、Svenが言ったように、新しいスタイルのクラスでは動作しません。 –

+0

@チアゴ:しかしそれは機能に関係なく機能します。 –

+0

@Ignacio:はい、それは機能で動作します。最後の行の後に "return w"を入力してください。それがなければ、例外が発生します。編集:さて、私は修正を見た。参考として、私はそれをdownvoteしなかった。 –

2

すでにあなたの質問に示唆したよう次のように、あなたが何かをすることができます:

from functools import wraps 

def docstring(docstr): 
    def decorator(cls): 
     @wraps(cls) 
     def wrapper(*args, **kwargs): 
      return cls(*args, **kwargs) 
     wrapper.__doc__ = docstr 
     return wrapper 
    return decorator 

@docstring("""Class docstring""") 
class MyClass(object): 
    def my_method(self): 
     pass 

print MyClass.__doc__ # Class docstring 

しかし、私は現在の構文よりも、これが特に良く見つけることはありません。

+2

これは、 'MyClass'を関数に変換することを妨げています。表現は ''のようなものになり、 '__base__'のような特殊な属性へのアクセスが失われます。 –

+0

型識別関数に影響はありますか? –

+0

@ThiagoChaves:あなたはisinstance()を意味しますか?これはもはや機能しません。また、このようなデコレータを持つクラスから派生することもできません。結局、このデコレータは完全に使用できないかもしれません。 –

関連する問題