ABOUT ME

-

Today
-
Yesterday
-
Total
-
  • PCA(Principal Component Analysis)란 무엇인가? (파이썬으로 PCA 구현하기 실습 포함)
    데이터/처리 및 분석 2024. 10. 15. 10:24

     

     

     

     

     

     

     

     

     

    PCA(Principal Component Analysis)란 무엇인가?

    PCA(Principal Component Analysis)는 복잡한 고차원 데이터를 더 적은 차원으로 효율적으로 축소하면서도 핵심 정보를 유지할 수 있는 방법입니다. 고차원 데이터는 변수가 많기 때문에 처리하는 데 시간이 많이 걸리고 분석이 복잡할 수 있습니다. PCA는 이런 문제를 해결하기 위해, 데이터를 새로운 좌표계로 변환하여 중요한 패턴을 유지하면서도 차원을 줄입니다. 이 새로운 좌표계의 축들은 주성분(Principal Components)이라고 불리며, 데이터의 핵심 정보를 잘 설명할 수 있는 새로운 변수들입니다.

     

    PCA의 핵심 아이디어는 데이터의 분산(Variance), 즉 데이터가 얼마나 퍼져 있는지를 기준으로 중요한 축을 찾는 것입니다. 데이터를 여러 축(방향)으로 바라볼 때, 가장 많이 퍼져 있는 방향이 데이터를 설명하는 데 가장 중요한 축이 됩니다. 예를 들어, 타원형 모양으로 퍼진 데이터를 보면, 타원의 긴 축이 가장 중요한 정보가 담긴 축이라고 할 수 있죠.

     

    PCA는 데이터를 분산이 가장 큰 축(주성분)으로 변환하여 차원을 줄이더라도 중요한 정보를 최대한 유지하는 방법입니다. 즉, 데이터가 차원을 축소한 후에도 가장 중요한 정보는 여전히 남아 있는 것이죠.

    PCA 계산 과정

    PCA는 고차원 데이터를 더 낮은 차원으로 변환하면서도 본질적인 정보를 유지하기 위해 다음과 같은 과정을 거칩니다:

    1. 데이터 정규화

    PCA를 적용하기 전에 데이터는 반드시 정규화가 필요합니다. 정규화란 각 변수의 값들이 평균이 0, 표준편차가 1이 되도록 변환하는 작업입니다. 이를 통해 변수들 간의 단위 차이로 인한 왜곡을 방지하고, 주성분 분석 시 특정 변수가 결과에 과도하게 영향을 미치는 것을 막을 수 있습니다.

     

    정규화는 다음과 같은 수식으로 표현됩니다:

    $$ Z = \frac{X-\mu}{\sigma} $$

    여기서  \( X \) 는 원본 데이터,  \( \mu \)  는 각 변수의 평균,  \( \sigma \)  는 각 변수의 표준편차입니다. 이 과정을 통해 변수들은 동일한 스케일로 조정되며, PCA의 정확도를 높이게 됩니다.

    2. 공분산 행렬 계산

    정규화된 데이터에 대해 각 변수 간의 공분산 행렬을 계산합니다. 공분산 행렬은 변수가 어떻게 함께 변동하는지를 나타내며, 이를 통해 데이터의 내재된 패턴을 이해할 수 있습니다. 공분산 값이 크다는 것은 두 변수가 강하게 상관되어 있다는 의미입니다.

     

    공분산 행렬 \( Cov(X) \)  는 다음과 같이 계산됩니다:

    $$ Cov(X) = \frac{1}{n-1} X^TX $$

    여기서 \( X \) 는 정규화된 데이터 매트릭스이고, \( n \) 은 샘플의 개수입니다. 이 행렬은 PCA의 주성분을 구하는 기초가 되며, 차원축소의 방향성을 결정하는 데 중요한 역할을 합니다.

    3. 고유값 분해

    공분산 행렬에 대해 고유값 분해(Eigendecomposition)를 수행하여 고유값(Eigenvalues)과 고유벡터(Eigenvectors)를 구합니다. 고유벡터는 데이터가 가장 많이 분산된 방향을 나타내며, 각 고유벡터에 대응하는 고유값은 그 방향이 데이터의 분산을 얼마나 잘 설명하는지를 나타냅니다.

     

    고유값 분해는 다음과 같은 방정식으로 표현됩니다:

    $$ Cov(X)v = \Lambda v $$

    여기서 \( v \) 는 고유벡터(주성분)이고, \( \lambda \) 는 고유값입니다. 고유값이 클수록 해당 고유벡터가 데이터를 설명하는 데 중요한 역할을 하게 됩니다. 따라서, 가장 큰 고유값을 가진 고유벡터들이 PCA에서 주요 주성분으로 선택됩니다.

    4. 주성분 선택 및 데이터 변환

    모든 고유값과 고유벡터를 계산한 후, 가장 큰 고유값에 대응하는 고유벡터들을 선택합니다. 일반적으로 몇 개의 주성분만 선택하여 데이터를 차원 축소하는데, 이는 데이터의 대부분의 변동을 설명하는 주성분들만 남기기 위함입니다.

     

    주성분을 선택한 후, 원본 데이터를 변환 행렬을 통해 새로운 좌표계로 투영하게 됩니다. 이 변환은 다음과 같이 이루어집니다:

    $$ Z_{new} = X · W $$

    여기서  \( W \) 는 선택된 주성분들로 이루어진 행렬입니다. 차원이 축소된 데이터는 주성분 축에 투영된 결과로, 정보의 손실을 최소화하면서도 데이터의 중요한 특성을 유지하게 됩니다.

    Iris 데이터셋이란?

    Iris 데이터셋은 붓꽃의 주요 형태적 특징을 측정한 데이터를 바탕으로 구성된 150개의 샘플로 이루어져 있으며, 머신러닝과 통계 분석의 성능을 평가하거나 학습하는 데 자주 사용됩니다. 이 데이터셋은 세 가지 붓꽃 품종을 포함하고 있으며, 각각의 샘플은 네 가지 특징을 기반으로 수집되었습니다. 이 네 가지 특징은 각 붓꽃의 형태를 수치화하여 품종을 구분하는 데 중요한 역할을 합니다.

     

    Iris 데이터셋은 다음과 같은 네 가지 특징을 가지고 있습니다:

    1. 꽃받침 길이 (Sepal Length): 꽃받침은 꽃잎 아래에 위치해 꽃봉오리를 보호하는 부분입니다. 그 길이는 붓꽃의 크기를 측정하는 데 중요한 요소로 사용됩니다.
    2. 꽃받침 너비 (Sepal Width): 꽃받침의 폭은 꽃 전체의 균형과 모양을 파악하는 데 도움이 됩니다.
    3. 꽃잎 길이 (Petal Length): 꽃잎의 길이는 붓꽃 품종을 구분하는 데 매우 중요한 특징으로, 각 품종마다 꽃잎의 길이에 큰 차이가 있습니다.
    4. 꽃잎 너비 (Petal Width): 꽃잎의 폭 역시 품종 구분에 중요한 요소로, 꽃잎의 형태와 구조를 이해하는 데 필수적인 정보입니다.

    Iris 데이터셋에 포함된 붓꽃 품종은 세 가지로 분류됩니다: :

    1. Iris Setosa
    2. Iris Versicolor
    3. Iris Virginica

    이 데이터셋의 주된 목적은 각 샘플이 어떤 품종에 속하는지를 분석하는 것입니다. 그러나 4개의 특징을 모두 분석하는 것은 차원이 높아져 시각적으로 복잡해질 수 있으며, 직관적인 해석이 어려울 수 있습니다. 이러한 문제를 해결하기 위해 PCA(주성분 분석)가 사용됩니다.

    PCA의 역할

    PCA(주성분 분석)는 데이터를 단순화하는 데 매우 유용한 도구입니다. 데이터에 여러 가지 특징이 있을 때, 모든 정보를 한꺼번에 분석하기는 쉽지 않습니다. 특히, 차원이 높아질수록 데이터의 구조를 시각적으로 이해하기 어려워집니다. PCA는 데이터를 더 적은 차원으로 축소해 복잡한 데이터를 간소화하면서도 중요한 정보를 유지할 수 있게 해줍니다.

     

    Iris 데이터셋을 예로 들어보면, 이 데이터는 네 가지 특징(꽃받침 길이, 꽃받침 너비, 꽃잎 길이, 꽃잎 너비)을 사용해 붓꽃을 설명합니다. 하지만 네 개의 특징을 모두 시각화하려면 차원이 너무 높아서, 데이터를 한눈에 이해하기가 어렵습니다. PCA는 이 문제를 해결합니다. 네 개의 특징을 두 개의 주성분으로 변환해 붓꽃 품종 간의 차이를 2차원 평면에서 쉽게 볼 수 있게 만들어 주죠.

     

    이 과정을 통해 우리는 데이터를 시각적으로 분석할 수 있고, 붓꽃 품종 간의 차이가 명확하게 드러납니다. 이렇게 차원을 줄이면 복잡한 데이터를 단순화하면서도 중요한 패턴을 유지할 수 있습니다. PCA는 데이터가 많을 때, 그 핵심적인 부분만 남겨서 분석을 쉽게 만들어주는 도구라고 생각하면 됩니다.

    IRIS 데이터셋에 PCA 적용하기

    이번에는 Iris 데이터셋을 사용하여 PCA를 파이썬으로 구현한 후, 차원 축소 모델과 기존 모델의 성능을 비교해보겠습니다. Logistic Regression을 이용하여 PCA를 적용한 모델과 적용하지 않은 모델의 성능을 비교하며, 두 모델의 차이를 확인할 수 있습니다.

    1. 필요한 라이브러리 임포트

    먼저, PCA를 적용하고 모델 성능을 비교하기 위해 필요한 라이브러리들을 임포트합니다 .

    # 1. 필요한 라이브러리 임포트
    import numpy as np
    import pandas as pd
    from sklearn.preprocessing import StandardScaler
    from sklearn.decomposition import PCA
    from sklearn.model_selection import train_test_split
    from sklearn.linear_model import LogisticRegression
    from sklearn.metrics import accuracy_score
    from sklearn.datasets import load_iris

     

    이 라이브러리들의 역할은 다음과 같습니다:

    • NumPy와 Pandas: 데이터 생성 및 처리 도구.
    • scikit-learn:
      • StandardScaler: 데이터를 표준화(정규화)합니다.
      • PCA: 주성분 분석을 수행합니다.
      • train_test_split: 데이터를 훈련 세트와 테스트 세트로 분할합니다.
      • LogisticRegression: 분류 모델을 학습합니다.
      • accuracy_score: 모델 성능 평가 지표로 사용합니다.
    • load_iris: Iris 데이터셋을 불러옵니다..

    2. 데이터 로드 및 데이터프레임 구성

    Iris 데이터셋을 불러와 데이터프레임으로 구성합니다.

    # 2. Iris 데이터셋 로드 및 데이터프레임 구성
    iris = load_iris()
    df = pd.DataFrame(iris.data, columns=iris.feature_names)
    df['target'] = iris.target

     

    Iris 데이터셋: 꽃받침 길이와 너비, 꽃잎 길이와 너비의 4가지 특징을 가진 150개의 샘플로 구성되어 있습니다. 분석과 모델 적용을 쉽게 하기 위해 데이터프레임 형태로 변환합니다.

    3. 데이터 분할 (Train/Test Split)

    데이터를 훈련 세트와 테스트 세트로 분할합니다.

    # 3. 데이터 분할 (Train/Test Split)
    X = df.drop(columns=['target'])
    y = df['target']
    X_train, X_test, y_train, y_test = train_test_split(X, y, test_size=0.3, random_state=42)

     

    • train_test_split 함수를 사용하여 데이터를 70% 훈련 세트와 30% 테스트 세트로 분할합니다.
    • random_state를 지정하여 재현 가능한 결과를 얻을 수 있습니다.

    4. 데이터 정규화

    PCA와 Logistic Regression을 적용하기 전에 데이터를 정규화합니다.

    # 4. 데이터 표준화 (훈련 데이터로만 fit)
    scaler = StandardScaler()
    X_train_standardized = scaler.fit_transform(X_train)
    X_test_standardized = scaler.transform(X_test)

     

    • 정규화의 중요성: 각 특징의 단위나 범위가 다르면 PCA 결과에 영향을 줄 수 있습니다.
    • 훈련 데이터로만 fit: 데이터 누수를 방지하기 위해 훈련 데이터로만 스케일을 학습합니다.

    5. PCA 적용

    훈련 데이터에 PCA를 적용하고, 학습된 모델로 테스트 데이터를 변환합니다 .

    # 5. PCA 적용 (훈련 데이터로만 fit)
    pca = PCA(n_components=2)
    X_train_pca = pca.fit_transform(X_train_standardized)
    X_test_pca = pca.transform(X_test_standardized)

     

    • n_components=2: 2개의 주성분으로 차원 축소합니다.
    • 훈련 데이터로만 fit: PCA 모델은 훈련 데이터로만 학습하고, 테스트 데이터에는 이 학습된 모델을 그대로 적용합니다.

    6. Logistic Regression 적용 및 성능 비교 

    PCA를 적용하지 않은 기존 모델과 PCA 모델에 대해 Logistic Regression을 적용한 후, 성능을 비교해보겠습니다.

    # 6. Logistic Regression 적용 및 성능 비교
    log_reg = LogisticRegression()
    log_reg.fit(X_train_standardized, y_train)
    y_pred_original = log_reg.predict(X_test_standardized)
    
    log_reg_pca = LogisticRegression()
    log_reg_pca.fit(X_train_pca, y_train)
    y_pred_pca = log_reg_pca.predict(X_test_pca)

     

    • 기존 모델: PCA를 적용하지 않은 원본 데이터를 사용한 Logistic Regression 모델.
    • PCA 모델: PCA를 적용하여 차원 축소된 데이터를 사용한 Logistic Regression 모델.
    • 정확도 비교: accuracy_score를 사용해 두 모델의 정확도를 평가합니다.

    7. 성능 비교 결과

    PCA 적용 여부에 따른 Logistic Regression의 성능 차이를 확인할 수 있습니다. 원본 데이터와 PCA로 차원 축소된 데이터 각각의 정확도를 출력합니다.  

    # 7. 성능 비교 (정확도 계산)
    accuracy_original = accuracy_score(y_test, y_pred_original)
    accuracy_pca = accuracy_score(y_test, y_pred_pca)
    
    # 결과 출력
    print("원본 데이터의 정확도 (PCA 적용 안함):", accuracy_original)
    print("PCA 적용한 데이터의 정확도:", accuracy_pca)

     

    모든 차원을 사용했기 때문에 모델이 충분한 정보를 바탕으로 학습할 수 있었고, 그 결과로 테스트 데이터에서 100%의 정확도를 기록했습니다. 이는 모델이 훈련 데이터의 모든 패턴을 학습한 덕분입니다. Iris 데이터셋은 비교적 단순한 데이터셋이라 차원이 높지 않고, 모델이 데이터를 정확하게 예측할 수 있었던 것으로 보입니다.

    원본 데이터의 정확도 (PCA 적용 안함): 1.0
    PCA 적용한 데이터의 정확도: 0.9111111111111111

     

    PCA를 적용해 차원을 4차원에서 2차원으로 축소했을 때, 정확도가 91.1%로 약간 감소했습니다. 이는 차원 축소 과정에서 일부 정보가 손실되었기 때문입니다. 그러나 중요한 점은, 차원을 크게 줄였음에도 불구하고 여전히 90% 이상의 정확도를 유지했다는 사실입니다. 이는 PCA가 데이터의 중요한 패턴을 유지하면서도 덜 중요한 정보는 제거해, 모델이 효율적으로 학습할 수 있도록 도와주었음을 보여줍니다.

     

    전체 코드

    다음은 Iris 데이터셋에 PCA를 적용하는 전체 코드를 보여줍니다.

    # 1. 필요한 라이브러리 임포트
    import numpy as np
    import pandas as pd
    from sklearn.preprocessing import StandardScaler
    from sklearn.decomposition import PCA
    from sklearn.model_selection import train_test_split
    from sklearn.linear_model import LogisticRegression
    from sklearn.metrics import accuracy_score
    from sklearn.datasets import load_iris
    
    # 2. Iris 데이터셋 로드 및 데이터프레임 구성
    iris = load_iris()
    df = pd.DataFrame(iris.data, columns=iris.feature_names)
    df['target'] = iris.target
    
    # 3. 데이터 분할 (Train/Test Split)
    X = df.drop(columns=['target'])
    y = df['target']
    X_train, X_test, y_train, y_test = train_test_split(X, y, test_size=0.3, random_state=42)
    
    # 4. 데이터 표준화 (훈련 데이터로만 fit)
    scaler = StandardScaler()
    X_train_standardized = scaler.fit_transform(X_train)
    X_test_standardized = scaler.transform(X_test)
    
    # 5. PCA 적용 (훈련 데이터로만 fit)
    pca = PCA(n_components=2)
    X_train_pca = pca.fit_transform(X_train_standardized)
    X_test_pca = pca.transform(X_test_standardized)
    
    # 6. Logistic Regression 적용 및 성능 비교
    log_reg = LogisticRegression()
    log_reg.fit(X_train_standardized, y_train)
    y_pred_original = log_reg.predict(X_test_standardized)
    
    log_reg_pca = LogisticRegression()
    log_reg_pca.fit(X_train_pca, y_train)
    y_pred_pca = log_reg_pca.predict(X_test_pca)
    
    # 7. 성능 비교 (정확도 계산)
    accuracy_original = accuracy_score(y_test, y_pred_original)
    accuracy_pca = accuracy_score(y_test, y_pred_pca)
    
    # 결과 출력
    print("원본 데이터의 정확도 (PCA 적용 안함):", accuracy_original)
    print("PCA 적용한 데이터의 정확도:", accuracy_pca)

     

    마무리

    PCA는 복잡한 데이터를 더 간단하게 만들면서도 중요한 정보를 최대한 유지할 수 있는 강력한 차원 축소 기법입니다. 데이터가 어떤 방향으로 가장 많이 퍼져 있는지를 기준으로 주성분을 찾아내고, 그 주성분을 따라 데이터를 축소하는 방식으로 작동합니다. 이렇게 함으로써, 차원을 줄이더라도 중요한 패턴을 놓치지 않고 데이터를 분석할 수 있게 됩니다.

     

    PCA의 수학적 원리는 먼저 공분산 행렬을 구하고, 이를 고유값 분해하는 과정에서 데이터를 가장 잘 설명할 수 있는 주성분을 찾는 것입니다. 즉, 차원을 줄여 데이터의 복잡성을 감소시키면서도 본질적인 정보를 보존하는 것이 PCA의 핵심입니다.

     

    특히 Python과 같은 프로그래밍 언어에서는 Pandas와 scikit-learn 같은 라이브러리를 사용해 이 과정을 매우 간단하게 구현할 수 있습니다. 이러한 도구들은 복잡한 계산을 자동으로 처리해주기 때문에, PCA를 쉽게 적용할 수 있습니다. 이 때문에 PCA는 데이터 분석과 머신러닝 분야에서 매우 널리 사용되는 중요한 기법입니다.

     

    PCA를 통해 우리는 데이터를 효율적으로 분석할 수 있을 뿐만 아니라, 차원을 줄임으로써 분석 속도도 크게 향상시킬 수 있습니다. 따라서 복잡한 데이터를 다루는 다양한 문제에서 PCA는 매우 유용한 도구로 활용될 수 있습니다.

Designed by Tistory.