johhny.b
johhny.b

Reputation: 33

Perceptron does not learn correct

i write 3 class classification for iris dataset(there are 3 classes) and i use 3 perceptrons. I have problem with perceptron learning, perceptron learn correct only for first class, second and third class have the same weights and i dont know what i make wrong. Always perceptron for first class learn correct and classifies correct. First perceptron have target 0, second 1 and third 2. When i swap places and the first one learns, the perceptron with target 2 will work fine, the first one always works fine and the next two work badly. There is something wrong with setting the data to train.

PS. This is my first python application.

import matplotlib.pyplot as plt
import numpy as np
from sklearn.model_selection import train_test_split
from sklearn import datasets

class Perceptron(object):

def __init__(self, eta=0.01, n_iter=10):
    self.eta = eta
    self.n_iter = n_iter

def fit(self, X, y):
    self.w_ = np.zeros(1+ X.shape[1])
    self.errors_ = []

    for _ in range(self.n_iter):
        errors = 0
        for xi, target in zip(X,y):
            update = self.eta * (target - self.predict(xi))
            self.w_[1:] += update *xi
            self.w_[0] += update
            errors += int(update != 0.0)
        self.errors_.append(errors)
    print(self.w_)
    return self

def net_input(self, X):
    return np.dot(X, self.w_[1:]) + self.w_[0]

def predict(self, X):
    return np.where(self.net_input(X) >= 0.0, 1, -1)

def main():
iris = datasets.load_iris()
X = iris.data[:, [2, 3]]
y = iris.target

X_train, X_test, y_train, y_test = train_test_split(X, y, test_size=0.3, random_state=1, stratify=y)

X_train_01_subset = X_train
y_train_01_subset = y_train


y_train_01_subset[(y_train_01_subset == 0)] = -1
y_train_01_subset[(y_train_01_subset == 1)] = -1
y_train_01_subset[(y_train_01_subset == 2)] = 0

ppn01 = Perceptron(eta=0.1, n_iter=10)
ppn01.fit(X_train_01_subset, y_train_01_subset)

X_train_02_subset = X_train
y_train_02_subset = y_train

y_train_02_subset[(y_train_02_subset == 1)] = 1
y_train_02_subset[(y_train_02_subset == 0)] = -1
y_train_02_subset[(y_train_02_subset == 2)] = -1

ppn02 = Perceptron(eta=0.1, n_iter=10)
ppn02.fit(X_train_02_subset, y_train_02_subset)


X_train_03_subset = X_train
y_train_03_subset = y_train

y_train_03_subset[(y_train_03_subset == 1)] = -1
y_train_03_subset[(y_train_03_subset == 0)] = 2
y_train_03_subset[(y_train_03_subset == 2)] = -1

ppn03 = Perceptron(eta=0.1, n_iter=10)  
ppn03.fit(X_train_03_subset, y_train_03_subset)

Upvotes: 0

Views: 132

Answers (1)

jhso
jhso

Reputation: 3283

Two things I noted in your code:

  1. When you assign numpy arrays to a new variable, they are treated as the same variable, ie. changes to the new variable will affect the initial. That means your code will change y_train when you change your y_train_01_subset, y_train_02_subset, and y_train_03_subset values. This means that your code will only work for your first subset because y_train will be all -1's when you reach the second set. Use .copy() to get around this.
  2. In your y_train_03_subset, you set your values equal to 0 to be 2, and then set values equal to 2 equal to -1, so all of your values will be -1. Rearrange these lines.

To get around these, substitute in the following code:

X_train_01_subset = X_train.copy()
y_train_01_subset = y_train.copy()


y_train_01_subset[(y_train_01_subset == 0)] = -1
y_train_01_subset[(y_train_01_subset == 1)] = -1
y_train_01_subset[(y_train_01_subset == 2)] = 0

ppn01 = Perceptron(eta=0.1, n_iter=10)
ppn01.fit(X_train_01_subset, y_train_01_subset)

X_train_02_subset = X_train.copy()
y_train_02_subset = y_train.copy()

y_train_02_subset[(y_train_02_subset == 1)] = 1
y_train_02_subset[(y_train_02_subset == 0)] = -1
y_train_02_subset[(y_train_02_subset == 2)] = -1

ppn02 = Perceptron(eta=0.1, n_iter=10)
ppn02.fit(X_train_02_subset, y_train_02_subset)


X_train_03_subset = X_train.copy()
y_train_03_subset = y_train.copy()

y_train_03_subset[(y_train_03_subset == 1)] = -1
y_train_03_subset[(y_train_03_subset == 2)] = -1
y_train_03_subset[(y_train_03_subset == 0)] = 2

ppn03 = Perceptron(eta=0.1, n_iter=10)  
ppn03.fit(X_train_03_subset, y_train_03_subset)

Upvotes: 1

Related Questions