Bir Python modülündeki tüm fonksiyonlar nasıl listelenir?


418

Sistemime yüklü bir python modülü var ve içinde hangi işlevlerin / sınıfların / yöntemlerin mevcut olduğunu görmek istiyorum.

Her birinde doc işlevini çağırmak istiyorum. Ruby'de ClassName.methods gibi bir şey yapabilirim. Python'da benzer bir şey var mı?

Örneğin. gibi bir şey:

from somemodule import foo
print foo.methods # or whatever is the correct method to call

3
lütfen seçilen cevabı gözden geçirmeyi düşünün! diğer cevaplarda önerilen daha iyi / daha kolay çözümler vardır.
Zahra

Yanıtlar:


139

inspectModülü. Ayrıca pydocmodüle, help()etkileşimli yorumlayıcıdaki işleve ve pydocpeşinde olduğunuz belgeleri oluşturan komut satırı aracına bakın. Onlara sadece belgelerini görmek istediğiniz sınıfı verebilirsiniz. Ayrıca HTML çıktısı oluşturabilir ve diske yazabilirler.


3
Cevabımınast bazı durumlarda modülü kullanma davası açtım .
csl

28
TL: Aşağıdaki cevapların DR'si: dirişlev ve değişkenleri döndürmek için kullanın ; inspectyalnızca işlevleri filtrelemek için kullanın ; ve astiçe aktarmadan ayrıştırmak için kullanın .
Jonathan H

Sheljohn tarafından özetlenen yaklaşımların her birini test etmeye değer, çünkü elde edilen çıktı bir çözümden diğerine büyük ölçüde farklıdır.
clozach

1
@ Hack-R Mymodule içindeki tüm fonksiyonları listeleyen kod: [f [0] f için inspect.getmembers (mymodule, inspect.isfunction)]
SurpriseDog

498

dir(module)Kullanılabilir tüm yöntemleri / nitelikleri görmek için kullanabilirsiniz . Ayrıca PyDocs'a da göz atın.


15
Bu kesinlikle doğru değil. dir()Fonksiyon “girişimleri en alakalı ziyade tam bilgi üretmek”. Kaynak: docs.python.org/library/functions.html#dir .
Zearin

15
@jAckOdE Alıntı yapıldı? Ardından, dize modülünün kullanılabilir yöntemlerini ve özniteliklerini alırsınız.
OrangeTux

@OrangeTux: Hata! Bu bir soru olmalı. cevap verdin.
jAckOdE

1
OP açıkça değişkenleri değil fonksiyonları ister. Cf kullanarak cevaplar inspect.
Jonathan H

168

importModülü düzenledikten sonra şunları yapabilirsiniz:

 help(modulename)

... Dokümanları tüm fonksiyonlara aynı anda, interaktif olarak almak için. Veya şunları kullanabilirsiniz:

 dir(modulename)

... Modülde tanımlanan tüm işlevlerin ve değişkenlerin adlarını listelemek için.


1
@ sheljohn… bu eleştirinin amacı nedir? Benim çözümüm işlevleri de listeliyor ve inspect burada açıkça istenmese de modül değişkenleri de listeleyebiliyor. Bu çözüm, yalnızca Python'un kısıtlanmış / kilitli / bozuk bir ortama kurulduğu bazı durumlarda çok yararlı olabilecek yerleşik nesneler gerektirir.
Dan Lenski

Teşekkürler, bu neredeyse işe yaradı, ancak dirsonuçların yazdırılacağını düşündüm , ancak yapmanız gerekiyor gibi görünüyor print(dir(modulename)).
Eliot

96

Inspect ile bir örnek:

from inspect import getmembers, isfunction
from my_project import my_module

functions_list = [o for o in getmembers(my_module) if isfunction(o[1])]

getmembers (nesne_adı, nesne_türü) gruplarının listesini döndürür.

İşlevi, denetleme modülündeki diğer isXXX işlevlerinden herhangi biriyle değiştirebilirsiniz.


27
getmembersbir yüklem alabilir, böylece örneğiniz de yazılabilir: functions_list = [o for o in getmembers(my_module, isfunction)]
Christopher Currie

27
@ChristopherCurrie, functions_list = getmembers(my_module, predicate)zaten bir liste döndürdüğü için işe yaramaz liste kavrayışından da kaçınabilirsiniz ;)
Nil

5
İşlevin bu modülde (içe aktarılmak yerine) tanımlanıp tanımlanmadığını bulmak için şunu ekleyin: "isfunction (o [1]) ve o [1] .__ module__ == my_module .__ name__ " - şunu ekleyin: içe aktarılan işlev, bu modülle aynı ada sahip bir modülden gelir.
Michael Scott Cuthbert

72
import types
import yourmodule

print([getattr(yourmodule, a) for a in dir(yourmodule)
  if isinstance(getattr(yourmodule, a), types.FunctionType)])

8
Bu rota için, modeliniz yerine getattr (yourmodule, a, None) kullanın .__ dict __. Get (a)
Thomas Wouters

4
your_module .__ dict__ benim seçimim çünkü aslında functionName: <function> işlevini içeren bir dikte edin ve şimdi bu işlevi dinamik olarak CALL etme yeteneğine sahipsiniz. iyi zamanlar!
jsh

1
Python 3 biraz şekerle dost: ithalat türleri def print_module_functions (module): isinstance (modül) durumunda bir dir (modül) için print ('\ n'.join ([str (modül .__ dict __. Get (a) .__ name__). __dict __. get (a), türleri.FunctionType)]))
y.selivonchyk

1
Bu, modülün içe aktardığı tüm işlevleri de listeler. İstediğiniz şey olabilir veya olmayabilir.
scubbo

47

Tamlık uğruna, bazen kodu içe aktarmak yerine kodu ayrıştırmak isteyebileceğinizi belirtmek isterim . Bir importedecektir yürütmek üst düzey ifadeleri, bu da bir sorun olabilir.

Örneğin, kullanıcıların zipapp ile yapılan paketler için giriş noktası işlevlerini seçmelerine izin veriyorum . Kullanılması importve inspect, yoldan kodunu çalıştıran çöker yol açan riski, yardım mesajları çıktısı olan, GUI diyaloglar gelmeyip vb.

Bunun yerine tüm üst düzey işlevleri listelemek için ast modülünü kullanıyorum :

import ast
import sys

def top_level_functions(body):
    return (f for f in body if isinstance(f, ast.FunctionDef))

def parse_ast(filename):
    with open(filename, "rt") as file:
        return ast.parse(file.read(), filename=filename)

if __name__ == "__main__":
    for filename in sys.argv[1:]:
        print(filename)
        tree = parse_ast(filename)
        for func in top_level_functions(tree.body):
            print("  %s" % func.name)

Bu kodu koyarak list.pyve giriş olarak kendini kullanarak, ben olsun:

$ python list.py list.py
list.py
  top_level_functions
  parse_ast

Tabii ki, bir AST'de gezinmek bazen Python gibi nispeten basit bir dil için bile zor olabilir, çünkü AST oldukça düşük seviyededir. Ancak basit ve net bir kullanım durumunuz varsa, hem yapılabilir hem de güvenlidir.

Olsa da, bir dezavantajı, çalışma zamanında üretilen işlevleri algılayamamanızdır foo = lambda x,y: x*y.


2
Bunu severim; Şu anda birisi zaten pydoc gibi bir şey yapar ama modül ithal etmeden bir araç yazmış olup olmadığını öğrenmek için çalışıyorum. Şimdiye kadar bu bulduğum en iyi örnek :)
James Mills

Bu cevaba katılıyorum. Hedef dosya ne alabilir ya da bunun için yazılmış python sürümü ne olursa olsun çalışmak için bu işlevi gerekir. Bu, imp ve importlib'in içe aktardığı içe aktarma sorunlarıyla karşılaşmaz.
Eric Evans

Modül değişkenleri ( __version__vs) hakkında. Bunu almanın bir yolu var mı?
frakman1

29

Ayrıştırmak istemediğiniz kod için, yukarıdaki @csl'nin AST tabanlı yaklaşımını öneririm.

Diğer her şey için inceleme modülü doğrudur:

import inspect

import <module_to_inspect> as module

functions = inspect.getmembers(module, inspect.isfunction)

Bu, formdaki 2 tüpün bir listesini verir [(<name:str>, <value:function>), ...].

Yukarıdaki basit cevap, çeşitli yanıtlarda ve yorumlarda ima edilir, ancak açıkça çağrılmaz.


Hecelediğiniz için teşekkürler; İncelemek için modül üzerinde ithalat çalıştırabilirseniz, bu doğru cevap olduğunu düşünüyorum.
Jonathan H

25

Bu hile yapacak:

dir(module) 

Ancak, döndürülen listeyi okumayı rahatsız edici bulursanız, her satıra bir ad almak için aşağıdaki döngüyü kullanmanız yeterlidir.

for i in dir(module): print i

2
OP açıkça değişkenleri değil fonksiyonları ister. Cf kullanarak cevaplar inspect. Ayrıca, bu @ DanLenski'nin cevabından nasıl farklı?
Jonathan H

20

dir(module) çoğu cevapta belirtildiği gibi bir komut dosyası veya standart yorumlayıcı kullanmanın standart yoludur.

Ancak IPython gibi etkileşimli bir python kabuğu ile modülde tanımlanan tüm nesnelere genel bir bakış için sekme tamamlama özelliğini kullanabilirsiniz. Bu, bir komut dosyası kullanmaktan printve modülde neyin tanımlandığını görmekten çok daha uygundur .

  • module.<tab> modülde tanımlanan tüm nesneleri gösterecektir (fonksiyonlar, sınıflar vb.)
  • module.ClassX.<tab> size bir sınıfın yöntemlerini ve özelliklerini gösterecek
  • module.function_xy?ya module.ClassX.method_xy?da size bu işlevin / yöntemin öğretisini gösterecek
  • module.function_x??veya module.SomeClass.method_xy??işlevin / yöntemin kaynak kodunu gösterecektir.

19

Küresel işlevler dir()için (bu yanıtların çoğunda belirtildiği gibi) kullanılacak komuttur, ancak bu hem genel işlevleri hem de genel olmayan işlevleri birlikte listeler.

Örneğin koşu:

>>> import re
>>> dir(re)

Aşağıdaki gibi fonksiyonları / sınıfları döndürür:

'__all__', '_MAXCACHE', '_alphanum_bytes', '_alphanum_str', '_pattern_type', '_pickle', '_subx'

Bazıları genellikle genel programlama kullanımı için değildir (ancak modülün kendisi tarafından __doc__, __file__vb. Gibi DunderAliases hariç ). Bu nedenle, bunları halka açık olanlarla listelemek yararlı olmayabilir (Python, kullanırken ne elde edeceğini bu şekilde bilir from module import *).

__all__Bu sorunu çözmek için kullanılabilir, bir modülde tüm kamu işlevlerinin ve sınıfların listesini döndürür (bu yok çizgi ile başlar - _). Bkz Can birisi Python __all__ açıklamak? kullanımı için __all__.

İşte bir örnek:

>>> import re
>>> re.__all__
['match', 'fullmatch', 'search', 'sub', 'subn', 'split', 'findall', 'finditer', 'compile', 'purge', 'template', 'escape', 'error', 'A', 'I', 'L', 'M', 'S', 'X', 'U', 'ASCII', 'IGNORECASE', 'LOCALE', 'MULTILINE', 'DOTALL', 'VERBOSE', 'UNICODE']
>>>

Alt çizgileri olan tüm işlevler ve sınıflar kaldırılmıştır, yalnızca genel olarak tanımlanmış ve bu nedenle üzerinden kullanılabilir import *.

Bunun __all__her zaman tanımlanmadığını unutmayın. İçermezse AttributeError, bir yükseltilir.

Bunun bir örneği ast modülünde:

>>> import ast
>>> ast.__all__
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
AttributeError: module 'ast' has no attribute '__all__'
>>>

4

Söz konusu Python dosyasını içe aktarma hataları olmadan içe aktaramazsanız bu cevapların hiçbiri işe yaramaz. Bağımlılığı çok olan büyük bir kod tabanından gelen bir dosyayı incelerken bu durum benim için geçerliydi. Aşağıdakiler dosyayı metin olarak işleyecek ve "def" ile başlayan tüm yöntem adlarını arayacak ve bunları ve satır numaralarını yazdıracaktır.

import re
pattern = re.compile("def (.*)\(")
for i, line in enumerate(open('Example.py')):
  for match in re.finditer(pattern, line):
    print '%s: %s' % (i+1, match.groups()[0])

3
Bu durumda astmodülü kullanmak çok daha iyidir . Bir örnek için cevabımı görün .
csl

Bunun geçerli bir yöntem olduğunu düşünüyorum. Neden bir aşağı oy?
m3nda

2

Önceki yanıtlarda belirtilen dir (modül) veya yardım (modül) dışında şunları da deneyebilirsiniz:
- ipython'u açın - modül_adı
alma
- modül_adı yazın, sekme tuşuna basın. Python modülündeki tüm fonksiyonları listeleyen küçük bir pencere açılacaktır.
Çok düzgün görünüyor.

İşte hashlib modülünün tüm işlevlerini listeleyen snippet

(C:\Program Files\Anaconda2) C:\Users\lenovo>ipython
Python 2.7.12 |Anaconda 4.2.0 (64-bit)| (default, Jun 29 2016, 11:07:13) [MSC v.1500 64 bit (AMD64)]
Type "copyright", "credits" or "license" for more information.

IPython 5.1.0 -- An enhanced Interactive Python.
?         -> Introduction and overview of IPython's features.
%quickref -> Quick reference.
help      -> Python's own help system.
object?   -> Details about 'object', use 'object??' for extra details.

In [1]: import hashlib

In [2]: hashlib.
             hashlib.algorithms            hashlib.new                   hashlib.sha256
             hashlib.algorithms_available  hashlib.pbkdf2_hmac           hashlib.sha384
             hashlib.algorithms_guaranteed hashlib.sha1                  hashlib.sha512
             hashlib.md5                   hashlib.sha224

1

Bu, modülünüzde tanımlanan tüm işlevleri bir listeye ekler.

result=[]
for i in dir(your_module):
    if type(getattr(your_module, i)).__name__ == "function":
        result.append(getattr(your_module, i))

Bu unit8_conversion_methodsnedir? Bu sadece modül adına bir örnek mi?
nocibambi

@nocibambi evet bu sadece bir modül adı.
Manish Kumar

2
teşekkürler Manish. Aşağıdaki tek satırlık alternatifi öneriyorum:[getattr(your_module, func) for func in dir(your_module) if type(getattr(your_module, func)).__name__ == "function"]
amine

0

Modülünüzdeki tüm işlevleri kabuktan listelemek için aşağıdaki yöntemi kullanabilirsiniz:

import module

module.*?

1
@GabrielFair python'u hangi sürümde / platformda çalıştırıyorsunuz? Py3.7 / Win10'da bir sözdizimi hatası alıyorum.
toonarmycaptain

0
import sys
from inspect import getmembers, isfunction
fcn_list = [o[0] for o in getmembers(sys.modules[__name__], isfunction)]

0
r = globals()
sep = '\n'+100*'*'+'\n' # To make it clean to read.
for k in list(r.keys()):
    try:
        if str(type(r[k])).count('function'):
            print(sep+k + ' : \n' + str(r[k].__doc__))
    except Exception as e:
        print(e)

Çıktı :

******************************************************************************************
GetNumberOfWordsInTextFile : 

    Calcule et retourne le nombre de mots d'un fichier texte
    :param path_: le chemin du fichier à analyser
    :return: le nombre de mots du fichier

******************************************************************************************

    write_in : 

        Ecrit les donnees (2nd arg) dans un fichier txt (path en 1st arg) en mode a,
        :param path_: le path du fichier texte
        :param data_: la liste des données à écrire ou un bloc texte directement
        :return: None


 ******************************************************************************************
    write_in_as_w : 

            Ecrit les donnees (2nd arg) dans un fichier txt (path en 1st arg) en mode w,
            :param path_: le path du fichier texte
            :param data_: la liste des données à écrire ou un bloc texte directement
            :return: None
Sitemizi kullandığınızda şunları okuyup anladığınızı kabul etmiş olursunuz: Çerez Politikası ve Gizlilik Politikası.
Licensed under cc by-sa 3.0 with attribution required.