Notice
Recent Posts
Recent Comments
«   2025/01   »
1 2 3 4
5 6 7 8 9 10 11
12 13 14 15 16 17 18
19 20 21 22 23 24 25
26 27 28 29 30 31
Archives
Today
Total
관리 메뉴

SYDev

Chapter 06-3: 주성분 분석 본문

KHUDA 4th/머신러닝 기초 세션

Chapter 06-3: 주성분 분석

시데브 2023. 8. 29. 02:39
차원 축소에 대해 이해하고
대표적인 차원 축소 알고리즘 중 하나인 PCA 모델을 만들어보자.

 

 

차원 축소

  • 차원 축소(Dimensionality Reduction): 저차원 표현이 고차원 원본 데이터의 의미 있는 특성을 이상적으로 원래의 차원에 가깝게 유지할 수 있도록 고차원 공간에서 저차원 공간으로  데이터를 변환하는 것을 의미한다.
  • 다시 말해서, 차원 축소를 하면 고차원에서 저차원으로 변환되는 과정에서 정보 손실(information loss)이 발생하는데, 이런 정보 손실을 최소화하면서 저차원으로 변환해야 한다.

 

차원 축소의 필요성

1. 차원의 저주

  • 머신러닝에서 차원이 증가할수록 데이터 공간의 부피가 기하급수적으로 증가하기 때문 데이터의 밀도가 낮아지고, 데이터 간의 거리가 증가한다. 이러한 데이터를 이용해 학습을 진행하게 되면 모델이 복잡해져 과대적합이 발생하기 쉽고, 모델의 예측 신뢰도가 떨어진다.

출처: https://jermwatt.github.io/

 

  • 차원이 일정 크기를 넘으면 성능은 점점 떨어져 0에 수렴한다.

 

출처: https://blog.mathpresso.com/mathpresso-%EB%A8%B8%EC%8B%A0-%EB%9F%AC%EB%8B%9D-%EC%8A%A4%ED%84%B0%EB%94%94-15-%EC%B0%A8%EC%9B%90-%EC%B6%95%EC%86%8C-dimensionality-reduction-76b13460506f

2. 시각화를 통한 데이터 분석

  • 탐색형 데이터 분석을 할 때에, 변수 간 관계를 파악하기 위해서 데이터의 산점도를 시각화해서 보면 좋은데, feature의 개수가 여러 개일 때는 데이터의 시각화가 어려워진다.
  • 차원축소를 통해서 고차원의 데이터를 쉽게 시각화하여 데이터를 분석할 수 있다.

 

3. 데이터 처리, 분석 시에 연산 속도 향상 

4. 데이터를 압축하여 데이터의 저장, 전송 효율 향상

 

 

차원 축소의 종류

  • 특성 선택(Feature Selection): 가지고 있는 특성 중에서 훈련에 가장 유용한 특성을 선택하는 것으로, 원본 데이터에서 가장 좋은 성능을 보여줄 수 있는 데이터의 부분집합(subset)을 찾아내는 방법이다.
  • 특성 추출(Feature Extraction): 기존 feature를 저차원 feature로 압축시키는 방법으로, 이렇게 압축된 feature는 기존과는 다른 새로운 값이 된다.

 

 예를 들어 야외 활동이 좋은지 알아내기 위해 다음과 같이 101개의 야외활동과 관련된 feature가 있다고 치자. 

  온도 습도 강수량 미세먼지 풍속 태풍여부 ... 교통량 유동인구
0801 32 15 66 3 111 0   15 40326127
0802                  
...                  
0831                  

 

 위 특성들 중 습도와 강수량, 풍속과 태풍여부는 밀접한 연관성이 있다. 이처럼 밀접한 연관성이 있는 특성들을 묶어주는 것이 특성 추출의 과정이다. 

  온도 습도 강수량 미세먼지 풍속 태풍여부 ... 교통량 유동인구
0801 32 15 66 3 111 0   15 40326127
0802           0      
...                  
0831                  

 

 그러나, 위와 같이 직관적으로 연관성을 확인할 수 없는 데이터의 경우에는 임의로 특성을 묶기 힘들어지는데, 이때 활용할 수 있는 방법 중 하나가 주성분 분석(Principle Component Analysis)이다. 

 

 

주성분 분석

  • 주성분 분석(Principle Component Analysis): 데이터를 축에 사영했을 때, 가장 높은 분산을 가지는 데이터의 축을 찾아 그 축으로 차원을 축소하는 방식이다.
  • 높은 분산을 가지는 축을 찾는 이유는, 분산이 커져야 데이터들 간 차이가 명확해지고, 이로 인해서 모델을 더 좋은 방향으로 학습시킬 수 있기 때문이다.

 

 다음 이미지를 봤을 때, 직관적으로 봐도 좌측 축이 원래 데이터를 더 잘 표현한다고 할 수 있다.

 

 

출처: https://www.youtube.com/watch?v=FhQm2Tc8Kic&list=PLpIPLT0Pf7IoTxTCi2MEQ94MZnHaxrP0j&index=11

 

 

PCA의 차원 축소 절차는 다음과 같다.

 

  1. 데이터를 사영시켰을 때, 가장 분산이 큰 축(주성분)을 찾는다.
  2. 1번에서 찾은 축에 직교하며, 다음으로 분산이 큰 축(다음 주성분)을 찾는다.
  3. 위 과정을 반복하여 k개의 축을 찾아냈을 때, 원래의 고차원 데이터를 k차원 데이터로 다시 나타낼 수 있다.

 

출처 : https://blog.bioturing.com/2018/06/14/principal-component-analysis-explained-simply/

 

주성분 분석의 수식적 이해

 

  • 대칭 행렬의 고유 벡터는 직교한다!

 

설명된 분산

  • 설명된 분산(explained variance): 주성분이 원본 데이터의 분산을 얼마나 잘 나타내는지 기록한 값을 의미한다.
  • 설명된 분산의 비율을 모두 더하면 총 분산 비율을 얻을 수 있다.

 

PCA를 이용한 데이터의 차원 축소

#데이터 준비
!wget https://bit.ly/fruits_300_data -O fruits_300.npy
import numpy as np
fruits = np.load('fruits_300.npy')
fruits_2d = fruits.reshape(-1, 100*100)
 
#PCA를 이용한 차원 축소
from sklearn.decomposition import PCA
pca = PCA(n_components=50) #주성분 50개
pca.fit(fruits_2d)
print(pca.components_.shape)
(50, 10000)
  • 각 50개의 주성분에 투영된 10000개의 픽셀을 의미!

 

import matplotlib.pyplot as plt
def draw_fruits(arr, ratio=1):
  n = len(arr)
  rows = int(np.ceil(n/10))
  cols = n if rows<2 else 10
  fig, axs = plt.subplots(rows, cols,
                          figsize=(cols*ratio, rows*ratio), squeeze=False)
  for i in range(rows):
    for j in range(cols):
      if i*10 + j < n:
        axs[i, j].imshow(arr[i*10 + j], cmap='gray_r')
      axs[i, j].axis('off')
  plt.show()

draw_fruits(pca.components_.reshape(-1, 100, 100))

분산이 큰 순서대로 나열

 

#원본 데이터셋과 차원 축소된 데이터셋의 비교
print(fruits_2d.shape)

fruits_pca = pca.transform(fruits_2d)
print(fruits_pca.shape)
(300, 10000)
(300, 50)

 

#분산이 큰 방향으로 데이터를 투영했기 때문에 원본 데이터를 상당 부분 재구성할 수 있음
fruits_inverse = pca.inverse_transform(fruits_pca)
print(fruits_inverse.shape)
 
fruits_reconstruct = fruits.reshape(-1, 100, 100)
for start in [0, 100, 200]:
  draw_fruits(fruits_reconstruct[start:start+100])
  print("\n")
(300, 10000)

 

#설명된 분산 비율의 합
print(np.sum(pca.explained_variance_ratio_))
0.9215768225179868

 

#설명된 분산을 이용해 적절한 주성분의 개수를 탐색
plt.plot(pca.explained_variance_ratio_)
plt.show()

>> 처음 10개의 주성분이 대부분의 분산을 표현

 

 

다른 알고리즘과 함께 사용

로지스틱 회귀

#지도 학습 알고리즘인 로지스틱 회귀 모델 사용
from sklearn.linear_model import LogisticRegression

lr = LogisticRegression()
 
target = np.array([0]*100 + [1]*100 + [2]*100)
 
#교차 검증 수행
from sklearn.model_selection import cross_validate
scores = cross_validate(lr, fruits_2d, target)
print(np.mean(scores['test_score']))
print(np.mean(scores['fit_time']))
0.9966666666666667
2.0395181655883787
  • 특성(픽셀)이 10000개나 되기 때문에 300개의 샘플에서는 과대적합된 모델을 만들기 쉬움
  • 교차 검증 폴드의 훈련 시간 대략 2.04초

 

#PCA로 차원 축소한 데이터로 훈련
scores = cross_validate(lr, fruits_pca, target)
print(np.mean(scores['test_score']))
print(np.mean(scores['fit_time']))
1.0
0.03729820251464844
  • 50개의 특성만 사용했는데도 정확도가 100%
  • 훈련 시간은 0.04초로 대략 50배 이상 빨라짐

 

pca = PCA(n_components=0.5) #설명된 분산의 50%에 달하는 주성분을 탐색 
pca.fit(fruits_2d)
 
print(pca.n_components_)
2

>> 2개의 특성만으로 원본 데이터에 있는 분산의 50% 표현 가능

 

#주성분 2개로 원본 데이터 변환
fruits_pca = pca.transform(fruits_2d)
print(fruits_pca.shape)
 
scores = cross_validate(lr, fruits_pca, target)
print(np.mean(scores['test_score']))
print(np.mean(scores['fit_time']))
(300, 2)
0.9933333333333334
0.04042010307312012

 

k-평균 알고리즘

#PCA로 축소된 데이터로 KMeans 알고리즘 학습
from sklearn.cluster import KMeans
km = KMeans(n_clusters=3, random_state=42)
km.fit(fruits_pca)
print(np.unique(km.labels_, return_counts=True))
 
for label in range(0, 3):
  draw_fruits(fruits[km.labels_ == label])
  print("\n")
(array([0, 1, 2], dtype=int32), array([110,  99,  91]))

 

 

#차원 축소로 인한 시각화의 장점!!
for label in range(0, 3):
  data = fruits_pca[km.labels_ == label]
  plt.scatter(data[:,0], data[:,1])
plt.legend(['apple', 'banana', 'pineapple'])
plt.show()

 


참고자료

  • 박해선, <혼자 공부하는 머신러닝+딥러닝>, 한빛미디어(주), 2022.2.4
 

차원 축소 - PCA, 주성분분석 (1)

차원 축소 - PCA (1)대부분 실무에서 분석하는 데이터는 매우 많은 특성(feature)들을 가지고 있다. 이러한 데이터를 가지고 머신러닝 알고리즘을 적용해 문제를 해결하려고 한다면, 데이터의 차원

excelsior-cjh.tistory.com

 

차원 축소 (Dimension Reduction) - PCA, LDA

*해당 포스팅은 파이썬 머신러닝 완벽 가이드(권철민 지음) 교재를 공부하며 작성한 글입니다. 안녕하세요! 오늘은 차원 축소 알고리즘 중 PCA 와 LDA에 대해 알아보겠습니다. 1. 차원 축소란? 2. PCA

casa-de-feel.tistory.com

 

QANDA 머신 러닝 스터디

15. 차원 축소(Dimensionality Reduction)

blog.mathpresso.com

 

차원 축소 (Dimensionality Reduction)

이번 포스팅에서는 정답 레이블 Y는 없고 오직 설명변수 X 만을 사용해서 데이터 내 관계, 패턴, 구조를 탐색하는데 사용하는 비지도학습 중에서 차원 축소 (Dimensionality Reduction) 에 대한 이론적인

rfriend.tistory.com

 

차원 축소 (Dimension Reduction) - PCA, LDA

*해당 포스팅은 파이썬 머신러닝 완벽 가이드(권철민 지음) 교재를 공부하며 작성한 글입니다. 안녕하세요! 오늘은 차원 축소 알고리즘 중 PCA 와 LDA에 대해 알아보겠습니다. 1. 차원 축소란? 2. PCA

casa-de-feel.tistory.com

  • https://huidea.tistory.com/44?category=879541
  • https://m.blog.naver.com/PostView.naver?blogId=euleekwon&logNo=221464171572&referrerCode=0&searchKeyword=feature%20extraction
  • https://velog.io/@swan9405/PCA
 

머신러닝 - PCA (Principal Component Analysis)

1. PCA(Principal Component Analysis) - 주성분 분석이란? 주성분이란 전체 데이터(독립변수들)의 분산을 가장 잘 설명하는 성분을 말한다. 변수의 개수 = 차원의 개수 e.g.) iris 데이터에서, 4개의 독립변인

velog.io

  • https://www.youtube.com/watch?v=5TLPtscN3Tg&list=PLSB4-69yY3od7cw1naXNgUsbdph6A3Aw7&index=19