Seaborn(sns)을 활용한 건강검진 데이터 시각화

Seaborn은 파이썬에서 사용되는 시각화 라이브러리입니다. 아름답고 다채로운 그래프를 그려 주고, 통계적 내용을 시각화에 쉽게 통합할 수 있도록 지원해 주는 파이썬 시각화의 꽃입니다. 이번 글에서는 챗GPT의 GPTs 가운데 Data Analyst에서 Seaborn으로 그래프를 그려봅니다.


데이터셋은 data.go.kr에서 제공하는 국민건강보험공단_건강검진정보입니다. 국민건강보험 가입자의 당해 연도 검진 결과 중 40대 이상에서 1백만 건이 랜덤으로 추출된 데이터셋입니다.


이 91MB 크기의 데이터셋을 시험 삼아 챗GPT에게 읽혀 보니, 의외로 일단 읽어 들이는데, 열 이름을 추출하다가 멈춥니다. 아무래도 무리인가 봅니다. 그래서 앞부분 20만 행(18MB)만 잘라서 사용합니다. 열도 원 데이터에 34개가 있는데, 대표성을 띠는 지표 12개만 추려서 사용합니다. 수축기 혈압과 이완기 혈압 중 수축기 혈압만을 사용하는 식입니다.


이번 글을 통해서 챗GPT가 Seaborn(이하 ‘sns’)을 활용하는 시각화를 어디까지 구현하는지 확인해 보시기 바랍니다.


대화 링크: https://chat.openai.com/share/ba405925-3aed-4c0c-9d8c-4c5383683ce9



전처리


필요한 열만 지정하여 파일을 읽어 들입니다. 행은 미리 1백만 개 가운데 앞쪽 20만 개를 추려서 csv로 저장해 두었습니다. 부담을 줄여주기 위하여 필요한 열만 읽으라고 합니다.


한글 폰트 파일(SCDREAM5.OTF)을 사용하여 그래프에 한글이 잘 표시되는지 확인하기 위한 시험 그래프를 그립니다. 아직 이상치 제거를 하지 않아서, 이상치의 영향으로 데이터가 한 쪽으로 쏠려 나오기는 하지만, 한글 표시는 잘 합니다. 이번 세션에는 한글 표시가 잘되지 않을까 기대해 봅니다.



참고로, 챗GPT가 Seaborn 라이브러리를 써서 그래프를 그릴 때 한글을 표시하는 수준은 세션에 따라 차이가 있습니다. 어떤 세션에서는 설정을 잘 하여 일부 그래프에서라도 한글을 표시하지만, 어떤 세션에서는 설정을 못하여 아예 표시하지 못하기도 합니다.

따라서 한글을 사용하려면 세션을 열자마자 그래프를 하나 그려서 한글을 표시하는지 확인하는 것이 좋습니다. 하지만 처음에 성공한다고 세션 내내 한글을 잘 표시하는 것은 아닙니다. 한글 표시가 반드시 필요한 경우가 아니라면 데이터를 영문으로 바꾸어 영문 그래프를 그리는 방법도 생각해 볼 수 있습니다.



열 이름을 간단하게 바꿉니다.



데이터 값이 숫자로 표현되어 있는 열들이 있어서 알아보기 쉽게 문자로 바꿉니다.



결측치를 제거합니다. 데이터가 충분히 많으니 고민하지 않고 결측치는 모두 제거합니다.



이상치도 과감하게 제거합니다. 최초 20만 행이 최종 6만 7천 행으로 줄었습니다.



체질량 분석을 추가하기 위하여 BMI(체질량) 열을 추가합니다. 공식을 알려주지 않고 넣으라고만 해도 알아들으니 편리합니다. 신장, 체중 열은 이제 필요하지 않으니 삭제합니다. 참고로 BMI는 체중(kg)을 키(m)의 제곱으로 나눈 값으로서, 비만을 판단하는 데 사용되는 지표입니다.



전처리가 완료된 데이터 파일을 다운로드합니다. 이렇게 해 놓으면 혹시 세션을 다시 열어 시각화를 다시 해야 하는 일이 생기더라도 처음부터 작업을 다시 하지 않아도 되니까요.



시각화

이제 본격 시각화를 시작합니다.

sns의 jointplot부터 그려 봅니다. jointplot은 산점도와 히스토그램을 결합하여 두 변수 사이의 상관관계 및 각 변수의 분포를 한눈에 파악할 수 있는 도구입니다.



다음은 sns의 relplot입니다. relplot은 여러 서브플롯(subplot)과 hue 파라미터를 사용하여 다차원 데이터를 효과적으로 표현할 수 있습니다. 아래 그래프가 3개인 이유는 흡연 상태에 따라 왼쪽부터 비흡연, 금연, 흡연을 하나씩 그렸기 때문입니다. 시도별로 LDL 수치의 차이, 또 각 시도 내에서도 연령대별로 어느 연령대의 LDL 수치가 높은지 색상의 진하기로 대략 파악이 됩니다. (예를 들어 첫 번째 비흡연 그래프에서는 높은 연령대의 LDL 수치가 낮은 편입니다)

그런데 한글이 표시되지 않아서 다시 그렸으나 또 실패, 꼭 그려달라고 했더니 그 말이 통한 것인지, 아니면 때가 된 것인지 세 번째에 성공했습니다.

(중간 생략)


한글 설정을 어떻게 해서 성공했는지 물어봅니다.



sns의 catplot, 그중에서도 바이올린 플롯을 그려 봅니다. 바이올린 플롯은 박스 플롯의 정보와 커널 밀도 추정(KDE)을 결합하여, 데이터의 분포 형태와 중앙값(아래 그래프에서 각 바이올린 중앙의 점), 사분위수(중앙값 선 위아래에 있는 검은 막대의 끝)를 한눈에 파악할 수 있도록 해주며, 데이터의 분포와 중요한 통계적 정보를 동시에 제공합니다.

연령대별로 남자 바이올린 하나, 여자 바이올린 하나를 그려달라고 했는데 합쳐서 하나로 그렸습니다. 범례의 한글도 깨졌습니다.



다시 그려달라고 하니 연령대별로 바이올린 하나씩은 잘 그리는데, 한글은 여전히 완벽하게 나오지 않습니다.



다음으로 넘어갑니다. 이번에는 복잡한 분석을 맡깁니다. ‘경기도의 혈압 평균이 전국 혈압 평균 대비 어느 정도일까’라는 질문에서 출발하는 지역별 비교 분석입니다. 혈압뿐만 아니라 혈당, LDL, 크레아티닌, ALT, BMI 지표를 모든 지역에 대해 비율을 구하고 비교해 봅니다. 계산이 좀 필요한지라 한꺼번에 그래프까지 그리라고 하지 않고 먼저 비율부터 구하라고 합니다.


그리고 이를 꺾은선 그래프로 그려 봅니다. 범례의 한글 제목이 또 깨졌습니다. 다시 그려달라고 했지만 나아지지 않습니다(다시 그려달라고 한 대화의 화면 카피는 생략합니다).



이 수치를 한 번 더 사용하되, 이번에는 서울과 제주만을 비교해 봅니다. 어떻게 범례를 저 위치에 둘 생각을 했는지 신기합니다.



y 축 최소치를 90으로 설정하면 비교가 쉬워질 듯합니다. 한글 표시도 다시 해달라고 합니다.


지역별로 건강한 사람의 비율을 비교해 봅니다. 이 분석도 복잡하기 때문에 두 단계로 나누어, 우선 새로운 열을 4개 추가하고 성인병 여부를 1(이상), 0(정상)으로 기록합니다.



다음 새로 추가한 4가지 질병 모두에 걸리지 않은 사람을 건강한 사람이라고 임의로 정의하고, 지역별로 막대그래프를 그립니다. 모처럼 한글이 완벽하게 나왔습니다. 범례가 없는 덕이지요.


y 축 최소치를 50으로 너무 낮게 잡았다가 45로 바꾸고, 데이터 레이블을 넣습니다.



마지막으로 지도 위에 정보를 표시할 수 있는지 물어봅니다.


조금 아쉽지만 괜찮습니다. 가점을 주려는 질문이었지, 감점하려는 질문 아니었습니다. folium의 wheel 파일을 구하여 업로드를 시도해 볼 수 있겠으나, 글의 범위를 벗어나는 느낌이므로 여기서 멈춥니다.



그냥 끝내기가 아쉬워서 pairplot을 그려 봅니다. 다른 세션에서 pairplot을 그리려다가 이미 여러 번 실패했기 때문에 가볍게 첫 500행 만으로 그려 달라고 합니다. 그리고 모처럼 성공합니다! (원래 pairplot을 분석 초기에 그려서 변수들 간의 상관관계를 보지만, 다른 세션 실패의 아픔이 있어서 마지막에 그렸습니다.)



결론

  1. Seaborn 라이브러리를 사용한 시각화는 상당한 수준에서 구현되었습니다. 그러나 두 가지 사항은 개선이 필요합니다.

    첫째 한글 표시가 불완전합니다. 세션에 따라서는 한글 표시가 전혀 안 되기도 하고, 잘 되다가 불안정해지기도 합니다. 특히 범례의 제목 표시가 되지 않는 경우가 많습니다.

    다른 하나는 pairplot 그래프 생성의 어려움입니다. 이번 세션에서는 데이터양을 제한(500개의 행)하여 성공하였지만, 다른 두 번의 세션에서는 모두 실패하였습니다. 이는 챗GPT의 프로그램 실행시간 1분 제한의 영향으로 추정됩니다. 파이썬에서도 pairplot을 그리려면 시간이 꽤 소요됩니다.

    그럼에도 불구하고, 파이썬을 이용한 복잡한 코딩 없이 이 정도의 시각화가 가능하다는 것은 큰 장점입니다. 더구나 챗GPT가 사용자 요구 사항을 매우 잘 이해하며, 심지어 사용자의 실수도 바로잡아 처리하는 것은 매력적입니다.

  2. 대용량의 데이터 처리와 시각화에 성공했습니다. 20만 행 x 34열의 18MB 데이터 파일을 읽어 들이고, 그중 6만 7천 행 x 11개 행을 사용하여 여러 그래프를 그렸습니다. 이는 Seaborn과 챗GPT를 결합한 데이터 분석 및 시각화의 가능성을 보여줍니다.

  3. 마지막으로 데이터 보관 시간의 제한은 주의가 필요한 부분입니다. 세션을 시작하고 데이터를 올린 뒤 2시간 만에 데이터를 읽어올 수 없다는 메시지가 나와서 처음부터 다시 작업한 적이 있습니다. 데이터 전처리가 끝나면 파일로 다운로드해서 저장해 두는 것이 바람직해 보입니다.

4
4개의 답글

👉 이 게시글도 읽어보세요

모집 중인 AI 스터디