Obsah
1. Neuronové sítě v knihovně scikit-learn (2.část)
3. Jakou strukturu neuronové sítě zvolit?
4. Změna počtu neuronů v jediné skryté vrstvě
5. Změna počtu neuronů ve větším množství skrytých vrstev
6. Vliv postupného zvyšování počtu skrytých vrstev na kvalitu odpovědí neuronové sítě
7. Zjištění kvality modelu s využitím matice záměn (confusion matrix)
8. Vizualizace matice záměn s absolutními i relativními odchylkami pro model lineární regrese
9. Získané a vizualizované výsledky
10. Matice záměn pro odlišný model: hledání K nejbližších sousedů
11. Získané a vizualizované výsledky
12. Matice záměn pro klasifikátor implementovaný pomocí neuronové sítě
13. Získané a vizualizované výsledky
14. Lze regresní neuronovou síť naučit malou násobilku?
15. Výsledek: neuronová síť na úrovni prváka
16. Vizualizace rozdílů předpovědí neuronové sítě od korektních výsledků
17. Numerické i grafické výsledky korektnosti výpočtů tabulky malé násobilky
18. Dokáže takto natrénovaná neuronová síť generalizovat?
19. Repositář s demonstračními příklady
1. Neuronové sítě v knihovně scikit-learn (2.část)
Na předchozí článek o knihovně scikit-learn dnes přímo navážeme. Opět se totiž budeme zabývat problematikou konstrukce, učení a validace neuronových sítí. Nejprve si ukážeme, jakým způsobem je možné měnit, resp. přesněji řečeno definovat topologii neuronové sítě provádějící regresi (tedy nikoli klasifikaci), ovšem v dalším pokračování nezapomeneme ani na problematiku volby takzvané aktivační funkce, která může ovlivnit globální chování celé neuronové sítě.

Obrázek 1: Idealizovaný model neuronu použitý v klasických neuronových sítích.
Pro zajímavost se pokusíme natrénovat si neuronovou síť pro výpočet malé i velké násobilky (tam lze dobře pochopit různá úskalí neuronových sítí, i když zrovna tento úkol se pro neuronové sítě příliš nehodí, což bude ostatně patrné i z výsledků). Ukážeme si například i použití takzvané matice záměn (confusion matrix), kterou lze využít proto, abychom dobře porozuměli, jakým způsobem se „pletou“ či naopak „trefují“ modely provádějící klasifikaci.

Obrázek 2: Idealizovaný model neuronu s biasem (což je vlastně konstantní vstup 1, který je váhován podobně, jako i ostatní vstupy).
2. Krátké zopakování z minula: neuronová síť provádějící regresi natrénovaná na datové sadě California Housings
Nejprve si připomeňme, jakým způsobem můžeme s využitím knihovny scikit-learn realizovat jednoduchou neuronovou sít provádějící regresi (tedy odhad numerické hodnoty z určitého rozsahu). Klasické neuronové sítě mají neurony uspořádány do vrstev, přičemž první vrstva se nazývá vstupní, poslední vrstva výstupní a mezivrstvy se nazývají skryté:

Obrázek 3: Uspořádání neuronů do vrstev ve feed-forward síti.
Naše konkrétní neuronová síť bude mít ve vstupní vrstvě osm neuronů, protože ve vstupní datové sadě je osm atributů. Výstupní vrstva bude obsahovat jen jeden neuron, neboť se jedná o výpočet jediné konkrétní hodnoty (ceny bytu, resp. bloku). A jediná vnitřní vrstva bude obsahovat sto neuronů, protože se jedná o výchozí hodnotu dosazenou přímo knihovnou scikit-learn:
# model zalozeny na neuronove siti from sklearn.neural_network import MLPRegressor from sklearn.datasets import fetch_california_housing from sklearn.metrics import mean_squared_error, r2_score from sklearn.model_selection import train_test_split # nacteni datove sady housings = fetch_california_housing() # precteni dat z datove sady # urcenych pro trenink, validaci atd. data = housings["data"] # ceny bloku targets = housings["target"] # X je matice, y je vektor X = data y = targets # rozdeleni dat na treninkovou a testovaci mnozinu X_train, X_test, y_train, y_test = train_test_split(X, y, test_size=0.5) # konstrukce modelu nn = MLPRegressor(max_iter=5000) # trénink modelu nn.fit(X_train, y_train) # predikce modelu y_pred = nn.predict(X_test) # chyba predikce print("Mean squared error: %.2f" % mean_squared_error(y_test, y_pred)) # 1 = nejlepší predikce modelu print("Coefficient of determination: %.2f" % r2_score(y_test, y_pred)) print(f"Features: {nn.n_features_in_}") print(f"Layers: {nn.n_layers_}") print(f"Outputs: {nn.n_outputs_}") print("Weights:") for layer, weights in enumerate(nn.coefs_): print("\t", layer, weights.shape) print("Biases:") for layer, biases in enumerate(nn.intercepts_): print("\t", layer, biases.shape)
Po spuštění výše uvedeného skriptu se nejdříve zobrazí výsledek validace modelu, ovšem nutno dodat, že v tomto případě s nepříliš lichotivými výsledky (R2 skóre dokonce kleslo těsně pod nulu):
Mean squared error: 1.34 Coefficient of determination: -0.01
Posléze skript zobrazí informace o neuronové síti. Ze zpráv, které jsou vytisknuty, plyne, že ve vstupní vrstvě je osm neuronů, což odpovídá počtu atributů, na které byla síť natrénována. Výstupní vrstva má jeden neuron, což je opět pochopitelné, protože výstupem má být jediné reálné číslo. A celkový počet vrstev je roven třem – tedy kromě vstupní vrstvy a vrstvy výstupní máme jedinou skrytou vrstvu:
Features: 8 Layers: 3 Outputs: 1
Posledními údaji, které skript uvedený v této kapitole zobrazí, jsou tvary (shape) polí s váhami neuronů a taktéž pole s hodnotami bias. Tvary těchto polí plně odpovídají očekávané topologii neuronové sítě (tedy vazby 8:100:1 atd.):
Weights: 0 (8, 100) 1 (100, 1) Biases: 0 (100,) 1 (1,)
3. Jakou strukturu neuronové sítě zvolit?
Při konstrukci neuronové sítě musíme nějakým způsobem zjistit nebo alespoň odhadnout, kolik skrytých vrstev by se mělo použít a kolik neuronů by v každé z těchto vrstev mělo být. Taktéž je nutné vybrat vhodnou aktivační funkci, způsob realizace tréninkového algoritmu atd. Jedná se o velké množství proměnných hodnot, takže výběr může probíhat v několika kolech, které typicky obsahují křížovou validaci modelu.
Existuje několik více či méně kvalitních heuristik, které nám povídají, jakou zvolit topologii neuronové sítě. Vybírám ty nejjednodušší a nejznámější heuristiky:
- Počet neuronů ve skryté vrstvě by měl být zhruba 2/3 velikosti vstupní vrstvy (někdo udává rozsah 70%-90%).
- Počet neuronů ve skryté vrstvě by měl být menší, než dvojnásobek velikosti (počtu neuronů) ve vstupní vrstvě.
- Počet neuronů ve skryté vrstvě by měl ležet na rozsahu počtu neuronů vstupní a výstupní vrstvy (což platí pro sítě provádějící klasifikaci).
- Počet neuronů ve skrytých vrstvách by měl postupně klesat (někdy se uvádí exponenciální pokles, ovšem zde skutečně záleží na množství vstupů).
- Postupně přidávejte další skryté vrstvy až do chvíle, kdy se začne snižovat přesnost nebo R2 skóre (většinou najdeme skokovou změnu po přidání další vrstvy).
4. Změna počtu neuronů v jediné skryté vrstvě
Pokusme se nyní zjistit, jakým způsobem se změní kvalita neuronové sítě (tedy přesnosti předpovědí při provádění regrese) v případě, že budeme měnit počet neuronů ve skryté vrstvě. Volba počtu neuronů je snadná, protože při konstrukci neuronové sítě můžeme použít parametr hidden_layer_sizes, kterému se předá n-tice obsahující počty neuronů ve skryté vrstvě (jednice) či ve více vrstvách:
nn = MLPRegressor(max_iter=5000, hidden_layer_sizes = (neurons, ))
Celý skript, který provádí konstrukci neuronové sítě, její natrénování a otestování, vypadá následovně:
import matplotlib.pyplot as plt # model zalozeny na neuronove siti from sklearn.neural_network import MLPRegressor from sklearn.datasets import fetch_california_housing from sklearn.model_selection import cross_val_score # nacteni datove sady housings = fetch_california_housing() # precteni dat z datove sady # urcenych pro trenink, validaci atd. data = housings["data"] # ceny bloku targets = housings["target"] # X je matice, y je vektor X = data y = targets r = range(1, 12) avg_scores = [] # hledani optimalniho poctu neuronu ve vrstvach for i in r: # konstrukce modelu neurons = 2**i nn = MLPRegressor(max_iter=5000, hidden_layer_sizes = (neurons, )) scores = cross_val_score(nn, X, y, cv=10, scoring='r2') # vypsani prumerneho skore do tabulky avg_score = scores.mean() print(neurons, avg_score) avg_scores.append(avg_score) plt.plot(r, avg_scores) plt.xlabel("Změna počtu neuronů v jedné vrstvě") plt.ylabel("R2") # ulozeni grafu do souboru plt.savefig("144.png") # vykresleni grafu na obrazovku #plt.show()
Výsledky výpočtu R2 skóre pro postupně se měnící počty neuronů vypadají takto:
2 -0.1454302734588354 4 -0.03707952396388188 8 0.024029461721653787 16 0.15975633333410563 32 0.0019421990876153927 64 0.2831746308829118 128 0.30220876727407814 256 -0.08924552002434508 512 -0.0007001958806893916 1024 -5.531109632506313 2048 -20.041735587898025

Obrázek 4: Závislost kvality odpovědí neuronové sítě s jednou skrytou vrstvou na počtu neuronů v této vrstvě.
5. Změna počtu neuronů ve větším množství skrytých vrstev
Naprosto stejným způsobem se můžeme pokusit o zjištění, jaký vliv má počet neuronů umístěných ve větším množství skrytých vrstev na kvalitu odhadů neuronové sítě. Pokusíme se zjistit tyto vlastnosti pro neuronové sítě se třemi a pěti skrytými vrstvami. Skript pro neuronovou síť se třemi vrstvami:
import matplotlib.pyplot as plt # model zalozeny na neuronove siti from sklearn.neural_network import MLPRegressor from sklearn.datasets import fetch_california_housing from sklearn.model_selection import cross_val_score # nacteni datove sady housings = fetch_california_housing() # precteni dat z datove sady # urcenych pro trenink, validaci atd. data = housings["data"] # ceny bloku targets = housings["target"] # X je matice, y je vektor X = data y = targets r = range(1, 12) avg_scores = [] # hledani optimalniho poctu neuronu ve vrstvach for i in r: # konstrukce modelu neurons = 2**i nn = MLPRegressor(max_iter=5000, hidden_layer_sizes = (neurons, neurons, neurons)) scores = cross_val_score(nn, X, y, cv=10, scoring='r2') # vypsani prumerneho skore do tabulky avg_score = scores.mean() print(neurons, avg_score) avg_scores.append(avg_score) plt.plot(r, avg_scores) plt.xlabel("Změna počtu neuronů ve třech vrstvách") plt.ylabel("R2") # ulozeni grafu do souboru plt.savefig("145.png") # vykresleni grafu na obrazovku #plt.show()
Výsledky již nyní nejsou tak jednoznačné, jako tomu bylo v předchozím příkladu, protože i neuronová síť se zbytečně velkým počtem neuronů dokázala tuto nevýhodu do určité míry kompenzovat:
2 -0.283005105231359 4 0.148825137624293 8 0.3334395444819797 16 0.14779810169991886 32 -0.14617386521960413 64 0.17143912954224527 128 -0.35915114561290196 256 0.028327261438945373 512 -0.5219569442908789 1024 0.22234451593419272 2048 0.32266508344685396

Obrázek 5: Závislost kvality odpovědí neuronové sítě se třemi skrytými vrstvami na počtu neuronů v této vrstvě.
Realizace téhož příkladu, nyní ovšem pro pět skrytých vrstev vypadá následovně:
import matplotlib.pyplot as plt # model zalozeny na neuronove siti from sklearn.neural_network import MLPRegressor from sklearn.datasets import fetch_california_housing from sklearn.model_selection import cross_val_score # nacteni datove sady housings = fetch_california_housing() # precteni dat z datove sady # urcenych pro trenink, validaci atd. data = housings["data"] # ceny bloku targets = housings["target"] # X je matice, y je vektor X = data y = targets r = range(1, 12) avg_scores = [] # hledani optimalniho poctu neuronu ve vrstvach for i in r: # konstrukce modelu neurons = 2**i nn = MLPRegressor(max_iter=5000, hidden_layer_sizes = (neurons, neurons, neurons, neurons, neurons)) scores = cross_val_score(nn, X, y, cv=10, scoring='r2', n_jobs=-1) # vypsani prumerneho skore do tabulky avg_score = scores.mean() print(neurons, avg_score) avg_scores.append(avg_score) plt.plot(r, avg_scores) plt.xlabel("Změna počtu neuronů v pěti vrstvách") plt.ylabel("R2") # ulozeni grafu do souboru plt.savefig("146.png") # vykresleni grafu na obrazovku #plt.show()
Numerické výsledky v tabulkové podobě:
2 -0.0754384824557155 4 -0.14798990918251986 8 0.3995421626439365 16 0.010342881370922475 32 0.19336159679802659 64 0.17877679646955416 128 0.2820772221907199 256 0.5288142058348293 512 0.44223558072990465 1024 0.44861141341888383 2048 0.40412403628968663

Obrázek 6: Závislost kvality odpovědí neuronové sítě s pěti skrytými vrstvami na počtu neuronů v této vrstvě.
6. Vliv postupného zvyšování počtu skrytých vrstev na kvalitu odpovědí neuronové sítě
Z výsledků, které jsme získali z předchozí trojice skriptů, by se mohlo zdát, že spíše než zvyšování počtu neuronů ve skrytých vrstvách může být výhodnější spíše zvýšit počet těchto vrstev s menším počtem neuronů. Zkusme si tuto domněnku ověřit, a to tak, že ponecháme počet neuronů v každé skryté vrstvě konstantní, ale budeme zvyšovat počet těchto vrstev. Využijeme přitom možnosti „opakování“ prvků v n-tici:
NEURONS = 5 layer_sizes = (NEURONS, ) * layers nn = MLPRegressor(max_iter=5000, hidden_layer_sizes = layer_sizes)
Celý skript, který postupně zvyšuje počet vrstev a následně ověřuje kvalitu neuronové sítě, vypadá následovně:
import matplotlib.pyplot as plt # model zalozeny na neuronove siti from sklearn.neural_network import MLPRegressor from sklearn.datasets import fetch_california_housing from sklearn.model_selection import cross_val_score # nacteni datove sady housings = fetch_california_housing() # precteni dat z datove sady # urcenych pro trenink, validaci atd. data = housings["data"] # ceny bloku targets = housings["target"] # X je matice, y je vektor X = data y = targets NEURONS = 5 r = range(1, 40) avg_scores = [] # hledani optimalniho poctu neuronu ve vrstvach for layers in r: # konstrukce modelu layer_sizes = (NEURONS, ) * layers nn = MLPRegressor(max_iter=5000, hidden_layer_sizes = layer_sizes) # vypocet skore scores = cross_val_score(nn, X, y, cv=10, scoring='r2', n_jobs=-1) # vypsani prumerneho skore do tabulky avg_score = scores.mean() print(layers, avg_score) avg_scores.append(avg_score) plt.plot(r, avg_scores) plt.xlabel("Změna počtu vrstev") plt.ylabel("R2") # ulozeni grafu do souboru plt.savefig("147.png") # vykresleni grafu na obrazovku plt.show()
Opět si nejprve uveďme výsledky v numerické podobě:
1 0.3756102466117746 2 0.33435201837938544 3 0.12054109495792083 4 0.09916830519723958 5 0.3239525018951458 6 0.06484265048651823 7 -0.10421240952695066 8 0.27187249385037804 9 0.2882272162105404 10 0.14207548441647116 11 0.2264986054565991 12 0.0731174214139199 13 0.13308221750444812 14 0.19895244674967708 15 0.1294763780958599 16 -0.12671951662229197 17 0.17829603759203674 18 0.12295044855822954 19 0.3231971403204573 20 0.08460788802486123 21 0.1255234820631603 22 0.22386452833322137 23 0.08215259556813452 24 -0.09532343419407868 25 -0.10410875091569269 26 -0.14048312380932332 27 -0.2770565595807387 28 -0.20586069878082425 29 -0.0911768500198286 30 -0.2797797072289029 31 -0.2698970179654826 32 -0.27684226485857805 33 -0.13352979202774717 34 -0.27688492300614664 35 -0.198615684982469 36 -0.18700389633765757 37 -0.264543446558973 38 -0.2696700809142521 39 -0.21418061259668536

Obrázek 7: Závislost kvality odpovědí neuronové sítě na počtu skrytých vrstev.
7. Zjištění kvality modelu s využitím matice záměn (confusion matrix)
Při zjišťování kvality modelů, které provádí klasifikaci, se s úspěchem používá takzvaná matice záměn neboli confusion matrix. Jedná se o matici, která ve sloupcích obsahuje očekávané hodnoty a v řádcích pak předpovědi/odpovědi modelu. Pokud model odpoví ve všech případech správně, bude matice obsahovat nenulové hodnoty pouze na hlavní diagonále a tyto hodnoty budou znamenat „očekávalo se X odpovědí A a model takto odpověděl skutečně X-krát“. Ovšem ve chvíli, kdy se model splete, vypíše se tato hodnota mimo hlavní diagonálu; tj. hodnoty mimo hlavní diagonálu znamenají chyby a navíc můžeme zjistit, které odpovědi způsobují modelu největší problémy (tj. například které druhy květin z datové sady Iris zaměňuje a které naopak nalezne vždy bez problémů).
Podívejme se na příklad modelu, který vždy odpoví korektně:
| A B C --+------------ A | 10 0 0 B | 0 20 0 C | 0 0 30
Model pro 10 očekávaných odpovědí A skutečně desetkrát odpověděl „A“ atd. Celkem se provedlo 10+20+30 testů.
Naopak může model nesprávně rozlišovat mezi odpověďmi A a B. Potom může matice vypadat například takto:
| A B C --+------------ A | 7 3 0 B | 0 20 0 C | 0 0 30
Nebo takto:
| A B C --+------------ A | 10 0 0 B | 10 10 0 C | 0 0 30
Zkoumáním obsahu matice záměn můžeme zjistit nejenom citlivost modelu, ale i specificitu modelu (což je mnohdy důležitější atribut – ještě se k němu vrátíme).
Matice záměn může obsahovat i relativní hodnoty, které jsou nezávislé na počtu měření. Maximální hodnota prvku v takové matici je rovna 1.0 a minimální pochopitelně 0.0.
8. Vizualizace matice záměn s absolutními i relativními odchylkami pro model lineární regrese
Podívejme se nyní na způsob výpočtu a vizualizace matice záměn (confusion matrix). Nejprve zkonstruujeme nějaký model, natrénujeme ho běžným způsobem a taktéž ho necháme odhadnout výsledky pro testovací (nikoli trénovací!) data. Tyto kroky již velmi dobře známe:
# konstrukce klasifikatoru # (s hyperparametrem) classifier = LogisticRegression(max_iter=1000) # trening modelu (se vsemi dostupnymi daty) classifier.fit(trainX, trainY) y_pred = classifier.predict(testX)
Následně si na základě testovacích dat necháme vypočítat matici záměn. Ta může obsahovat buď absolutní hodnoty (tedy jednotlivé testy a jejich výsledky odhadnuté modelem) nebo hodnoty relativní. Matici záměn s absolutními hodnotami získáme takto:
# absolutni hodnoty disp = ConfusionMatrixDisplay.from_estimator( classifier, testX, testY, display_labels=class_names, cmap=plt.cm.Blues, normalize=None, )
Naopak matici s relativními hodnotami (nezávislými na počtu testů) si necháme vypočítat tímto způsobem:
# relativni hodnoty disp = ConfusionMatrixDisplay.from_estimator( classifier, testX, testY, display_labels=class_names, cmap=plt.cm.Blues, normalize="true", )
Úplný zdrojový kód skriptu, který tyto výpočty provádí a obě matice následně zobrazí, vypadá následovně:
import matplotlib.pyplot as plt from sklearn.datasets import load_iris from sklearn.model_selection import train_test_split from sklearn.linear_model import LogisticRegression from sklearn.metrics import classification_report from sklearn.metrics import ConfusionMatrixDisplay # nacteni datove sady iris = load_iris() # X je matice (feature matrix) X = iris.data # y je vektor (response vector) y = iris.target # rozdělení dat trainX, testX, trainY, testY = train_test_split(X, y, test_size = 0.7) # konstrukce klasifikatoru # (s hyperparametrem) classifier = LogisticRegression(max_iter=1000) # trening modelu (se vsemi dostupnymi daty) classifier.fit(trainX, trainY) y_pred = classifier.predict(testX) print(classification_report(testY, y_pred)) class_names = iris.target_names # absolutni hodnoty disp = ConfusionMatrixDisplay.from_estimator( classifier, testX, testY, display_labels=class_names, cmap=plt.cm.Blues, normalize=None, ) # zobrazeni matice print(disp.confusion_matrix) # ulozeni vysledku plt.savefig("148_1.png") # vizualizace matice plt.show() # relativni hodnoty disp = ConfusionMatrixDisplay.from_estimator( classifier, testX, testY, display_labels=class_names, cmap=plt.cm.Blues, normalize="true", ) # zobrazeni matice print(disp.confusion_matrix) # ulozeni vysledku plt.savefig("148_2.png") # vizualizace matice plt.show()
9. Získané a vizualizované výsledky
Po spuštění skriptu z předchozí kapitoly se nejdříve zobrazí vypočtené informace o validaci modelu, které byly získané zavoláním classification_report (tyto informace nás však prozatím nebudou zajímat, vyžadují totiž hlubší porozumění jednotlivým veličinám):
precision recall f1-score support 0 1.00 1.00 1.00 39 1 1.00 0.94 0.97 35 2 0.94 1.00 0.97 31 accuracy 0.98 105 macro avg 0.98 0.98 0.98 105 weighted avg 0.98 0.98 0.98 105
Důležitější je samotná matice záměn, která vypadá následovně:
[[39 0 0] [ 0 33 2] [ 0 0 31]]
Z matice je patrné, že se celkem otestovalo 39+33+31+2=105 vstupů, což odpovídá nastavení test_size=0.7. Přitom první druh květiny byl rozeznán vždy, ale u dalších dvou druhů se model ve dvou případech spletl. Ideálně by totiž tato matice měla vypadat takto:
[[39 0 0] [ 0 33 0] [ 0 0 33]]
Aby byly výsledky nezávislé na počtu otestovaných záznamů, je lepší použít relativní vyjádření, které dopadne následovně:
[[1. 0. 0. ] [0. 0.94285714 0.05714286] [0. 0. 1. ]]
Opět platí, že v ideálním případě by se mělo jednat o jednotkovou matici.
Vizuální výsledky ve formě diagramu jsou ještě názornější, neboť jsou přidány i popisky jednotlivých os:

Obrázek 8: Matice záměn s absolutními odchylkami.

Obrázek 9: Matice záměn s relativními odchylkami.
10. Matice záměn pro odlišný model: hledání K nejbližších sousedů
Samozřejmě nám vůbec nic nebrání v tom, abychom se pokusili matici záměn vypočítat i pro odlišné modely. Společně s datovou sadou Iris jsme již několikrát použili model KNeighborsClassifier, který provádí klasifikaci na základě nalezení K sousedů k testovanému bodu (atributy leží v n-rozměrném prostoru a od testovaného bodu postupně rozšiřujeme oblast a hledáme sousedy). Tento model by mohl být přesnější, než model lineární regrese, takže si to ověřme:
import matplotlib.pyplot as plt from sklearn.datasets import load_iris from sklearn.model_selection import train_test_split from sklearn.neighbors import KNeighborsClassifier from sklearn.metrics import classification_report from sklearn.metrics import ConfusionMatrixDisplay # nacteni datove sady iris = load_iris() # X je matice (feature matrix) X = iris.data # y je vektor (response vector) y = iris.target # rozdělení dat trainX, testX, trainY, testY = train_test_split(X, y, test_size = 0.5) # konstrukce klasifikatoru # (s hyperparametrem) classifier = KNeighborsClassifier(n_neighbors=5) # trening modelu (se vsemi dostupnymi daty) classifier.fit(trainX, trainY) y_pred = classifier.predict(testX) print(classification_report(testY, y_pred)) class_names = iris.target_names # absolutni hodnoty disp = ConfusionMatrixDisplay.from_estimator( classifier, testX, testY, display_labels=class_names, cmap=plt.cm.Blues, normalize=None, ) # zobrazeni matice print(disp.confusion_matrix) # ulozeni vysledku plt.savefig("149_1.png") # vizualizace matice plt.show() # relativni hodnoty disp = ConfusionMatrixDisplay.from_estimator( classifier, testX, testY, display_labels=class_names, cmap=plt.cm.Blues, normalize="true", ) # zobrazeni matice print(disp.confusion_matrix) # ulozeni vysledku plt.savefig("149_2.png") # vizualizace matice plt.show()
11. Získané a vizualizované výsledky
Opět se podívejme na výsledky, které jsme získali po spuštění skriptu z předchozí kapitoly. Podle očekávání budou výsledky nepatrně odlišné, protože je jiný i model, který testujeme:
precision recall f1-score support 0 1.00 1.00 1.00 18 1 0.89 0.94 0.91 33 2 0.91 0.83 0.87 24 accuracy 0.92 75 macro avg 0.93 0.92 0.93 75 weighted avg 0.92 0.92 0.92 75
Z maticí záměn je patrné, že se opět model nemohl vždy správně rozhodnout mezi druhým a třetím druhem květin, zatímco druh první rozpoznal vždy na 100%:
[[18 0 0] [ 0 31 2] [ 0 4 20]] [[1. 0. 0. ] [0. 0.93939394 0.06060606] [0. 0.16666667 0.83333333]]
A jak správně tušíte, je vizualizace matice záměn formou diagramu ještě názornější:

Obrázek 10: Matice záměn s absolutními odchylkami.

Obrázek 11: Matice záměn s relativními odchylkami.
12. Matice záměn pro klasifikátor implementovaný pomocí neuronové sítě
Napotřetí si matici záměn necháme zobrazit pro klasifikátor, který je implementovaný s využitím neuronové sítě. Jedná se tedy o model typu MLPClassifier, s nímž jsme se podrobně seznámili v předchozím článku:
import matplotlib.pyplot as plt from sklearn.datasets import load_iris from sklearn.model_selection import train_test_split from sklearn.metrics import classification_report from sklearn.metrics import ConfusionMatrixDisplay # model zalozeny na neuronove siti from sklearn.neural_network import MLPClassifier # nacteni datove sady iris = load_iris() # X je matice (feature matrix) X = iris.data # y je vektor (response vector) y = iris.target # rozdělení dat trainX, testX, trainY, testY = train_test_split(X, y, test_size = 0.5) # konstrukce klasifikatoru # (s hyperparametrem) classifier = MLPClassifier(max_iter=5000) # trening modelu (se vsemi dostupnymi daty) classifier.fit(trainX, trainY) y_pred = classifier.predict(testX) print(classification_report(testY, y_pred)) class_names = iris.target_names # absolutni hodnoty disp = ConfusionMatrixDisplay.from_estimator( classifier, testX, testY, display_labels=class_names, cmap=plt.cm.Blues, normalize=None, ) # zobrazeni matice print(disp.confusion_matrix) # ulozeni vysledku plt.savefig("150_1.png") # vizualizace matice plt.show() # relativni hodnoty disp = ConfusionMatrixDisplay.from_estimator( classifier, testX, testY, display_labels=class_names, cmap=plt.cm.Blues, normalize="true", ) # zobrazeni matice print(disp.confusion_matrix) # ulozeni vysledku plt.savefig("150_2.png") # vizualizace matice plt.show()
13. Získané a vizualizované výsledky
A opět se podívejme na výsledky získané skriptem uvedeným v předchozí kapitole:
precision recall f1-score support 0 1.00 1.00 1.00 25 1 0.96 0.96 0.96 23 2 0.96 0.96 0.96 27 accuracy 0.97 75 macro avg 0.97 0.97 0.97 75 weighted avg 0.97 0.97 0.97 75
Z matice záměn je patrné, že i neuronová síť má, podobně jako ostatní dva modely, problém rozlišit druhé dva druhy květin, zatímco první druh odliší ve všech případech (což mnohé napovídá o volbě atributů):
[25 0 0] [ 0 22 1] [ 0 1 26]] [[1. 0. 0. ] [0. 0.95652174 0.04347826] [0. 0.03703704 0.96296296]]
A takto vypadá vizualizovaný výsledek obou matic záměn (s absolutními i relativními odchylkami):

Obrázek 12: Matice záměn s absolutními odchylkami.

Obrázek 13: Matice záměn s relativními odchylkami.
14. Lze regresní neuronovou síť naučit malou násobilku?
Nyní již známe způsob konstrukce a tréninku neuronové sítě provádějící regresi. To znamená, že dokážeme zkonstruovat model, který na základě několika numerických vstupů vypočte jeden numerický výstup. Je tedy možné například vytvořit neuronovou síť, která dokáže vypočítat malou násobilku? Nejedná se o typický případ využití neuronových sítí, ale o něco podobného se samozřejmě můžeme pokusit. Tato sít bude mít dva vstupy (tedy dva neurony ve vstupní vrstvě) a jeden výstup (jediný neuron ve výstupní vrstvě). A zvolme například, že síť bude obsahovat dvě skryté vrstvy, každou se 100 neurony:
# konstrukce modelu nn = MLPRegressor(max_iter=5000, hidden_layer_sizes=(100, 100))
Tréninková a validační data budou tvořena maticí vstupů, tedy všech kombinací celočíselných hodnot 0..10. A výstupy (trénovací hodnoty) budou tvořeny součinem vstupů:
# X je matice, y je vektor X = np.zeros( (MAX_N*MAX_N, 2) ) # kombinace cinitelu y = np.zeros( (MAX_N*MAX_N, )) # vektor soucinu i = 0 for a in range(1, MAX_N+1): for b in range(1, MAX_N+1): X[i, 0] = a # cinitel X[i, 1] = b # cinitel y[i] = a * b # soucin i+=1
Model následně natrénujeme a otestujeme ho na několika zadaných hodnotách a a b. Teoreticky by měl model odpovědět celým číslem, ovšem regresní sítě vrací reálné hodnoty, takže musíme provést zaukrouhlení:
import numpy as np from sklearn.model_selection import train_test_split from sklearn.metrics import mean_squared_error, r2_score # model zalozeny na neuronove siti from sklearn.neural_network import MLPRegressor # velikost tabulky soucinu MAX_N = 10 # X je matice, y je vektor X = np.zeros( (MAX_N*MAX_N, 2) ) # kombinace cinitelu y = np.zeros( (MAX_N*MAX_N, )) # vektor soucinu i = 0 for a in range(1, MAX_N+1): for b in range(1, MAX_N+1): X[i, 0] = a # cinitel X[i, 1] = b # cinitel y[i] = a * b # soucin i+=1 # rozdeleni dat na treninkovou a testovaci mnozinu X_train, X_test, y_train, y_test = train_test_split(X, y, test_size=0.5) # konstrukce modelu nn = MLPRegressor(max_iter=5000, hidden_layer_sizes=(100, 100)) # trénink modelu nn.fit(X_train, y_train) # predikce modelu y_pred = nn.predict(X_test) # chyba predikce print("Mean squared error: %.2f" % mean_squared_error(y_test, y_pred)) # 1 = nejlepší predikce modelu print("Coefficient of determination: %.2f" % r2_score(y_test, y_pred)) # zobrazit parametry neuronove site print(f"Features: {nn.n_features_in_}") print(f"Layers: {nn.n_layers_}") print(f"Outputs: {nn.n_outputs_}") print("Weights:") # vahy neuronu for layer, weights in enumerate(nn.coefs_): print("\t", layer, weights.shape) # posuny (dalsi vstup do neuronu) print("Biases:") for layer, biases in enumerate(nn.intercepts_): print("\t", layer, biases.shape) # nezname vstupy inputs = [[1, 1], [2, 3], [5, 5], [4, 10], [10, 4], [9, 9], [10, 10]] predicted = nn.predict(inputs) # odhady neuronove site bez dalsich uprav print("w/o rounding:") for i, p in zip(inputs, predicted): print(f"{i[0]:2} * {i[1]:2} = {p:6.2f}") # odhady neuronove site po zaokrouhleni print("rounded:") for i, p in zip(inputs, predicted): print(f"{i[0]:2} * {i[1]:2} = {int(p):2}")
15. Výsledek: neuronová síť na úrovni prváka
Při numerickém vyjádření kvality modelu (tedy neuronové sítě) dostaneme skóre 1.0, což je podezřele dobrý výsledek (ovšem trénujeme i validujeme nad stejnými daty!):
Mean squared error: 0.34 Coefficient of determination: 1.00
Vlastnosti neuronové sítě odpovídají hodnotám, které jsme zadali konstruktoru MLPClassifier:
Features: 2 Layers: 4 Outputs: 1 Weights: 0 (2, 100) 1 (100, 100) 2 (100, 1) Biases: 0 (100,) 1 (100,) 2 (1,)
Zajímavější jsou však výsledky neuronové sítě pro zadané hodnoty a a b. Síť vrátí reálné číslo, které by se mělo přibližovat korektnímu výsledku součinu:
w/o rounding: 1 * 1 = -0.12 2 * 3 = 6.50 5 * 5 = 24.62 4 * 10 = 40.02 10 * 4 = 40.73 9 * 9 = 81.74 10 * 10 = 98.44
Po zaokrouhlení získáme sérii zcela korektních výsledků, ale i výsledky, které se (nepatrně) odlišují od korektního součinu. Problémy nastávají zejména na obou „mezích“ tabulky malé násobilky, tj. pro hodnoty blízké jedničce a naopak pro hodnoty blízké 100:
rounded: 1 * 1 = 0 špatně 2 * 3 = 6 5 * 5 = 24 špatně 4 * 10 = 40 10 * 4 = 40 9 * 9 = 81 10 * 10 = 98 špatně
16. Vizualizace rozdílů předpovědí neuronové sítě od korektních výsledků
Pro model provádějící regresi a nikoli klasifikaci sice nemůžeme použít matici záměn, ale můžeme si pomoci jiným způsobem. Vypočteme si například rozdíl mezi očekávanými výsledky a výsledky vypočtenými modelem. Bude se opět jednat o matici 10×10:
# korektni tabulka male nasobilky W = y.reshape((MAX_N, MAX_N)) print("Relative errors:") errors = (100*(Z-W)/W).astype("int") print(errors)
A takovou matici již můžeme zobrazit i formou grafu:
# vizualizace chyb plt.matshow(Z-W)
Podívejme se tedy na skript, který nejprve natrénuje neuronovou síť na výpočet malé násobilky, potom nechá tuto síť vytvořit tabulku (matici) malé násobilky a následně zobrazí chyby (jak ve tvaru matice, tak i grafu):
import numpy as np import matplotlib.pyplot as plt # model zalozeny na neuronove siti from sklearn.neural_network import MLPRegressor # velikost tabulky soucinu MAX_N = 10 # X je matice, y je vektor X = np.zeros( (MAX_N*MAX_N, 2) ) # kombinace cinitelu y = np.zeros( (MAX_N*MAX_N, )) # vektor soucinu i = 0 for a in range(1, MAX_N+1): for b in range(1, MAX_N+1): X[i, 0] = a # cinitel X[i, 1] = b # cinitel y[i] = a * b # soucin i+=1 # konstrukce modelu nn = MLPRegressor(max_iter=5000, hidden_layer_sizes=(100, 100)) # trénink modelu nad vsemi daty nn.fit(X, y) # zobrazit parametry neuronove site print(f"Features: {nn.n_features_in_}") print(f"Layers: {nn.n_layers_}") print(f"Outputs: {nn.n_outputs_}") print("Weights:") # vahy neuronu for layer, weights in enumerate(nn.coefs_): print("\t", layer, weights.shape) # posuny (dalsi vstup do neuronu) print("Biases:") for layer, biases in enumerate(nn.intercepts_): print("\t", layer, biases.shape) # odhady (odpovedi) neuronove site po uprave do matice 10x10 Z = nn.predict(X).round().reshape((MAX_N, MAX_N)) print("Prediction:") print(Z) # korektni tabulka male nasobilky W = y.reshape((MAX_N, MAX_N)) print("Relative errors:") errors = (100*(Z-W)/W).astype("int") print(errors) # vizualizace chyb plt.matshow(Z-W) # ulozeni vysledku plt.savefig("152.png") # zobrazeni plt.show()
17. Numerické i grafické výsledky korektnosti výpočtů tabulky malé násobilky
Po spuštění výše uvedeného skriptu se nejprve zobrazí parametry neuronové sítě, což již dobře známe:
Features: 2 Layers: 4 Outputs: 1 Weights: 0 (2, 100) 1 (100, 100) 2 (100, 1) Biases: 0 (100,) 1 (100,) 2 (1,)
Dále se zobrazí tabulka malé násobilky vypočtená neuronovou sítí (s chybami!):
Prediction: [[-0. 2. 3. 4. 5. 6. 7. 8. 9. 10.] [ 2. 4. 6. 8. 10. 12. 14. 16. 18. 20.] [ 3. 6. 9. 12. 15. 18. 21. 24. 27. 30.] [ 4. 8. 12. 16. 20. 24. 28. 32. 36. 40.] [ 5. 10. 15. 20. 25. 30. 35. 40. 45. 50.] [ 6. 12. 18. 24. 30. 36. 42. 48. 54. 60.] [ 7. 14. 21. 28. 35. 42. 49. 56. 63. 70.] [ 8. 15. 24. 32. 40. 48. 57. 65. 73. 80.] [ 9. 18. 27. 36. 45. 54. 63. 73. 82. 89.] [10. 20. 30. 40. 50. 61. 70. 80. 89. 98.]]
Relativní chyby vyjádřené v procentech nejsou většinou příliš velké, až na ten nejjednodušší výpočet 1×1 :-)
Relative errors: [[-100 0 0 0 0 0 0 0 0 0] [ 0 0 0 0 0 0 0 0 0 0] [ 0 0 0 0 0 0 0 0 0 0] [ 0 0 0 0 0 0 0 0 0 0] [ 0 0 0 0 0 0 0 0 0 0] [ 0 0 0 0 0 0 0 0 0 0] [ 0 0 0 0 0 0 0 0 0 0] [ 0 -6 0 0 0 0 1 1 1 0] [ 0 0 0 0 0 0 0 1 1 -1] [ 0 0 0 0 0 1 0 0 -1 -2]]
Vizuální zobrazení chyb pro čtyři běhy skriptu (síť se pokaždé natrénuje odlišně):

Obrázek 14: Z grafu je patrné, ve kterých místech neuronová síť nejvíce chybuje (horní a dolní roh).

Obrázek 15: Výsledky pro nepatrně odlišně natrénovanou sít.

Obrázek 16: Výsledky pro nepatrně odlišně natrénovanou sít.

Obrázek 17: Výsledky pro nepatrně odlišně natrénovanou sít.
18. Dokáže takto natrénovaná neuronová síť generalizovat?
Nyní si otestujme, jestli neuronová síť natrénovaná pouze na výpočet malé násobilky dokáže provádět součiny i pro větší hodnoty (například od 1 do 20, tedy nejvyšším očekávaným výsledkem bude 20×20=400). Otestujeme tedy, jestli neuronová síť dokáže nějakým způsobem generalizovat to, co se naučila (a jestli si jako celek udělala správný „mentální model“ řešeného problému). Předchozí skript tedy upravíme tak, že nejdříve neuronovou síť běžným způsobem natrénujeme pro malou násobilku a posléze jí pošleme pro ohodnocení matici s kombinacemi činitelů 0 až 20, což znamená, že jen 25% vstupů tato síť „viděla“ při tréninku (MAXN se liší od MAX_TO_COMPUTE):
import numpy as np import matplotlib.pyplot as plt # model zalozeny na neuronove siti from sklearn.neural_network import MLPRegressor # velikost tabulky soucinu MAX_N = 10 # X je matice, y je vektor X = np.zeros( (MAX_N*MAX_N, 2) ) # kombinace cinitelu y = np.zeros( (MAX_N*MAX_N, )) # vektor soucinu i = 0 for a in range(1, MAX_N+1): for b in range(1, MAX_N+1): X[i, 0] = a # cinitel X[i, 1] = b # cinitel y[i] = a * b # soucin i+=1 # konstrukce modelu nn = MLPRegressor(max_iter=5000, hidden_layer_sizes=(100, 100)) # trénink modelu nad vsemi daty nn.fit(X, y) # zobrazit parametry neuronove site print(f"Features: {nn.n_features_in_}") print(f"Layers: {nn.n_layers_}") print(f"Outputs: {nn.n_outputs_}") print("Weights:") # vahy neuronu for layer, weights in enumerate(nn.coefs_): print("\t", layer, weights.shape) # posuny (dalsi vstup do neuronu) print("Biases:") for layer, biases in enumerate(nn.intercepts_): print("\t", layer, biases.shape) MAX_TO_COMPUTE = 20 X2 = np.zeros( (MAX_TO_COMPUTE*MAX_TO_COMPUTE, 2) ) # kombinace cinitelu y2 = np.zeros( (MAX_TO_COMPUTE*MAX_TO_COMPUTE, )) # vektor soucinu i = 0 for a in range(1, MAX_TO_COMPUTE+1): for b in range(1, MAX_TO_COMPUTE+1): X2[i, 0] = a # cinitel X2[i, 1] = b # cinitel y2[i] = a * b # soucin i+=1 # odhady (odpovedi) neuronove site po uprave do matice 10x10 Z = nn.predict(X2).round().reshape((MAX_TO_COMPUTE, MAX_TO_COMPUTE)) print("Prediction:") print(Z) # korektni tabulka male nasobilky W = y2.reshape((MAX_TO_COMPUTE, MAX_TO_COMPUTE)) print("Relative errors:") errors = (100*(Z-W)/W).astype("int") print(errors) # vizualizace chyb plt.matshow(Z-W) # ulozeni vysledku plt.savefig("153.png") # zobrazeni plt.show()
Skript po svém spuštění opět zobrazí základní parametry neuronové sítě (ta se přitom nijak nezměnila):
Features: 2 Layers: 4 Outputs: 1 Weights: 0 (2, 100) 1 (100, 100) 2 (100, 1) Biases: 0 (100,) 1 (100,) 2 (1,)
Výsledky pro vyšší činitele již nejsou nijak oslňující – tuto část se neuronová síť evidentně nenaučila ani neprovedla generalizaci:
Prediction: [[ 0. 2. 3. 4. 5. 6. 7. 8. 9. 10. 12. 13. 15. 18. 20. 22. 25. 27. 29. 32.] [ 1. 4. 7. 8. 10. 12. 14. 16. 18. 20. 22. 24. 26. 28. 31. 33. 35. 38. 40. 42.] [ 3. 6. 9. 12. 15. 18. 21. 24. 27. 30. 33. 35. 37. 40. 42. 44. 47. 49. 51. 54.] [ 4. 8. 12. 16. 19. 24. 28. 32. 36. 40. 44. 47. 50. 52. 54. 56. 59. 61. 63. 66.] [ 5. 10. 15. 20. 25. 30. 35. 40. 45. 50. 54. 58. 62. 65. 67. 69. 71. 73. 76. 78.] [ 6. 12. 18. 24. 30. 36. 42. 48. 54. 60. 65. 70. 73. 77. 80. 83. 85. 87. 89. 91.] [ 7. 14. 21. 28. 35. 42. 49. 56. 64. 70. 75. 81. 86. 90. 93. 97. 99. 101. 103. 105.] [ 8. 16. 24. 32. 40. 48. 57. 66. 73. 80. 86. 92. 97. 102. 106. 110. 113. 116. 118. 120.] [ 9. 18. 27. 36. 45. 54. 63. 73. 82. 89. 96. 102. 108. 113. 118. 122. 126. 129. 132. 135.] [ 10. 20. 30. 40. 50. 60. 70. 80. 89. 98. 106. 112. 118. 123. 129. 134. 138. 142. 145. 148.] [ 12. 22. 33. 44. 54. 65. 76. 86. 96. 105. 114. 121. 128. 133. 139. 144. 150. 154. 158. 162.] [ 15. 25. 36. 47. 59. 70. 81. 92. 102. 112. 121. 129. 137. 143. 149. 154. 160. 165. 170. 174.] [ 17. 28. 39. 50. 62. 74. 86. 97. 108. 117. 127. 136. 145. 152. 159. 164. 170. 175. 181. 186.] [ 20. 31. 41. 53. 65. 78. 90. 102. 113. 123. 133. 142. 151. 160. 167. 174. 180. 185. 191. 196.] [ 23. 33. 44. 56. 67. 81. 94. 106. 118. 129. 139. 148. 157. 166. 175. 182. 189. 195. 200. 206.] [ 26. 36. 47. 58. 70. 83. 97. 111. 122. 133. 144. 154. 163. 173. 181. 190. 198. 204. 210. 216.] [ 28. 39. 50. 61. 73. 86. 100. 114. 126. 138. 149. 159. 169. 179. 188. 196. 205. 213. 220. 226.] [ 31. 42. 53. 64. 76. 89. 102. 117. 131. 142. 154. 165. 175. 185. 194. 203. 212. 220. 228. 235.] [ 34. 45. 55. 67. 79. 91. 105. 119. 133. 147. 158. 169. 180. 190. 200. 209. 218. 227. 235. 243.] [ 37. 47. 58. 70. 81. 94. 108. 121. 136. 150. 163. 174. 185. 196. 206. 215. 224. 233. 242. 250.]]
Ještě více je to patrné při vyjádření relativní chyby:
Relative errors: [[-100 0 0 0 0 0 0 0 0 0 9 8 15 28 33 37 47 50 52 60] [ -50 0 16 0 0 0 0 0 0 0 0 0 0 0 3 3 2 5 5 5] [ 0 0 0 0 0 0 0 0 0 0 0 -2 -5 -4 -6 -8 -7 -9 -10 -10] [ 0 0 0 0 -5 0 0 0 0 0 0 -2 -3 -7 -10 -12 -13 -15 -17 -17] [ 0 0 0 0 0 0 0 0 0 0 -1 -3 -4 -7 -10 -13 -16 -18 -20 -22] [ 0 0 0 0 0 0 0 0 0 0 -1 -2 -6 -8 -11 -13 -16 -19 -21 -24] [ 0 0 0 0 0 0 0 0 1 0 -2 -3 -5 -8 -11 -13 -16 -19 -22 -25] [ 0 0 0 0 0 0 1 3 1 0 -2 -4 -6 -8 -11 -14 -16 -19 -22 -25] [ 0 0 0 0 0 0 0 1 1 -1 -3 -5 -7 -10 -12 -15 -17 -20 -22 -25] [ 0 0 0 0 0 0 0 0 -1 -2 -3 -6 -9 -12 -14 -16 -18 -21 -23 -26] [ 9 0 0 0 -1 -1 -1 -2 -3 -4 -5 -8 -10 -13 -15 -18 -19 -22 -24 -26] [ 25 4 0 -2 -1 -2 -3 -4 -5 -6 -8 -10 -12 -14 -17 -19 -21 -23 -25 -27] [ 30 7 0 -3 -4 -5 -5 -6 -7 -10 -11 -12 -14 -16 -18 -21 -23 -25 -26 -28] [ 42 10 -2 -5 -7 -7 -8 -8 -10 -12 -13 -15 -17 -18 -20 -22 -24 -26 -28 -30] [ 53 10 -2 -6 -10 -10 -10 -11 -12 -14 -15 -17 -19 -20 -22 -24 -25 -27 -29 -31] [ 62 12 -2 -9 -12 -13 -13 -13 -15 -16 -18 -19 -21 -22 -24 -25 -27 -29 -30 -32] [ 64 14 -1 -10 -14 -15 -15 -16 -17 -18 -20 -22 -23 -24 -26 -27 -29 -30 -31 -33] [ 72 16 -1 -11 -15 -17 -19 -18 -19 -21 -22 -23 -25 -26 -28 -29 -30 -32 -33 -34] [ 78 18 -3 -11 -16 -20 -21 -21 -22 -22 -24 -25 -27 -28 -29 -31 -32 -33 -34 -36] [ 85 17 -3 -12 -19 -21 -22 -24 -24 -25 -25 -27 -28 -30 -31 -32 -34 -35 -36 -37]]
Poslední věcí, kterou si dnes ukážeme, je vizualizace chyb na grafu:

Obrázek 18: Vizualizace chyb pro vstupní činitele od 1 do 20.
19. Repositář s demonstračními příklady
Všechny demonstrační příklady využívající knihovnu Scikit-learn lze nalézt v repositáři https://github.com/tisnik/most-popular-python-libs. Následují odkazy na jednotlivé příklady i na (Jupyter) diáře s postupem výpočtů a analýz:
V repositáři nalezneme taktéž projektový soubor a Jupyter Notebook s vysvětlením, jak lze modely využít pro rozpoznávání obsahu rastrových obrázků:
# | Příklad | Stručný popis | Adresa příkladu |
---|---|---|---|
1 | pyproject.toml | projektový soubor (pro PDM) se všemi závislostmi | https://github.com/tisnik/most-popular-python-libs/blob/master/sklearn/pyproject.toml |
2 | pdm.lock | lock soubor s konkrétními verzemi všech přímých i tranzitivních závislostí | https://github.com/tisnik/most-popular-python-libs/blob/master/sklearn/pdm.lock |
3 | Rozpoznání_obrazu_scikit-learn.ipynb | Jupyter notebook s celým postupem | https://github.com/tisnik/most-popular-python-libs/blob/master/sklearn/Rozpoznání_obrazu_scikit-learn.ipynb |
4 | particle_life.py | emergence: příklad vzniku struktury | https://github.com/tisnik/most-popular-python-libs/blob/master/particles/particle_life.py |
20. Odkazy na Internetu
- Shluková analýza (clustering) a knihovna Scikit-learn
https://www.root.cz/clanky/shlukova-analyza-clustering-a-knihovna-scikit-learn/ - Shluková analýza (clustering) a knihovna Scikit-learn (2)
https://www.root.cz/clanky/shlukova-analyza-clustering-a-knihovna-scikit-learn-2/ - Shluková analýza (clustering) a knihovna Scikit-learn (z plochy do 3D prostoru)
https://www.root.cz/clanky/shlukova-analyza-clustering-a-knihovna-scikit-learn-z-plochy-do-3d-prostoru/ - Rozpoznávání obrázků knihovnou Scikit-learn: první kroky
https://www.root.cz/clanky/rozpoznavani-obrazku-knihovnou-scikit-learn-prvni-kroky/ - scikit-learn: Machine Learning in Python
https://scikit-learn.org/stable/index.html - Sklearn-pandas
https://github.com/scikit-learn-contrib/sklearn-pandas - sklearn-xarray
https://github.com/phausamann/sklearn-xarray/ - Clustering
https://scikit-learn.org/stable/modules/clustering.html - Cluster analysis (Wikipedia)
https://en.wikipedia.org/wiki/Cluster_analysis - Shluková analýza (Wikipedia)
https://cs.wikipedia.org/wiki/Shlukov%C3%A1_anal%C3%BDza - K-means
https://cs.wikipedia.org/wiki/K-means - k-means clustering
https://en.wikipedia.org/wiki/K-means_clustering - Spectral clustering
https://en.wikipedia.org/wiki/Spectral_clustering - Emergence
https://cs.wikipedia.org/wiki/Emergence - Particle Life: Vivid structures from rudimentary rules
https://particle-life.com/ - Hertzsprungův–Russellův diagram
https://cs.wikipedia.org/wiki/Hertzsprung%C5%AFv%E2%80%93Russell%C5%AFv_diagram - Using Machine Learning in an HR Diagram
https://cocalc.com/share/public_paths/08b6e03583cbdef3cdb9813a54ec68ff773c747f - Gaia H-R diagrams: Querying Gaia data for one million nearby stars
https://vlas.dev/post/gaia-dr2-hrd/ - The Hertzsprung–Russell diagram
https://scipython.com/book2/chapter-9-data-analysis-with-pandas/problems/p92/the-hertzsprung-russell-diagram/ - Animated Hertzsprung-Russell Diagram with 119,614 datapoints
https://github.com/zonination/h-r-diagram - Neuraxle Pipelines
https://github.com/Neuraxio/Neuraxle - scikit-learn: Getting Started
https://scikit-learn.org/stable/getting_started.html - Support Vector Machines
https://scikit-learn.org/stable/modules/svm.html - Use Deep Learning to Detect Programming Languages
http://searene.me/2017/11/26/use-neural-networks-to-detect-programming-languages/ - Natural-language processing
https://en.wikipedia.org/wiki/Natural-language_processing - THE MNIST DATABASE of handwritten digits
http://yann.lecun.com/exdb/mnist/ - MNIST database (Wikipedia)
https://en.wikipedia.org/wiki/MNIST_database - MNIST For ML Beginners
https://www.tensorflow.org/get_started/mnist/beginners - Stránka projektu Torch
http://torch.ch/ - Torch: Serialization
https://github.com/torch/torch7/blob/master/doc/serialization.md - Torch: modul image
https://github.com/torch/image/blob/master/README.md - Data pro neuronové sítě
http://archive.ics.uci.edu/ml/index.php - Torch na GitHubu (několik repositářů)
https://github.com/torch - Torch (machine learning), Wikipedia
https://en.wikipedia.org/wiki/Torch_%28machine_learning%29 - Torch Package Reference Manual
https://github.com/torch/torch7/blob/master/README.md - Torch Cheatsheet
https://github.com/torch/torch7/wiki/Cheatsheet - Neural network containres (Torch)
https://github.com/torch/nn/blob/master/doc/containers.md - Simple layers
https://github.com/torch/nn/blob/master/doc/simple.md#nn.Linear - Transfer Function Layers
https://github.com/torch/nn/blob/master/doc/transfer.md#nn.transfer.dok - Feedforward neural network
https://en.wikipedia.org/wiki/Feedforward_neural_network - Biologické algoritmy (4) – Neuronové sítě
https://www.root.cz/clanky/biologicke-algoritmy-4-neuronove-site/ - Biologické algoritmy (5) – Neuronové sítě
https://www.root.cz/clanky/biologicke-algoritmy-5-neuronove-site/ - Umělá neuronová síť (Wikipedia)
https://cs.wikipedia.org/wiki/Um%C4%9Bl%C3%A1_neuronov%C3%A1_s%C3%AD%C5%A5 - PyTorch
http://pytorch.org/ - JupyterLite na PyPi
https://pypi.org/project/jupyterlite/ - JupyterLite na GitHubu
https://github.com/jupyterlite/jupyterlite - Dokumentace k projektu JupyterLite
https://github.com/jupyterlite/jupyterlite - Matplotlib Home Page
http://matplotlib.org/ - Matplotlib (Wikipedia)
https://en.wikipedia.org/wiki/Matplotlib - Popis barvových map modulu matplotlib.cm
https://gist.github.com/endolith/2719900#id7 - Ukázky (palety) barvových map modulu matplotlib.cm
http://matplotlib.org/examples/color/colormaps_reference.html - Galerie grafů vytvořených v Matplotlibu
https://matplotlib.org/3.2.1/gallery/ - 3D rendering
https://en.wikipedia.org/wiki/3D_rendering - 3D computer graphics
https://en.wikipedia.org/wiki/3D_computer_graphics - Primary 3D view planes
https://matplotlib.org/stable/gallery/mplot3d/view_planes_3d.html - Getting started in scikit-learn with the famous iris dataset
https://www.youtube.com/watch?v=hd1W4CyPX58 - Training a machine learning model with scikit-learn
https://www.youtube.com/watch?v=RlQuVL6-qe8 - Iris (plant)
https://en.wikipedia.org/wiki/Iris_(plant) - Kosatec
https://cs.wikipedia.org/wiki/Kosatec - Iris setosa
https://en.wikipedia.org/wiki/Iris_setosa - Iris versicolor
https://en.wikipedia.org/wiki/Iris_versicolor - Iris virginica
https://en.wikipedia.org/wiki/Iris_virginica - Druh
https://cs.wikipedia.org/wiki/Druh - Iris subg. Limniris
https://en.wikipedia.org/wiki/Iris_subg._Limniris - Iris Dataset Classification with Python: A Tutorial
https://www.pycodemates.com/2022/05/iris-dataset-classification-with-python.html - Iris flower data set
https://en.wikipedia.org/wiki/Iris_flower_data_set - List of datasets for machine-learning research
https://en.wikipedia.org/wiki/List_of_datasets_for_machine-learning_research - Analýza hlavních komponent
https://cs.wikipedia.org/wiki/Anal%C3%BDza_hlavn%C3%ADch_komponent - Principal component analysis
https://en.wikipedia.org/wiki/Principal_component_analysis - Scikit-learn Crash Course – Machine Learning Library for Python
https://www.youtube.com/watch?v=0B5eIE_1vpU - calm-notebooks
https://github.com/koaning/calm-notebooks - Should you teach Python or R for data science?
https://www.dataschool.io/python-or-r-for-data-science/ - nbviewer: A simple way to share Jupyter Notebooks
https://nbviewer.org/ - AI vs Machine Learning (Youtube)
https://www.youtube.com/watch?v=4RixMPF4×is - Machine Learning | What Is Machine Learning? | Introduction To Machine Learning | 2024 | Simplilearn (Youtube)
https://www.youtube.com/watch?v=ukzFI9rgwfU - A Gentle Introduction to Machine Learning (Youtube)
https://www.youtube.com/watch?v=Gv9_4yMHFhI - Machine Learning vs Deep Learning
https://www.youtube.com/watch?v=q6kJ71tEYqM - Umělá inteligence (slajdy)
https://slideplayer.cz/slide/12119218/ - Úvod do umělé inteligence
https://slideplayer.cz/slide/2505525/ - Umělá inteligence I / Artificial Intelligence I
https://ktiml.mff.cuni.cz/~bartak/ui/ - Matplotlib vs. seaborn vs. Plotly vs. MATLAB vs. ggplot2 vs. pandas
https://ritza.co/articles/matplotlib-vs-seaborn-vs-plotly-vs-MATLAB-vs-ggplot2-vs-pandas/ - Matplotlib, Seaborn or Plotnine?
https://www.reddit.com/r/datascience/comments/jvrqxt/matplotlib_seaborn_or_plotnine/ - @Rabeez: Rabeez/plotting_comparison.ipynb
https://gist.github.com/Rabeez/ffc0b59d4a41e20fa8d944c44a96adbc - Matplotlib, Seaborn, Plotly and Plotnine Comparison
https://python.plainenglish.io/matplotlib-seaborn-plotly-and-plotnine-comparison-baf2db5a9c40 - Data Visualization 101: How to Choose a Python Plotting Library
https://towardsdatascience.com/data-visualization-101-how-to-choose-a-python-plotting-library-853460a08a8a - Data science in Python: pandas, seaborn, scikit-learn
https://www.youtube.com/watch?v=3ZWuPVWq7p4 - 7.2. Real world datasets
https://scikit-learn.org/stable/datasets/real_world.html#california-housing-dataset - 7.2.7. California Housing dataset
https://scikit-learn.org/stable/datasets/real_world.html#california-housing-dataset - Comprehensive Guide to Classification Models in Scikit-Learn
https://www.geeksforgeeks.org/comprehensive-guide-to-classification-models-in-scikit-learn/ - Tidy Data Visualization: ggplot2 vs seaborn
https://blog.tidy-intelligence.com/posts/ggplot2-vs-seaborn/ - seaborn: statistical data visualization
https://seaborn.pydata.org/ - Linear regression (Wikipedia)
https://en.wikipedia.org/wiki/Linear_regression - Lineární regrese (Wikipedia)
https://cs.wikipedia.org/wiki/Line%C3%A1rn%C3%AD_regrese - Iris Flower Classification with MLP Classifier
https://www.metriccoders.com/post/iris-flower-classification-with-mlp-classifier