I egy régi pythonban írt kódalapot tartok fenn. Különösen van egy összetett kóddarab, amely egy modulból más függvényeket hív meg más modulokból, amelyek más funkciókat és így tovább hívnak. Ez nem OOP, csak függvények és modulok.
Megpróbáltam nyomon követni, hogy az áramlás hol kezdődik és mikor fejeződik be, bármikor felhívom a fő funkciót, de úgy érzem, rajzolnom kell ez azért van, mert eltévedek az alhívásokban.
Engem az aggaszt, hogy minden funkció több külső függvényt hív meg a testén belül, hogy elvégezzék a feladatukat, és visszaadják az értéket a hívónak.
Hogyan rajzolhatom ezt? Azt jelenti, hogy milyen diagram / grafika lenne megfelelő az ilyen viselkedés / kód dokumentálásához?
Tehát nem hinném, hogy hasznos lenne egy UML-diagramot megrajzolni , sem folyamatábra. Esetleg hívásgrafikon?
Megjegyzések
- doxygen – hívó / hívó grafikonokat generál, I ' nem tudom, mennyire támogatott a python. Tudom, hogy dokumentálhatja hozzá a Python-kódot.
- Próbáltam már a pycallgraph-ot, de ' is bonyolult / túl mély a használatához. Ennek oka a kódom bonyolultsága, mert a sima python-ot összekeveri a django-val és a külső hívást az API url-hez. Ezért szerettem volna kézzel megrajzolni, csak a vonatkozó részt figyelembe véve, amire szükségem van. A probléma az, hogy nem ' nem tudom, hogy milyen gráfot használjak a rendszer teljes megértése érdekében
- Ha ez csak a megértéshez vezet , csak rajzoljon bármit, ami magától jön. Később bármikor rendbe hozhatja, ha ' hivatalos dokumentációba megy.
Válasz
Azt hiszem, amit itt keres, az egy szekvencia ábra . Ezek lehetővé teszik a különböző modulok hívásának sorrendjének megjelenítését. nyilak segítségével.
Az egyik elkészítése egyszerű:
- Rajzold ki a kezdő osztályt pontozott vonallal alatta.
- Rajzold a következőt osztály / metódus a hívás nyomvonalában egy pontozott vonallal, amely alatt
- kösse össze a vonalakat egy nyíllal, függőlegesen az utolsó rajzolt nyíl alatt.
- Ismételje meg a 2-3. lépést minden hívásnál a nyomában
Példa
Tegyük fel, hogy a következő kóddal rendelkezünk, amelyhez szekvenciadiagramot szeretnénk létrehozni:
def long_division(quotient, divisor): solution = "" remainder = quotient working = "" while len(remainder) > 0: working += remainder[0] remainder = remainder[1:] multiplier = find_largest_fit(working, divisor) solution += multiplier working = calculate_remainder(working, multiplier, divisor) print solution def calculate_remainder(working, multiplier, divisor): cur_len = len(working) int_rem = int(working) - (int(multiplier) * int (divisor)) return "%*d" % (cur_len, int_rem) def find_largest_fit(quotient, divisor): if int(divisor) == 0: return "0" i = 0 while i <= 10: if (int(divisor) * i) > int(quotient): return str(i - 1) else: i += 1 if __name__ == "__main__": long_division("645", "5")
Az első dolog, amit rajzolni fogunk, az a belépési pont (main
), amely csatlakozik a long_division
metódushoz . Vegye figyelembe, hogy ez létrehoz egy mezőt a long_ osztás, jelezve a metódushívás körét. Ennél az egyszerű példánál a mező a sorrenddiagramunk teljes magassága lesz, annak a ténynek köszönhetően, hogy ez az egyetlen futtatott dolog.
Most felhívjuk a (z) find_largest_fit
számot, hogy megtaláljuk a legnagyobb számot, amely a munkaszámunkba illeszkedik , és visszaadja nekünk. Vonalat húzunk a long_division
és a find_largest_fit
között egy másik mezővel a függvényhívás hatókörének jelölésére. Vegye figyelembe, hogy a mező hogyan ér véget a szorzó visszaadásakor; ezzel vége a függvény hatókörének!
Ismételje meg néhányszor nagyobb szám esetén, és a diagramjának ilyennek kell lennie:
Megjegyzések
Kiválaszthatja, hogy a hívásokat átadott változónevekkel vagy azok értékével szeretné-e címkézni dokumentáljon egy konkrét esetet. A rekurziót egy olyan funkcióval is megjelenítheti, amely magát meghívja.
Ezenkívül itt is megmutathatja a felhasználókat, felszólíthatja őket, és elég könnyen megmutathatják a rendszerbe való belépésüket. Ez egy meglehetősen rugalmas rendszer, amelyet szerintem nagyon hasznosnak találsz!
Megjegyzések
- Köszönöm, ismerem a sorrenddiagramot, de úgy érzi, hogy ez inkább oop-ra alkalmas. Esetemben a dolgok egy kicsit rendetlenebbek, vagyis például körülbelül 20 funkcióm / segítőm van, amelyek több modul körül vannak elosztva. Ho megadnám azt a modult, amelyhez a függvény tartozik? Figyelembe véve, hogy egyes funkciókat az importálás során is átneveznek.
- Azt mondanám, hogy nem számít, hány modulja van – a fenti példa egyáltalán nem oop. Csak nevezze meg őket, hogy később megtalálja őket: A modul / function1, ModuleB / Function2 stb. 20 funkció esetén nagyobb lesz, de biztosan nem lehetetlen megérteni. Egy másik gondolat, hogy megteheti, hogy befejezi a függvény sorát az utolsó használat után, és egy másik függvény sort tesz alá, hogy vízszintes helyet takarítson meg a diagramban. >
Úgy gondolom, hogy egy hívási grafikon lenne a legmegfelelőbb megjelenítés.Ha úgy dönt, hogy nem kézzel csinálja, akkor van egy szép kis eszköz, az úgynevezett
pyan
, amely statikus elemzést végez egy python fájlon, és vizualizált hívási grafikont generálhat grafviz pont segítségével. fájl (amely képpé alakítható). Van néhány villa, de a legteljesebb tulajdonságú a https://github.com/davidfraser/pyan .Csak meg kell adnia az összes fájlt, amelyet feldolgozni szeretne a parancs futtatásakor:
python ~/bin/pyan.py --dot a.py b.py c.py -n > pyan.dot; dot -Tpng -opyan.png pyan.dot
vagy
python ~/bin/pyan.py --dot $(find . -name "*.py") -n > pyan.dot; dot -Tpng -opyan.png pyan.dot
A “-n” segítségével tisztábbá teheti a gráfot, amely eltávolítja a sorok, amelyek megmutatják, hogy hol definiáltak egy függvényt.