Bagaimana cara mendokumentasikan metode dengan parameter?

148

Bagaimana cara mendokumentasikan metode dengan parameter menggunakan string dokumentasi Python?

EDIT: PEP 257 memberikan contoh ini:

def complex(real=0.0, imag=0.0):
    """Form a complex number.

    Keyword arguments:
    real -- the real part (default 0.0)
    imag -- the imaginary part (default 0.0)

    """
    if imag == 0.0 and real == 0.0: return complex_zero
    ...

Apakah ini konvensi yang digunakan oleh sebagian besar pengembang Python?

Keyword arguments:
<parameter name> -- Definition (default value if any)

Saya mengharapkan sesuatu yang sedikit lebih formal seperti

def complex(real=0.0, imag=0.0):
    """Form a complex number.

    @param: real The real part (default 0.0)
    @param: imag The imaginary part (default 0.0)

    """
    if imag == 0.0 and real == 0.0: return complex_zero
    ...

Lingkungan : Python 2.7.1

David Andreoletti
sumber
1
Sudahkah Anda membaca PEP 257? python.org/dev/peps/pep-0257
NPE
2
Ada beberapa 'standar' di luar sana tetapi pada pendekatan praktis dan terutama jika Anda menyukai sesuatu yang formal, saya akan merekomendasikan sphinx . Integrasinya di Pycharm membuat pembuatan dokumen yang terstruktur dengan baik tidak terlalu menyakitkan. IMHO
jojo

Jawaban:

89

Berdasarkan pengalaman saya, konvensi docstring numpy (superset PEP257) adalah konvensi yang diikuti paling banyak tersebar yang juga didukung oleh alat, seperti Sphinx .

Satu contoh:

Parameters
----------
x : type
    Description of parameter `x`.
Vladimir Keleshev
sumber
2
Ini lebih dekat dengan apa yang saya harapkan. Sayangnya, saya memilih PEP 257 biasa dan menambahkan konvensi saya sendiri (dengan biaya kehilangan dokumentasi HTML / PDF yang dibuat secara otomatis). Namun, lain kali, saya akan memilih solusi ini. Terima kasih.
David Andreoletti
5
Ketika saya mencoba memproses docstring yang Anda sarankan, Sphinx mengeluh SEVERE: Unexpected section title- apakah Anda tahu cara membuat Sphinx lebih bahagia?
Brandon Rhodes
@BrandonRhodes tautan ini berbicara tentang penggunaan konvensi ini dengan Sphinx: github.com/numpy/numpy/blob/master/doc/HOWTO_DOCUMENT.rst.txt
Vladimir Keleshev
3
Sebenarnya ada ruang yang hilang sebelumnya Description. Saya mengecek dokumentasi numpy tersebut, karena saya langsung menyadarinya dan berpikir "Tunggu sebentar, kenapa tiga spasi? Aneh. Siapa yang pakai tiga spasi?"
Zelphir Kaltstahl
6
Ini mungkin jawaban terbaik pada saat pertanyaan diajukan, tetapi saya pikir sampai sekarang (akhir 2017), Sphinx telah menang.
Alex L
128

Karena docstring adalah bentuk bebas, itu sangat bergantung pada apa yang Anda gunakan untuk mengurai kode untuk menghasilkan dokumentasi API.

Saya akan merekomendasikan untuk terbiasa dengan markup Sphinx , karena ini banyak digunakan dan menjadi standar de-facto untuk mendokumentasikan proyek Python, sebagian karena layanan readthedocs.org yang sangat baik . Untuk memparafrasekan contoh dari dokumentasi Sphinx sebagai cuplikan Python:

def send_message(sender, recipient, message_body, priority=1):
   '''
   Send a message to a recipient

   :param str sender: The person sending the message
   :param str recipient: The recipient of the message
   :param str message_body: The body of the message
   :param priority: The priority of the message, can be a number 1-5
   :type priority: integer or None
   :return: the message id
   :rtype: int
   :raises ValueError: if the message_body exceeds 160 characters
   :raises TypeError: if the message_body is not a basestring
   '''

Markup ini mendukung referensi silang antar dokumen dan lainnya. Perhatikan bahwa dokumentasi Sphinx menggunakan (mis.) :py:attr:Sedangkan Anda hanya dapat menggunakannya :attr:saat mendokumentasikan dari kode sumber.

Secara alami, ada alat lain untuk mendokumentasikan API. Ada Doxygen yang lebih klasik yang menggunakan \param perintah tetapi tidak dirancang khusus untuk mendokumentasikan kode Python seperti Sphinx.

Perhatikan bahwa ada pertanyaan serupa dengan jawaban serupa di sini ...

anarcat
sumber
11
Ini adalah gaya yang digunakan oleh pembuatan otomatis komentar PyCharm secara default
Josiah Yoder
Bagaimana dengan sintaks tipe komposit seperti daftar barang?
matanster
maka itu a list.
anarcat
33

Konvensi:

Alat:


Pembaruan: Sejak Python 3.5 Anda dapat menggunakan petunjuk tipe yang merupakan sintaks yang ringkas dan dapat dibaca mesin:

from typing import Dict, Union

def foo(i: int, d: Dict[str, Union[str, int]]) -> int:
    """
    Explanation: this function takes two arguments: `i` and `d`.
    `i` is annotated simply as `int`. `d` is a dictionary with `str` keys
    and values that can be either `str` or `int`.

    The return type is `int`.

    """

Keuntungan utama dari sintaks ini adalah bahwa ia ditentukan oleh bahasa dan tidak ambigu, jadi alat seperti PyCharm dapat dengan mudah memanfaatkannya.

Jakub Roztocil
sumber
12
Meskipun jawaban ini sekarang adalah yang paling disukai, tidak satu pun dari PEP di atas menyediakan konvensi untuk menentukan jenis argumen dari suatu metode.
koriander
11

string doc python adalah bentuk bebas , Anda dapat mendokumentasikannya sesuka Anda.

Contoh:

def mymethod(self, foo, bars):
    """
    Does neat stuff!
    Parameters:
      foo - a foo of type FooType to bar with.
      bars - The list of bars
    """

Sekarang, ada beberapa konvensi, tapi python tidak memberlakukan satupun. Beberapa proyek memiliki konvensi sendiri. Beberapa alat untuk bekerja dengan docstrings juga mengikuti konvensi tertentu.

nosklo.dll
sumber
8

Jika Anda berencana menggunakan Sphinx untuk mendokumentasikan kode Anda, Sphinx mampu menghasilkan dokumen HTML yang diformat dengan baik untuk parameter Anda dengan fitur 'tanda tangan' mereka. http://sphinx-doc.org/domains.html#signatures

Kyle Mede
sumber
3

Yang utama adalah, seperti jawaban lain yang telah ditunjukkan di sini, mungkin menggunakan cara Sphinx sehingga Anda dapat menggunakan Sphinx untuk menghasilkan dokumen mewah itu nanti.

Karena itu, saya secara pribadi menggunakan gaya komentar sebaris kadang-kadang.

def complex(  # Form a complex number
        real=0.0,  # the real part (default 0.0)
        imag=0.0  # the imaginary part (default 0.0)
        ):  # Returns a complex number.
    """Form a complex number.

    I may still use the mainstream docstring notation,
    if I foresee a need to use some other tools
    to generate an HTML online doc later
    """
    if imag == 0.0 and real == 0.0:
        return complex_zero
    other_code()

Satu contoh lagi di sini, dengan beberapa detail kecil yang didokumentasikan secara inline:

def foo(  # Note that how I use the parenthesis rather than backslash "\"
          # to natually break the function definition into multiple lines.
        a_very_long_parameter_name,
            # The "inline" text does not really have to be at same line,
            # when your parameter name is very long.
            # Besides, you can use this way to have multiple lines doc too.
            # The one extra level indentation here natually matches the
            # original Python indentation style.
            #
            # This parameter represents blah blah
            # blah blah
            # blah blah
        param_b,  # Some description about parameter B.
            # Some more description about parameter B.
            # As you probably noticed, the vertical alignment of pound sign
            # is less a concern IMHO, as long as your docs are intuitively
            # readable.
        last_param,  # As a side note, you can use an optional comma for
                     # your last parameter, as you can do in multi-line list
                     # or dict declaration.
        ):  # So this ending parenthesis occupying its own line provides a
            # perfect chance to use inline doc to document the return value,
            # despite of its unhappy face appearance. :)
    pass

Manfaatnya (seperti yang telah ditunjukkan @ mark-horvath di komentar lain) adalah:

  • Yang terpenting, parameter dan dokumennya selalu bersama, yang memberikan manfaat berikut:
  • Lebih sedikit mengetik (tidak perlu mengulang nama variabel)
  • Perawatan lebih mudah setelah mengubah / menghapus variabel. Tidak akan pernah ada beberapa paragraf doc parameter yatim setelah Anda mengganti nama beberapa parameter.
  • dan lebih mudah menemukan komentar yang hilang.

Sekarang, beberapa mungkin berpikir gaya ini terlihat "jelek". Tapi saya akan mengatakan "jelek" adalah kata subjektif. Cara yang lebih netral adalah mengatakan, gaya ini tidak mainstream sehingga mungkin terlihat kurang familiar bagi Anda, sehingga kurang nyaman. Sekali lagi, "nyaman" juga merupakan kata subjektif. Tetapi intinya adalah, semua manfaat yang dijelaskan di atas bersifat obyektif. Anda tidak dapat mencapainya jika Anda mengikuti cara standar.

Mudah-mudahan suatu saat nanti akan ada tool doc generator yang juga bisa menggunakan inline style seperti itu. Itu akan mendorong adopsi.

PS: Jawaban ini berasal dari preferensi saya sendiri untuk menggunakan komentar sebaris kapan pun saya mau. Saya menggunakan gaya sebaris yang sama untuk mendokumentasikan kamus juga.

RayLuo
sumber
1

Berdasarkan jawaban petunjuk tipe ( https://stackoverflow.com/a/9195565/2418922 ), yang menyediakan cara terstruktur yang lebih baik untuk mendokumentasikan jenis parameter, terdapat juga cara terstruktur untuk mendokumentasikan jenis dan deskripsi parameter:

def copy_net(
    infile: (str, 'The name of the file to send'),
    host: (str, 'The host to send the file to'),
    port: (int, 'The port to connect to')):

    pass

contoh diadopsi dari: https://pypi.org/project/autocommand/

DreamFlasher
sumber
1
Apakah ini sintaks resmi? Ini sangat berguna, namun saya tidak dapat menemukannya di dokumen resmi / PEP ...
Ofri Raviv
1
Saya ingin mengetahuinya juga, jika ada PEP untuk itu.
DreamFlasher
0

Docstring hanya berguna dalam lingkungan interaktif, misalnya shell Python. Saat mendokumentasikan objek yang tidak akan digunakan secara interaktif (misalnya objek internal, callback kerangka kerja), Anda mungkin juga menggunakan komentar biasa. Berikut adalah gaya yang saya gunakan untuk menggantungkan komentar yang menjorok ke luar item, masing-masing di barisnya sendiri, sehingga Anda tahu bahwa komentar tersebut berlaku untuk:

def Recomputate \
  (
    TheRotaryGyrator,
      # the rotary gyrator to operate on
    Computrons,
      # the computrons to perform the recomputation with
    Forthwith,
      # whether to recomputate forthwith or at one's leisure
  ) :
  # recomputates the specified rotary gyrator with
  # the desired computrons.
  ...
#end Recomputate

Anda tidak dapat melakukan hal semacam ini dengan docstrings.

Lawrence D'Oliveiro
sumber
47
Oh, yang ini terlihat jelek.
Misha Akovantsev
1
Jelek ya? Ide yang menarik ... juga ya.
David
2
Komentar sebaris untuk variabel sangat masuk akal, lebih sedikit mengetik (tidak perlu mengulang nama variabel), perawatan lebih mudah setelah mengubah / menghapus variabel ... lebih mudah menemukan komentar yang hilang. Akan menggabungkannya dengan docstring yang tepat di bawah tanda tangan. +1
Mark Horvath
Itu tidak berfungsi sebagai dokumentasi. Jika Anda memberi komentar pada paket Anda seperti ini dan pengguna PyCharm mengunduhnya, mereka tidak akan dapat memeriksa apa yang dilakukan setiap param tanpa mengakses dokumentasi Anda - yang tidak dapat Anda buat dengan perangkat lunak apa pun. Kecuali jika Anda membuatnya sendiri. Itu sebabnya OP meminta untuk menentukannya di docstring. Maaf terlambat.
1
Ini sangat menyebalkan.
Michael Walters