머신러닝

Iris flowers data 사용 K 근접이웃 머신 러닝: K-nearest neighbors:KNN

coding art 2019. 4. 21. 20:25
728x90


파이선 코딩을 배우는 초보자도 머신 러닝에 독학으로 한번 도전해 보자.

그다지 어렵지 않으니까요!

머신 러닝을 배우려는 파이선 코딩 초보자들이 가지게 될 확률이 높은 의문점들을

하나하나 찾아내어 실제 풀어보고 결과를 확인해볼 수 있는 머신 러닝!

인터넷 교보문고에서 450페이지19900원에 판매중입니다.











________________________________________________________________________________________________________________________

K-nearest neighbors KNN classification 머신러닝 기법에 관해서 알아보자. 이 기법은 지금까지 우리가 알고 있는 학습기법과는 완전히 다르기 때문에 대단히 흥미로울 수도 있다. 과연 인간의 학습 지능과 어떤 유사성이 있을지 알아보기로 하자.

 

KNN은 즉 학습은 거의 하지 않으면서 목표를 달성하는 아주 게으른 학습자세를 가진 전형적인 사례이다. KNN은 학습 데이터로부터 뭔가를 판단할 수 있는 근거를 학습하지 않으며 단지 그 대신에 학습 데이터 전체를 기억해버리게 된다.

 

KNN 알고리듬은 별달리 설명할 필요도 없을 정도로 아주 단순하여 아래와 같이 간단히 기술할 수 있다.

K 의 숫자 값과 거리 계산법을 선택한다.

사용자가 분류해 보고자 하는 샘플 데이터와 가장 근접한 K개의 이웃 데이터를 찾는다.

다수결 원칙에 의해서 class 라벨 값을 부여한다.

 

다음의 예를 살펴보자. 3종류의 데이터가 섞여 있으며 한 곳에서 종류별 데이터들이 근접해서 위치하고 있다. 현재 K 값이 5인 상태에서 ?에 들어갈 데이터의 종류는 무엇인가? K-nearest neighbors 기법에 의해 결정하여라.

  


선택 지점으로부터 거리 측정 방식이 설정되어 있다면 분류(classification)하고 싶은 지점으로부터 가장 근접한 법위 내에 위치한 K(-5)개의 학습 데이터 샘플들을 찾아낼 수 있다. 학습이 필요한 새 데이터에 부여하고 싶은 class 라벨 값은 다수결 원칙에 따라서 삼각형()임을 알 수 있다.

 

KNN 은 학습하여 웨이트 값을 결정한 후 테스트에 이용하는 머신 러닝과는 달리 학습 데이터를 죄다 기억해서 저장하고 있어야 한다. 유달리 특징 데이터가 큰 샘플들을 대상으로 할 경우에 머신 러닝 기법들 중에 상대적으로 메모리 용량 부담이 클 수 있다.

 

scikit-learn 라이브러리와 유클리드 기하학에서의 거리 개념을 사용하여 Iris flowers 데이터 세트에 대한 KNN 모델 코드를 실행해 보자.

다음 KNeighborsClassifier 의 파라메터 사용법 설명이다. 유클리디안 거리 개념 사용을 위해서 p=2 metric=’minkowski’ 가 사용된다.


 계산 후 그래픽 처리 결과를 관찰해 보면 전체적으로 classification boundary 는 여타의 SVM 이나 퍼셉트론 기법과 유사하다고 할 수 있겠으나 데이터들이 섞인 영역에서 Overfitting 현상이 관찰된다.



#ch03_knn_01


from sklearn import __version__ as sklearn_version
import numpy as np
import matplotlib.pyplot as plt


from sklearn import datasets
iris = datasets.load_iris()
X = iris.data[:, [2, 3]]
y = iris.target

print('Class labels:', np.unique(y))

from sklearn.model_selection import train_test_split
X_train, X_test, y_train, y_test = train_test_split(
    X, y, test_size=0.3, random_state=1, stratify=y)

print('Labels counts in y:', np.bincount(y))
print('Labels counts in y_train:', np.bincount(y_train))
print('Labels counts in y_test:', np.bincount(y_test))


from sklearn.preprocessing import StandardScaler
sc = StandardScaler()
sc.fit(X_train)
X_train_std = sc.transform(X_train)
X_test_std = sc.transform(X_test)

from matplotlib.colors import ListedColormap
def plot_decision_regions(X, y, classifier, test_idx=None, resolution=0.02):

    # setup marker generator and color map
    markers = ('s', 'x', 'o', '^', 'v')
    colors = ('red', 'blue', 'lightgreen', 'gray', 'cyan')
    cmap = ListedColormap(colors[:len(np.unique(y))])

    # plot the decision surface
    x1_min, x1_max = X[:, 0].min() - 1, X[:, 0].max() + 1
    x2_min, x2_max = X[:, 1].min() - 1, X[:, 1].max() + 1
    xx1, xx2 = np.meshgrid(np.arange(x1_min, x1_max, resolution),
                           np.arange(x2_min, x2_max, resolution))
    Z = classifier.predict(np.array([xx1.ravel(), xx2.ravel()]).T)
    Z = Z.reshape(xx1.shape)
    plt.contourf(xx1, xx2, Z, alpha=0.3, cmap=cmap)
    plt.xlim(xx1.min(), xx1.max())
    plt.ylim(xx2.min(), xx2.max())

    for idx, cl in enumerate(np.unique(y)):
        plt.scatter(x=X[y == cl, 0],
                    y=X[y == cl, 1],
                    alpha=0.8,
                    c=colors[idx],
                    marker=markers[idx],
                    label=cl,
                    edgecolor='black')

    #highlight test samples
    if test_idx:
        #plot all samples
        X_test, y_test = X[test_idx, :], y[test_idx]

        plt.scatter(X_test[:, 0],
                    X_test[:, 1],
                    c='',
                    edgecolor='black',
                    alpha=1.0,
                    linewidth=1,
                    marker='o',
                    s=100,
                    label='test set')


#K-nearest neighbors - a lazy learning algorithm
from sklearn.neighbors import KNeighborsClassifier
knn = KNeighborsClassifier(n_neighbors=5, p=2, metric='minkowski')
knn.fit(X_train_std, y_train)
plot_decision_regions(X_combined_std, y_combined,
                      classifier=knn, test_idx=range(105, 150))

plt.xlabel('petal length [standardized]')
plt.ylabel('petal width [standardized]')
plt.legend(loc='upper left')
plt.tight_layout()
plt.show()