You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
ML-For-Beginners/translations/pl/2-Regression/4-Logistic
leestott 3773c80b49
🌐 Update translations via Co-op Translator
2 weeks ago
..
solution 🌐 Update translations via Co-op Translator 3 weeks ago
README.md 🌐 Update translations via Co-op Translator 2 weeks ago
assignment.md 🌐 Update translations via Co-op Translator 3 weeks ago
notebook.ipynb 🌐 Update translations via Co-op Translator 3 weeks ago

README.md

Regresja logistyczna do przewidywania kategorii

Infografika: regresja logistyczna vs. regresja liniowa

Quiz przed wykładem

Ta lekcja jest dostępna w R!

Wprowadzenie

W tej ostatniej lekcji dotyczącej regresji, jednej z podstawowych klasycznych technik ML, przyjrzymy się regresji logistycznej. Technika ta pozwala odkrywać wzorce w celu przewidywania binarnych kategorii. Czy ten cukierek to czekolada czy nie? Czy ta choroba jest zakaźna czy nie? Czy ten klient wybierze ten produkt czy nie?

W tej lekcji nauczysz się:

  • Nowej biblioteki do wizualizacji danych
  • Technik regresji logistycznej

Pogłęb swoją wiedzę na temat pracy z tego rodzaju regresją w tym module nauki

Wymagania wstępne

Pracując z danymi dotyczącymi dyni, jesteśmy już wystarczająco zaznajomieni z nimi, aby zauważyć, że istnieje jedna binarna kategoria, z którą możemy pracować: Color.

Zbudujmy model regresji logistycznej, aby przewidzieć, na podstawie pewnych zmiennych, jaki kolor ma dana dynia (pomarańczowy 🎃 czy biały 👻).

Dlaczego mówimy o binarnej klasyfikacji w lekcji dotyczącej regresji? Tylko dla wygody językowej, ponieważ regresja logistyczna jest tak naprawdę metodą klasyfikacji, choć opartą na metodach liniowych. Dowiedz się więcej o innych sposobach klasyfikacji danych w kolejnej grupie lekcji.

Zdefiniuj pytanie

Na potrzeby tej lekcji wyrazimy to jako binarną kategorię: 'Biała' lub 'Nie biała'. W naszym zbiorze danych znajduje się również kategoria 'pasiasta', ale jest niewiele jej przypadków, więc jej nie użyjemy. Znika ona zresztą po usunięciu wartości null ze zbioru danych.

🎃 Ciekawostka: białe dynie czasami nazywamy 'dyniami-duchami'. Nie są łatwe do rzeźbienia, więc nie są tak popularne jak pomarańczowe, ale wyglądają bardzo ciekawie! Możemy więc również sformułować nasze pytanie jako: 'Duch' czy 'Nie duch'. 👻

O regresji logistycznej

Regresja logistyczna różni się od regresji liniowej, którą poznaliśmy wcześniej, w kilku istotnych aspektach.

ML dla początkujących - Zrozumienie regresji logistycznej w klasyfikacji danych

🎥 Kliknij obrazek powyżej, aby obejrzeć krótki film o regresji logistycznej.

Klasyfikacja binarna

Regresja logistyczna nie oferuje tych samych funkcji co regresja liniowa. Pierwsza z nich pozwala przewidywać binarne kategorie ("biała czy nie biała"), podczas gdy druga jest w stanie przewidywać wartości ciągłe, na przykład na podstawie pochodzenia dyni i czasu zbioru, o ile wzrośnie jej cena.

Model klasyfikacji dyni

Infografika autorstwa Dasani Madipalli

Inne klasyfikacje

Istnieją inne rodzaje regresji logistycznej, w tym wieloklasowa i porządkowa:

  • Wieloklasowa, która obejmuje więcej niż jedną kategorię - "Pomarańczowa, Biała i Pasiasta".
  • Porządkowa, która obejmuje uporządkowane kategorie, przydatne, jeśli chcemy uporządkować wyniki logicznie, jak nasze dynie, które są uporządkowane według skończonej liczby rozmiarów (mini, mała, średnia, duża, XL, XXL).

Regresja wieloklasowa vs porządkowa

Zmienne NIE muszą być skorelowane

Pamiętasz, jak regresja liniowa działała lepiej z bardziej skorelowanymi zmiennymi? Regresja logistyczna jest odwrotna - zmienne nie muszą być ze sobą powiązane. To działa w przypadku tych danych, które mają raczej słabe korelacje.

Potrzebujesz dużej ilości czystych danych

Regresja logistyczna daje bardziej dokładne wyniki, jeśli używasz większej ilości danych; nasz mały zbiór danych nie jest optymalny do tego zadania, więc miej to na uwadze.

ML dla początkujących - Analiza i przygotowanie danych do regresji logistycznej

🎥 Kliknij obrazek powyżej, aby obejrzeć krótki film o przygotowaniu danych do regresji liniowej.

Zastanów się, jakie typy danych najlepiej nadają się do regresji logistycznej.

Ćwiczenie - uporządkuj dane

Najpierw trochę oczyść dane, usuwając wartości null i wybierając tylko niektóre kolumny:

  1. Dodaj następujący kod:

    
    columns_to_select = ['City Name','Package','Variety', 'Origin','Item Size', 'Color']
    pumpkins = full_pumpkins.loc[:, columns_to_select]
    
    pumpkins.dropna(inplace=True)
    

    Zawsze możesz zajrzeć do swojego nowego dataframe:

    pumpkins.info
    

Wizualizacja - wykres kategorii

Do tej pory załadowałeś notebook startowy z danymi o dyniach i oczyściłeś go, aby zachować zbiór danych zawierający kilka zmiennych, w tym Color. Zwizualizujmy dataframe w notebooku, używając innej biblioteki: Seaborn, która jest zbudowana na Matplotlib, którego używaliśmy wcześniej.

Seaborn oferuje ciekawe sposoby wizualizacji danych. Na przykład możesz porównać rozkłady danych dla każdej Variety i Color na wykresie kategorii.

  1. Utwórz taki wykres, używając funkcji catplot, korzystając z danych o dyniach pumpkins i określając mapowanie kolorów dla każdej kategorii dyni (pomarańczowa lub biała):

    import seaborn as sns
    
    palette = {
    'ORANGE': 'orange',
    'WHITE': 'wheat',
    }
    
    sns.catplot(
    data=pumpkins, y="Variety", hue="Color", kind="count",
    palette=palette, 
    )
    

    Siatka zwizualizowanych danych

    Obserwując dane, możesz zobaczyć, jak dane o kolorze odnoszą się do odmiany.

    Na podstawie tego wykresu kategorii, jakie interesujące eksploracje możesz sobie wyobrazić?

Przetwarzanie danych: kodowanie cech i etykiet

Nasz zbiór danych o dyniach zawiera wartości tekstowe dla wszystkich swoich kolumn. Praca z danymi kategorycznymi jest intuicyjna dla ludzi, ale nie dla maszyn. Algorytmy uczenia maszynowego dobrze działają z liczbami. Dlatego kodowanie jest bardzo ważnym krokiem w fazie przetwarzania danych, ponieważ pozwala nam zamienić dane kategoryczne na dane numeryczne, nie tracąc żadnych informacji. Dobre kodowanie prowadzi do budowy dobrego modelu.

Dla kodowania cech istnieją dwa główne typy kodowania:

  1. Kodowanie porządkowe: dobrze nadaje się do zmiennych porządkowych, które są zmiennymi kategorycznymi, gdzie ich dane mają logiczne uporządkowanie, jak kolumna Item Size w naszym zbiorze danych. Tworzy mapowanie, w którym każda kategoria jest reprezentowana przez liczbę, która jest kolejnością kategorii w kolumnie.

    from sklearn.preprocessing import OrdinalEncoder
    
    item_size_categories = [['sml', 'med', 'med-lge', 'lge', 'xlge', 'jbo', 'exjbo']]
    ordinal_features = ['Item Size']
    ordinal_encoder = OrdinalEncoder(categories=item_size_categories)
    
  2. Kodowanie kategoryczne: dobrze nadaje się do zmiennych nominalnych, które są zmiennymi kategorycznymi, gdzie ich dane nie mają logicznego uporządkowania, jak wszystkie cechy inne niż Item Size w naszym zbiorze danych. Jest to kodowanie typu one-hot, co oznacza, że każda kategoria jest reprezentowana przez binarną kolumnę: zakodowana zmienna jest równa 1, jeśli dynia należy do tej odmiany, a 0 w przeciwnym razie.

    from sklearn.preprocessing import OneHotEncoder
    
    categorical_features = ['City Name', 'Package', 'Variety', 'Origin']
    categorical_encoder = OneHotEncoder(sparse_output=False)
    

Następnie ColumnTransformer jest używany do połączenia wielu kodowań w jeden krok i zastosowania ich do odpowiednich kolumn.

    from sklearn.compose import ColumnTransformer
    
    ct = ColumnTransformer(transformers=[
        ('ord', ordinal_encoder, ordinal_features),
        ('cat', categorical_encoder, categorical_features)
        ])
    
    ct.set_output(transform='pandas')
    encoded_features = ct.fit_transform(pumpkins)

Z kolei do kodowania etykiety używamy klasy LabelEncoder z biblioteki scikit-learn, która jest narzędziem do normalizacji etykiet, tak aby zawierały tylko wartości między 0 a n_classes-1 (tutaj, 0 i 1).

    from sklearn.preprocessing import LabelEncoder

    label_encoder = LabelEncoder()
    encoded_label = label_encoder.fit_transform(pumpkins['Color'])

Po zakodowaniu cech i etykiety możemy połączyć je w nowy dataframe encoded_pumpkins.

    encoded_pumpkins = encoded_features.assign(Color=encoded_label)

Jakie są zalety używania kodowania porządkowego dla kolumny Item Size?

Analiza relacji między zmiennymi

Teraz, gdy przetworzyliśmy nasze dane, możemy przeanalizować relacje między cechami a etykietą, aby zrozumieć, jak dobrze model będzie w stanie przewidzieć etykietę na podstawie cech. Najlepszym sposobem na przeprowadzenie tego rodzaju analizy jest wykreślenie danych. Ponownie użyjemy funkcji catplot z biblioteki Seaborn, aby zwizualizować relacje między Item Size, Variety i Color na wykresie kategorii. Aby lepiej wykreślić dane, użyjemy zakodowanej kolumny Item Size i niezakodowanej kolumny Variety.

    palette = {
    'ORANGE': 'orange',
    'WHITE': 'wheat',
    }
    pumpkins['Item Size'] = encoded_pumpkins['ord__Item Size']

    g = sns.catplot(
        data=pumpkins,
        x="Item Size", y="Color", row='Variety',
        kind="box", orient="h",
        sharex=False, margin_titles=True,
        height=1.8, aspect=4, palette=palette,
    )
    g.set(xlabel="Item Size", ylabel="").set(xlim=(0,6))
    g.set_titles(row_template="{row_name}")

Wykres kategorii zwizualizowanych danych

Użyj wykresu typu swarm

Ponieważ Color jest kategorią binarną (Biała lub Nie), wymaga 'specjalnego podejścia do wizualizacji'. Istnieją inne sposoby wizualizacji relacji tej kategorii z innymi zmiennymi.

Możesz zwizualizować zmienne obok siebie za pomocą wykresów Seaborn.

  1. Wypróbuj wykres typu 'swarm', aby pokazać rozkład wartości:

    palette = {
    0: 'orange',
    1: 'wheat'
    }
    sns.swarmplot(x="Color", y="ord__Item Size", data=encoded_pumpkins, palette=palette)
    

    Swarm zwizualizowanych danych

Uwaga: powyższy kod może wygenerować ostrzeżenie, ponieważ Seaborn nie radzi sobie z reprezentacją takiej ilości punktów danych na wykresie typu swarm. Możliwym rozwiązaniem jest zmniejszenie rozmiaru markerów, używając parametru 'size'. Jednak pamiętaj, że wpływa to na czytelność wykresu.

🧮 Pokaż mi matematykę

Regresja logistyczna opiera się na koncepcji 'maksymalnego prawdopodobieństwa' przy użyciu funkcji sigmoidalnych. 'Funkcja sigmoidalna' na wykresie wygląda jak kształt litery 'S'. Przyjmuje wartość i mapuje ją na zakres między 0 a 1. Jej krzywa jest również nazywana 'krzywą logistyczną'. Jej wzór wygląda tak:

funkcja logistyczna

gdzie środek sigmoidy znajduje się w punkcie 0 osi x, L to maksymalna wartość krzywej, a k to stromość krzywej. Jeśli wynik funkcji jest większy niż 0.5, etykieta zostanie przypisana do klasy '1' w binarnym wyborze. W przeciwnym razie zostanie sklasyfikowana jako '0'.

Zbuduj swój model

Budowanie modelu do znajdowania tych klasyfikacji binarnych jest zaskakująco proste w Scikit-learn.

ML dla początkujących - Regresja logistyczna do klasyfikacji danych

🎥 Kliknij obrazek powyżej, aby obejrzeć krótki film o budowie modelu regresji liniowej.

  1. Wybierz zmienne, które chcesz użyć w swoim modelu klasyfikacji, i podziel zestawy treningowe i testowe, wywołując train_test_split():

    from sklearn.model_selection import train_test_split
    
    X = encoded_pumpkins[encoded_pumpkins.columns.difference(['Color'])]
    y = encoded_pumpkins['Color']
    
    X_train, X_test, y_train, y_test = train_test_split(X, y, test_size=0.2, random_state=0)
    
    
  2. Teraz możesz wytrenować swój model, wywołując fit() z danymi treningowymi, i wydrukować jego wynik:

    from sklearn.metrics import f1_score, classification_report 
    from sklearn.linear_model import LogisticRegression
    
    model = LogisticRegression()
    model.fit(X_train, y_train)
    predictions = model.predict(X_test)
    
    print(classification_report(y_test, predictions))
    print('Predicted labels: ', predictions)
    print('F1-score: ', f1_score(y_test, predictions))
    

    Spójrz na wyniki swojego modelu. Nie jest źle, biorąc pod uwagę, że masz tylko około 1000 wierszy danych:

                       precision    recall  f1-score   support
    
                    0       0.94      0.98      0.96       166
                    1       0.85      0.67      0.75        33
    
        accuracy                                0.92       199
        macro avg           0.89      0.82      0.85       199
        weighted avg        0.92      0.92      0.92       199
    
        Predicted labels:  [0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 1 0 0 1 0 0 0 0 0 0 0 0 1 0 0 0 0
        0 0 0 0 0 1 0 1 0 0 1 0 0 0 0 0 1 0 1 0 1 0 1 0 0 0 0 0 0 0 0 0 0 0 0 0 0
        1 0 0 0 0 0 0 0 1 0 0 0 0 0 0 0 1 0 0 0 0 0 0 0 0 1 0 1 0 0 0 0 0 0 0 1 0
        0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 1 0 0 0 0 0 0 0 0 1 0 0 0 1 1 0
        0 0 0 0 1 0 0 0 0 0 1 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 1
        0 0 0 1 0 0 0 0 0 0 0 0 1 1]
        F1-score:  0.7457627118644068
    

Lepsze zrozumienie dzięki macierzy pomyłek

Chociaż możesz uzyskać raport wyników terminy poprzez wydrukowanie powyższych elementów, możesz lepiej zrozumieć swój model, używając macierzy pomyłek, aby pomóc nam zrozumieć, jak model działa.

🎓 'Macierz pomyłek' (lub 'macierz błędów') to tabela, która wyraża prawdziwe vs. fałszywe pozytywy i negatywy twojego modelu, oceniając w ten sposób dokładność przewidywań.

  1. Aby użyć macierzy pomyłek, wywołaj confusion_matrix():

    from sklearn.metrics import confusion_matrix
    confusion_matrix(y_test, predictions)
    

    Spójrz na macierz pomyłek swojego modelu:

    array([[162,   4],
           [ 11,  22]])
    

W Scikit-learn macierze pomyłek: wiersze (oś 0) to rzeczywiste etykiety, a kolumny (oś 1) to przewidywane etykiety.

0 1
0 TN FP
1 FN TP

Co tu się dzieje? Załóżmy, że nasz model ma za zadanie klasyfikować dynie między dwoma binarnymi kategoriami, kategorią 'biała' i kategorią 'nie biała'.

  • Jeśli twój model przewiduje dynię jako nie białą, a w rzeczywistości należy ona do kategorii 'nie biała', nazywamy to prawdziwym negatywem, pokazanym przez liczbę w lewym górnym rogu.
  • Jeśli twój model przewiduje dynię jako białą, a w rzeczywistości należy ona do kategorii 'nie biała', nazywamy to fałszywym negatywem, pokazanym przez liczbę w lewym dolnym rogu.
  • Jeśli twój model przewiduje dynię jako nie białą, a w rzeczywistości należy ona do kategorii 'biała', nazywamy to fałszywym pozytywem, pokazanym przez liczbę w prawym górnym rogu.
  • Jeśli twój model przewiduje dynię jako białą, a w rzeczywistości należy ona do kategorii 'biała', nazywamy to prawdziwym pozytywem, pokazanym przez liczbę w prawym dolnym rogu.

Jak się domyślasz, preferowane jest posiadanie większej liczby prawdziwych pozytywów i prawdziwych negatywów oraz mniejszej liczby fałszywych pozytywów i fałszywych negatywów, co oznacza, że model działa lepiej. Jak macierz pomyłek odnosi się do precyzji i czułości? Pamiętaj, że raport klasyfikacji wydrukowany powyżej pokazał precyzję (0,85) i czułość (0,67).

Precyzja = tp / (tp + fp) = 22 / (22 + 4) = 0,8461538461538461

Czułość = tp / (tp + fn) = 22 / (22 + 11) = 0,6666666666666666

P: Jak według macierzy pomyłek poradził sobie model? O: Nieźle; jest sporo prawdziwych negatywów, ale także kilka fałszywych negatywów.

Przyjrzyjmy się jeszcze raz terminom, które poznaliśmy wcześniej, korzystając z mapowania TP/TN i FP/FN w macierzy pomyłek:

🎓 Precyzja: TP/(TP + FP) Ułamek istotnych przypadków wśród odzyskanych przypadków (np. które etykiety zostały dobrze oznaczone).

🎓 Czułość: TP/(TP + FN) Ułamek istotnych przypadków, które zostały odzyskane, niezależnie od tego, czy były dobrze oznaczone, czy nie.

🎓 f1-score: (2 * precyzja * czułość)/(precyzja + czułość) Średnia ważona precyzji i czułości, gdzie najlepszy wynik to 1, a najgorszy to 0.

🎓 Support: Liczba wystąpień każdej odzyskanej etykiety.

🎓 Dokładność: (TP + TN)/(TP + TN + FP + FN) Procent etykiet poprawnie przewidzianych dla próbki.

🎓 Średnia makro: Obliczenie nieważonej średniej metryk dla każdej etykiety, bez uwzględniania nierównowagi etykiet.

🎓 Średnia ważona: Obliczenie średniej metryk dla każdej etykiety, uwzględniające nierównowagę etykiet poprzez ważenie ich wsparciem (liczbą prawdziwych przypadków dla każdej etykiety).

Czy możesz wskazać, którą metrykę należy obserwować, jeśli chcesz, aby Twój model zmniejszył liczbę fałszywych negatywów?

Wizualizacja krzywej ROC dla tego modelu

ML dla początkujących - Analiza wydajności regresji logistycznej za pomocą krzywych ROC

🎥 Kliknij obrazek powyżej, aby obejrzeć krótki film o krzywych ROC.

Zróbmy jeszcze jedną wizualizację, aby zobaczyć tzw. krzywą 'ROC':

from sklearn.metrics import roc_curve, roc_auc_score
import matplotlib
import matplotlib.pyplot as plt
%matplotlib inline

y_scores = model.predict_proba(X_test)
fpr, tpr, thresholds = roc_curve(y_test, y_scores[:,1])

fig = plt.figure(figsize=(6, 6))
plt.plot([0, 1], [0, 1], 'k--')
plt.plot(fpr, tpr)
plt.xlabel('False Positive Rate')
plt.ylabel('True Positive Rate')
plt.title('ROC Curve')
plt.show()

Korzystając z Matplotlib, narysuj Receiving Operating Characteristic lub ROC modelu. Krzywe ROC są często używane, aby zobaczyć wyniki klasyfikatora w kontekście prawdziwych vs. fałszywych pozytywów. "Krzywe ROC zazwyczaj przedstawiają wskaźnik prawdziwych pozytywów na osi Y i wskaźnik fałszywych pozytywów na osi X." Dlatego stromość krzywej i przestrzeń między linią środkową a krzywą mają znaczenie: chcesz, aby krzywa szybko wznosiła się i oddalała od linii. W naszym przypadku na początku występują fałszywe pozytywy, a następnie linia wznosi się i oddala prawidłowo:

ROC

Na koniec użyj API roc_auc_score z biblioteki Scikit-learn, aby obliczyć rzeczywisty 'Obszar pod krzywą' (AUC):

auc = roc_auc_score(y_test,y_scores[:,1])
print(auc)

Wynik to 0.9749908725812341. Biorąc pod uwagę, że AUC mieści się w zakresie od 0 do 1, chcesz uzyskać wysoki wynik, ponieważ model, który jest w 100% poprawny w swoich przewidywaniach, będzie miał AUC równy 1; w tym przypadku model jest całkiem dobry.

W przyszłych lekcjach dotyczących klasyfikacji dowiesz się, jak iteracyjnie poprawiać wyniki swojego modelu. Ale na razie gratulacje! Ukończyłeś te lekcje dotyczące regresji!


🚀Wyzwanie

Regresja logistyczna kryje w sobie jeszcze wiele do odkrycia! Ale najlepszym sposobem na naukę jest eksperymentowanie. Znajdź zbiór danych, który nadaje się do tego typu analizy, i zbuduj na nim model. Czego się nauczysz? Wskazówka: sprawdź Kaggle w poszukiwaniu interesujących zbiorów danych.

Quiz po wykładzie

Przegląd i samodzielna nauka

Przeczytaj pierwsze kilka stron tego artykułu ze Stanfordu na temat praktycznych zastosowań regresji logistycznej. Zastanów się nad zadaniami, które lepiej nadają się do jednego lub drugiego typu zadań regresji, które studiowaliśmy do tej pory. Co sprawdziłoby się najlepiej?

Zadanie

Powtórka z tej regresji


Zastrzeżenie:
Ten dokument został przetłumaczony za pomocą usługi tłumaczenia AI Co-op Translator. Chociaż dokładamy wszelkich starań, aby zapewnić poprawność tłumaczenia, prosimy pamiętać, że automatyczne tłumaczenia mogą zawierać błędy lub nieścisłości. Oryginalny dokument w jego rodzimym języku powinien być uznawany za wiarygodne źródło. W przypadku informacji o kluczowym znaczeniu zaleca się skorzystanie z profesjonalnego tłumaczenia przez człowieka. Nie ponosimy odpowiedzialności za jakiekolwiek nieporozumienia lub błędne interpretacje wynikające z użycia tego tłumaczenia.