
📚 프로젝트 개요

- 공모전 : 2024 NH투자증권 빅데이터 경진대회
- 주제 : 생성형 AI를 활용한 미국 ETF 큐레이션 서비스 제안
- 진행 기간 : 24.09 ~ 24.11
- 팀 구성 : 3명
- 사용 데이터 : NH데이터, 종목 정보/시세 데이터, ETF 스코어/구성종목/배당 데이터
- 사용 언어 : Python
- 프로젝트 링크(예선) : https://dacon.io/competitions/official/236348/codeshare/11690
📍 프로젝트 목표

주식 시장의 복잡한 정보로 인해 투자 결정을 어려워하는 개인 투자자를 위해 생성형 AI 챗봇 기반의 ETF 큐레이션 서비스를 기획했다. AI와의 대화형 설문으로 투자 성향을 파악하고, PCA 분석을 통해 도출한 NBTI 지표를 기반으로 사용자 성향에 맞는 ETF를 추천하는 것이 핵심 목표이다. 이후에는 별점 피드백과 리밸런싱 기능을 더해 추천의 정확도를 지속적으로 개선하는 구조로 설계했다.
📍 데이터 수집 및 가공

주식 및 ETF 목록은 NH투자증권에서 제공한 내부 데이터를 활용해 구성했다. 내부 데이터에서 주식에 해당하는 종목만 추출해 ticker 리스트를 만들었고, 이를 기반으로 티커·영문 기업명·ETF 여부를 포함한 데이터프레임을 생성했다. 그 결과 주식 3,507개, ETF 1,126개 종목을 확인할 수 있었다.

재무 데이터는 Finbox 웹사이트를 통해 크롤링하여 수집했다. Finbox는 전 세계 상장 기업의 최신 재무 데이터를 제공하는 금융 정보 플랫폼으로, 재무상태표·손익계산서·시가총액 세 카테고리에서 총자산, 순이익, PER, EPS 등 주요 지표를 크롤링했다. 데이터를 수집하고, 유동 자산·부채 누락 시 총자산에서 역산하는 방식으로 결측값을 보완했으며, 연결 실패나 파싱 오류는 로그 파일로 별도 기록했다.

수집한 재무 데이터에 있던 결측값은 두 가지 방법으로 보완했다. 선형 보간(Linear Interpolation)은 두 점을 직선으로 연결해 그 사이의 값을 추정하는 방식이다. 데이터의 분포가 직선에 가까울 때 유용하며, 연도별 결측값을 시계열 순서로 정렬한 뒤 앞뒤 값 사이를 선형으로 채웠다.

KNN 보간(K-Nearest Neighbors Imputation)은 결측값이 있는 데이터와 가장 가까운 K개의 이웃을 찾아 가중평균으로 대체하는 방식이다. 선형 보간으로 채우기 어려운 결측값에 적용했으며, 데이터의 원래 패턴과 분포를 잘 보존한다는 장점이 있다. KNNImputer를 사용해 K=5로 설정했고, ticker 기준으로 병합 후 수치형 데이터만 남겼다.

결측값 보완이 끝난 뒤에는 분석에 필요한 파생변수를 추가로 생성했다.
- market_cap(시가총액) : stocks(주식 수) * price(주가)
기업의 전체 시장 가치를 나타내는 지표로, 이후 PER·PBR 등 비율 지표 계산의 기준이 됩니다. - evebit_ratio(EV/EBIT 비율) : market_cap(시가총액) / ebit(이자 및 세전 이익)
기업의 수익 창출 능력 대비 시장 평가 수준을 나타내며, PER보다 부채 구조의 영향을 덜 받아 기업 간 비교에 유용합니다. - pe_ratio(PER, 주가수익비율) : market_cap(시가총액) / eps_diluted(희석 주당순이익)
투자자가 1원의 이익을 얻기 위해 얼마를 지불하는지를 나타내며, 고평가·저평가 판단에 널리 쓰입니다. - rnd_ratio(연구개발비 비율) : op_exps(영업비용) / rnd_exps(연구개발비)
기술주나 바이오 섹터 ETF처럼 R&D 집약적인 기업군을 구분하는 데 활용됩니다. - com_equity(보통주 자본) : tot_equity(총자본) - pre_equity(우선주 자본)
실질적으로 보통주 주주에게 귀속되는 자본을 의미합니다. - pb_ratio(PBR, 주가순자산비율) : market_cap(시가총액) / com_equity(보통주 자본)
기업의 장부가치 대비 시장 평가를 나타내며, PER과 함께 가치주 판별에 자주 사용됩니다.
이렇게 산출한 파생변수들은 연도별 평균값으로 요약한 뒤, ETF별 보유 종목의 비중을 가중치로 적용해 ETF 단위의 재무 특성값으로 집계했다.

ETF별 가중평균 계산은 내부 데이터의 두 테이블을 결합하는 방식으로 진행했다. 데이터 준비 단계에서는 종목별 재무 데이터(cal_df)와 ETF별 보유 종목 리스트(hds_df)를 각각 불러왔고, hds_df는 ETF 코드를 기준으로 그룹화해 ETF별 구성 종목 목록을 만들었다.
가중평균 계산은 각 ETF에 포함된 종목 중 재무 데이터가 존재하는 종목만 필터링한 뒤, 종목별 보유 비중(wht_pct)을 가중치로 곱해 가중합을 구하고, ETF의 총 가중치로 나눠 최종 가중평균값을 산출했다. 보유 비중을 가중치로 쓰는 이유는 ETF 내에서 비중이 높은 종목일수록 해당 ETF의 특성에 더 큰 영향을 미치기 때문이다.
이렇게 산출된 ETF별 재무 특성값은 내부 데이터와 조인해 최종 데이터셋으로 통합했다. 최종 데이터프레임에는 총자산, EPS, 순이익, 매출총이익률, PER, PBR 같은 재무 지표뿐 아니라 거래량, 수익률, ETF 종합 점수(etf_sor), 배당수익률 등 내부 데이터 기반 지표까지 함께 포함해서 분석에 활용했다.
📍 데이터 분석

① 상관관계 분석
PCA 적용 전에 변수 간 상관관계를 먼저 확인했다. 다른 변수와 상관이 낮거나 중복되는 변수는 모델의 올바른 해석을 저해할 수 있기 때문에 제거했다. 또한 ETF 코드 관련 열을 추가하고, ETF 종목만 남기도록 필터링해 분석 대상을 정리했다.
② 표준화
PCA는 변수의 분산에 민감하게 반응하기 때문에 스케일링을 먼저 진행했다. StandardScaler로 평균 0, 분산 1로 표준화한 뒤, MinMaxScaler로 0~1 사이로 한 번 더 범위를 제한했다. 두 단계를 거치는 이유는 값의 상대적 크기를 더욱 안정적으로 관리하기 위함이었다. 이후 데이터의 치우침을 완화하기 위해 로그 변환도 적용했는데, 로그 함수가 음수를 처리하지 못하기 때문에 절댓값을 취한 뒤 변환했다.
③ 설명된 분산 확인
과적합을 방지하고 적절한 주성분 개수를 결정하기 위해 설명된 분산 비율을 기준으로 k를 선택했다. 분산 기여도가 급격히 줄어드는 지점을 확인한 결과, k=4일 때 데이터 설명력 72%를 확보할 수 있어 주성분 개수를 4개로 결정했다.


④ 차원별 비중 분석
4개의 주성분이 확정된 후, 각 변수가 주성분에 얼마나 기여하는지를 로딩 값으로 계산했다. 이를 히트맵으로 시각화해 변수와 주성분 간 상관성을 확인했고, 색상의 진하기와 방향으로 로딩 값의 크기와 부호를 파악했다.
⑤ 산포도 확인
주요 주성분을 조합한 3D 산포도를 생성해 ETF가 주성분 공간에서 어떻게 분포하는지 시각화했다. PC1~PC4를 세 개씩 조합한 총 4가지 시점(PC1·2·3, PC1·2·4, PC1·3·4, PC2·3·4)으로 확인했으며, 이를 통해 ETF 간의 유사성과 차이점을 직관적으로 비교할 수 있었다. 특정 주성분 축에서 뭉쳐 있는 ETF들은 해당 투자 성향이 유사한 종목들로 해석할 수 있었다.
📍 추천 서비스 구현


사용자의 투자 정보 수집을 위한 설문은 MS Azure의 OpenAI API와 연동해 동작한다. AI가 각 문항에 대해 질문을 던지면 사용자가 자유롭게 답변하는 대화형 방식으로, 기존 객관식 설문과 달리 사용자의 투자 성향을 더 깊이 파악할 수 있다. 답변 형식이 맞지 않으면 AI가 즉시 재요청해 결과의 정확성을 높였고, 오류를 최소화했다.
분류 문항(option)은 나이, 소득원, 보유 금융자산 규모, 투자 경험 기간, 관심 섹터 등 객관적인 정보를 수집한다. 성향 문항(score)은 투자 전략, 중요하게 생각하는 요소, 금융 상품 관리 경험, 미래 투자 목표 등을 자유롭게 서술하도록 해 정성적인 성향을 파악한다. 질문을 구성하는 딕셔너리에 options 키와 multie 키를 부여해 분류 모델과 평가 모델별 프롬프트를 구분하고, 중복 선택이 필요한 문항은 구조화된 방식으로 처리했다.
사용자는 AI와 자유롭게 대화하며 설문을 진행한다. AI는 각 문항에 대해 질문을 던지고 사용자는 자신의 투자 성향을 자유롭게 표현할 수 있다. AI는 사용자의 응답을 실시간으로 분석하면서 피드백을 제공하는 동적 시스템으로, 단순한 입력 수집이 아니라 자유로운 상호작용을 통해 투자 성향을 정확하게 파악한다.
응답이 수집되면 AI는 이를 바탕으로 다차원 분석을 수행해 각 차원에서 사용자의 성향을 점수화한다. 앞서 PCA로 도출한 4개의 주성분(PC1~PC4) 기준으로 성향을 판별하고, 각 축의 점수가 양수인지 음수인지에 따라 알파벳 코드를 부여해 NBTI 유형을 결정한다.


NBTI(NH Behavioral Type Indicator) 유형화 단계는 사용자의 투자 성향을 분석하고 이를 시각화된 나무 유형으로 제공하는 과정이다. 사용자는 자신의 투자 성향을 나무 이미지와 간결한 설명으로 제공받아 복잡한 분석 결과를 직관적으로 이해할 수 있다. 투자 성향을 친근한 나무로 표현함으로써 투자에 대한 복잡함을 덜고 쉽게 접근할 수 있도록 했다. 사용자의 PCA 점수를 기반으로 4개의 주요 투자 성향을 판별한다.
- PC1: R(고위험·고수익) / S(안정)
- PC2: I(지수 추종) / A(액티브)
- PC3: M(중소형주) / L(대형주)
- PC4: D(배당 선호) / G(성장 선호)
4개 축의 조합으로 총 16가지 NBTI 유형이 만들어지며, 각 유형은 대추나무·벚나무·자작나무·소나무 등 친숙한 나무 이름으로 표현된다.

16가지 NBTI 유형 각각에 대응하는 나무 이미지는 Microsoft Designer를 활용해 생성했다. 프롬프트를 설계해 각 나무의 특성과 투자 성향 콘셉트를 반영한 이미지를 제작했으며, 전체 16종을 일관된 스타일로 통일해 시각적 완성도를 높였다.

성향 기반 추천은 생성형 AI를 활용해 사용자가 평가한 성향 척도를 기반으로 투자 성향이 가장 유사한 ETF를 추천한다. 코사인 유사도를 활용해 투자 성향 일치도를 정량적으로 평가하고, 가장 유사한 ETF 리스트를 도출한다. 사용자의 별점 입력이 반영되어 성향 척도와 추천 결과를 맞춤화한다.
특성 기반 추천은 고객 분류 데이터(CUS_TP_IFO)의 비중 정보를 활용해 사용자가 속한 집단과 가장 유사한 종목을 추천한다. 유클리드 거리 계산을 사용해 종목 간 유사도를 측정하며, 사용자와 비슷한 투자 역량·연령대·자산 규모를 가진 고객들이 선호하는 종목을 추천받을 수 있습니다. 마찬가지로 별점 입력이 반영되어 추천 결과를 더욱 개인화한다.

PCA 칼럼을 추출한 뒤 -1에서 1 사이로 스케일링하고, 사용자의 NBTI 점수로부터 생성한 사용자 벡터도 동일하게 스케일링한다. ETF 성향 벡터도 같은 방식으로 생성한 뒤, 두 벡터 간의 코사인 유사도를 계산해 투자 성향 일치도를 정량적으로 측정한다. 유클리드 거리 대신 코사인 유사도를 사용하는 이유는 벡터의 크기보다 방향성을 기준으로 유사도를 측정하기 때문에 성향 비교에 더 적합하기 때문이었다. 코사인 유사도 기준으로 내림차순 정렬한 뒤 상위 5개 ETF를 추천 리스트로 도출하고, 각 ETF의 유사도 비율을 계산해 포트폴리오 비중을 할당한다. 추천 결과는 ETF 티커와 비중, 해당 ETF의 투자 성향 특성을 AI가 설명하는 형태로 제공된다.
별점 가중치 적용은 사용자가 추천받은 ETF에 1~5점의 만족도를 입력하면 이를 저장한다. 평가하지 않은 ETF는 결측값(NaN)으로 처리되며, 더미 데이터를 생성해 평가 데이터가 부족한 상황을 보완한다. 이후 사용자의 PCA 벡터와 별점 데이터를 불러와 결측값은 기본값(평균 3)으로 채운 뒤, 코사인 유사도에 별점을 곱해 최종 가중치 벡터(wht_vec)를 생성한다. 별점이 높은 ETF일수록 유사도 점수가 보정되어 추천 순위에 반영되는 구조로, 사용자가 평가를 누적할수록 점점 개인화된 추천이 가능해진다.

고객 분류 데이터(CUS_TP_IFO)의 비중 정보를 활용해 사용자가 속한 집단과 가장 유사한 종목을 추천하는 방식이다. 사용자와 비슷한 투자 역량·연령대·자산 규모를 가진 고객들이 선호하는 종목 패턴을 분석해 추천에 활용한다.
데이터 전처리 단계에서는 고객 분류 데이터를 대분류·중분류 두 가지 기준으로 그룹화했다. 중분류별로 각 매트릭스 값을 하나의 분포로 보고 표준화 단계와 Min-Max 정규화 단계를 적용해 z점수로 변환한다. z점수가 1인 것은 해당 중분류 값 중 최댓값에 해당하는 종목임을 의미한다. 표준화가 끝나면 행 인덱스에 종목 티커, 열 인덱스에 중분류를 재설정해 피벗 테이블을 만들고 저장한다.
성향 기반 추천과 달리 특성 기반 추천에서는 유클리드 거리를 이용해 계산한다. 나이·자산 규모·투자 경험 같은 인구통계학적 특성을 기준으로 사용자와 비슷한 고객 집단을 찾는 특성 기반 추천에서는 절대적인 수치 차이가 중요하다. 유클리드 거리는 다차원 공간에서 두 점 사이의 실제 거리를 측정하기 때문에 특성값의 차이를 직접적으로 반영할 수 있었다. 사용자의 중분류, 즉 options 벡터를 기준으로 전체 중분류 중 필요한 중분류를 선택해 가져온 뒤, 중분류의 z점수가 높은 종목을 가져오기 위해 사용자의 벡터값을 [1, 1, 1] 형태로 가정한다. 이후 사용자 벡터와 종목별 벡터의 유클리드 거리를 계산하고, 거리 값이 작을수록 해당 종목이 사용자의 특성과 유사함을 의미한다.
결과 도출 단계에서는 유클리드 거리가 0인 종목부터 포함해 출력 가능한 종목이 k개 이상이 될 때까지 허용 가능한 거리를 0.005씩 증가시키며 조건을 만족하는 종목을 출력한다. 별점 가중치와 데이터 변동 반영 옵션(wht, chg 파라미터)을 통해 성향 기반 추천과 동일하게 개인화된 추천 결과를 제공한다.

리밸런싱은 기존 포트폴리오와 시장 정보를 결합해 자산 배분의 효율성을 높이고, 변화하는 시장 환경에 대응하며 투자자 성향에 맞는 개인화된 전략을 제공한다.
포트폴리오 기반 리밸런싱은 사용자의 투자 성향(NBTI 점수)과 기존 보유 종목 데이터를 기반으로 현재 포트폴리오를 설정한다. 이후 PCA 점수를 정규화한 뒤, 포트폴리오 벡터(ivt_vec)와 사용자 벡터(user_vec)를 가중평균으로 조합해 최적의 투자 성향 점수를 계산한다. 코사인 유사도를 기반으로 기존 포트폴리오와 신규 종목 간 유사도를 비교하고, 유사도가 높은 종목을 순서대로 선택해 기존 종목과 신규 종목을 조합한 최종 포트폴리오를 구성하고 종목별 비중을 산출했다.
데이터 변동 기반 리밸런싱은 ETF 데이터가 업데이트될 경우 이를 기존 데이터에 반영하는 방식이다. ETF 데이터를 업데이트하고, [-1, 1] 범위로 스케일링한 뒤 PCA 모델을 적용해 주요 주성분(PC1~PC4)으로 변환한다. 변환된 PCA 결과는 CSV로 저장해 후속 작업에 활용한다. 이를 통해 시장 변화가 생길 때마다 ETF의 성향 벡터를 최신 상태로 유지하고, 업데이트된 데이터를 기반으로 성향 기반 추천을 다시 수행해 최신 시장 상황이 반영된 포트폴리오를 제안한다.
이후, 구현된 추천 시스템이 실제로 잘 작동하는지 확인하기 위해 4가지 페르소나를 설정해 검증했다. 23세 대학생(고위험 선호), 34세 직장인(안정적 배당 선호), 52세 사업가(소형주·섹터 ETF 선호), 63세 직장인(고배당·채권 ETF 선호)으로 구성했으며, 각 페르소나의 투자 성향과 목표에 맞게 NBTI 유형 분류, 성향 기반 포트폴리오 추천, 별점 반영 추천, 특성 기반 추천, 리밸런싱 단계를 순서대로 적용해 결과를 확인했다.
📍 후기
이번 프로젝트를 통해 금융 데이터를 활용한 투자 성향 분석과 ETF 특성 분석을 수행하며, 데이터 기반 투자 서비스 설계 과정을 경험할 수 있었다. 특히 분석 결과를 사용자에게 보다 직관적으로 전달하기 위해 생성형 AI 챗봇과 결합하는 방식을 고민하면서, 데이터 분석이 실제 금융 서비스로 이어지기 위해 필요한 관점을 배울 수 있었다.
또한 이전에 사용했던 데이터와 달리 실제 고객의 거래 데이터를 다루면서 초기에는 어려움도 많았다. 실제 금융 데이터는 내부 정책상 공모전 참여자에게 공개하더라도 변수의 의미나 기준이 명확하게 정의되어 있지 않은 경우가 많았다. 기존에 사용했던 리뷰 데이터와는 완전히 다른 데이터 형태였으며, 처음 접하는 데이터이기 때문에 어떤 방식으로 분석에 활용할 수 있을지 고민하는 과정이 필요했다. 하지만 이를 통해서 여러 분석 방법을 시도해볼 수 있었고, 이를 통해 데이터 활용에 대한 시야를 넓힐 수 있었다.
NBTI 서비스를 직관적으로 표현하기 위해 생성형 AI를 활용한 이미지 생성도 시도했다. 프롬프트 설계를 통해 서비스 콘셉트를 시각화할 수 있다는 점이 인상적이었고, 생성형 AI가 서비스 기획과 표현 방식에서도 활용될 수 있다는 가능성을 확인할 수 있었다.
'프로젝트 및 공모전' 카테고리의 다른 글
| [학회 발표] 토픽 모델링과 오피니언 마이닝을 활용한 영화 리뷰 유용성 측정 (1) | 2026.04.20 |
|---|