전공 과목 이수2👨‍💻/딥러닝

[혼공머] 3강.마켓과 머신러닝 / knn

천숭이 2022. 1. 18. 22:44
도미,  빙어 분류 문제

sklearn

k-최근점 이웃 알고리즘

 



# 도미 데이터(길이와 무게) 준비하기

bream_length = [25.4, 26.3, 26.5, 29.0, 29.0, 29.7, 29.7, 30.0, 30.0, 30.7, 31.0, 31.0, 31.5, 32.0, 32.0, 32.0, 33.0, 33.0, 33.5, 33.5, 34.0, 34.0, 34.5, 35.0, 35.0, 35.0, 35.0, 36.0, 36.0, 37.0, 38.5, 38.5, 39.5, 41.0, 41.0]
bream_weight = [242.0, 290.0, 340.0, 363.0, 430.0, 450.0, 500.0, 390.0, 450.0, 500.0, 475.0, 500.0, 500.0, 340.0, 600.0, 600.0, 700.0, 700.0, 610.0, 650.0, 575.0, 685.0, 620.0, 680.0, 700.0, 725.0, 720.0, 714.0, 850.0, 1000.0, 920.0, 955.0, 925.0, 975.0, 950.0]
print(len(bream_weight))  # 도미데이터 35개

 

# 산점도 (scatter plot)으로 도미데이터 살펴보기

import matplotlib.pyplot as plt
plt.scatter(bream_length, bream_weight)
plt.xlabel('length')
plt.ylabel('weight')
plt.show()

각 점이 도미 데이터

 

# 빙어 데이터(길이와 무게) 준비하기

smelt_length = [9.8, 10.5, 10.6, 11.0, 11.2, 11.3, 11.8, 11.8, 12.0, 12.2, 12.4, 13.0, 14.3, 15.0]
smelt_weight = [6.7, 7.5, 7.0, 9.7, 9.8, 8.7, 10.0, 9.9, 9.8, 12.2, 13.4, 12.2, 19.7, 19.9]
print(len(smelt_weight))  # 빙어 데이터 14개

 

# 도미와 빙어 데이터 모두 살펴보기

# scatter 메소드에 두 개의 데이터를 넣으면 색깔이 자동 지정되며 그래프 출력
plt.scatter(bream_length, bream_weight)  # 도미 (파랑색)
plt.scatter(smelt_length, smelt_weight)  # 빙어 (주황색)
plt.xlabel('length')
plt.ylabel('weight')
plt.show()

도미(파랑색), 빙어(주황색)

- 산점도를 보고 알 수 있는점 :

1. 빙어는 도미보다 크기와 무게가 작다

2. 빙어는 길이가 길어진다해도 무게가 크게 증가하지 않는다

3. 도미는 길이와 무게가 비례하다고 할 정도로 같이 커진다

4. 도미는 빙어보다 무겁고 무게가 많이 나간다

 


 

# 두 개의 length 데이터를 하나로 합친다

length = bream_length+smelt_length
weight = bream_weight+smelt_weight

 방어x 빙어o

fish_data = [[l, w] for l, w in zip(length, weight)]
# [[25.4, 242.0], [26.3, 290.0], [26.5, 340.0], [29.0, 363.0], [29.0, 430.0], [29.7, 450.0], [29.7, 500.0], .....

- 49개의 데이터를 가지고 있는 2차원 배열 fish_data가 생성됨

 

# label 생성

fish_target = [1]*35 + [0]*14

**    = 도미데이터        = 빙어 데이터  **


# knn(k-최근점이웃) 알고리즘 불러오기

from sklearn.neighbors import KNeighborsClassifier
kn = KNeighborsClassifier()

- 생성된 모델이 변수 kn. 앞으로 이 변수를 이용해 학습

 

# 위에서 만들어준 입력데이터와 정답데이터를 입력으로 학습 진행

kn.fit(fish_data, fish_target)

 

# score : 학습된 모델을 평가

- ret 정확도[0,1]

kn.score(fish_data, fish_target)
# 결과값이 1 => 모두 맞혔다

 

# 입력 데이터에 대해 class를 추정

# predecit 2차원 배열을 입력으로
# 주변의 데이터들과의 거리를 근거로 입력데이터를 예측
kn.predict([[30, 600]])   # [1] 도미
kn.predict([fish_data[-1]])   # [0] 빙어

 

# 학습에 쓰인 입력데이터 출력라벨 쉽게 가져오기

kn._fit_X # 입력 데이터

kn._y # 정답 데이터

입력 데이터 :

array([[ 25.4, 242. ], [ 26.3, 290. ], [ 26.5, 340. ], [ 29. , 363. ], [ 29. , 430. ], [ 29.7, 450. ], [ 29.7, 500. ], ......

 

정답데이터:

array([1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0])

 

# k 변경하기

- 예측하고자 하는 데이터의 주변 몇 개의 데이터를 볼 것인지 정할 수 있음 (k의 역할)

# 옵션값을 주고 새로운 모델 생성
kn49 = KNeighborsClassifier(n_neighbors=49)

 


K-최근접 이웃 알고리즘

- 지도학습

- 비지도학습인 클러스터링과 유사한 방식

- 데이터들 간의 거리를 참고해 분류작업

- '유클리디안 거리' 계산법 적용

- k의 수만큼의 주변 데이터를 관찰하기 때문에 홀수여야 한다

 

# knn 적용 시 주의사항

- 학습 전 입력데이터들을 정규화시키자

이 때, 대표적인두가지 변수 재조정 방법이 있다.

최소-최대 정규화 z-점수 표준화 (
변수의 범위를 0% ~ 100%로 조정

변수의 범위를 평균에서 떨어져 있는 정도를 이용해 확대 혹은 축소



- 최소값과 최대값이 [0,100] 범위에 없을 수도 있음
- 수의 범위를 정확히 파악한 후에 사용하기
- 수의 범위 정확하게 파악하지 않아도 됨

 

# knn 장/단점

- 수치 데이터 해석단계에서 시간을 많이 투자해야 한다.

출처:https://m.blog.naver.com/bestinall/221760380344

- 데이터가 많아지면 유클리디안 거리 연산하는 시간도 비례적으로 늘어나기에 분류 속도가 느리다