상세
- 기존의 구매한 물품을 바탕으로 다음 아이템을 추천해주는 서비스
역할
- 크롤링을 통한 데이터 수집
- React를 활용한 웹페이지 구성
- gensim 라이브러리를 활용하여 유사한 아이템 모델 구성
- Implicit 라이브러리를 활용하여 유사한 유저 모델 구성
- 기존 유사한 유저 모델을 활용한 아이템 긍부정 예측 모델 구성
경험
- 사용해본 어플 중에서 추천 서비스를 추가해보자
- 플랩풋볼에서 선수 매칭 서비스를 만들어보자
- 플랫풋볼에서 이미 경기를 추천하는 서비스가 있는 것으로 확인
- 오늘의집에서 개인화 추천 서비스를 만들어보자
- 오늘의집 쇼핑에서 보여주는 화면이 같아보여 개인화 추천이 없는 것으로 판단
- 수집할 데이터를 선정
- 모든 아이템으로 하기에는 수가 많음
- 집들이에서 아이템을 선정
- 집들이 게시물에 있는 아이템은 실제로 다른 아이템과 조합되는 아이템이라고 판단
- 아이템과 유저와의 interaction 데이터를 아이템의 리뷰로 선정
- 아이템을 구매한 유저가 리뷰를 작성할 수 있기에 확실히 구매했다는 근거가 존재
- React를 사용하여 화면을 구성함
- React는 처음
- 일단 React의 특징과 기능을 익히기 위해 quick start와 블로그를 바탕으로 학습
- 템플릿을 찾은 후 화면으로는 어떻게 보여지는 지 확인하며 수정
- 비동기도 처음
- console에 log를 찍어보며 데이터가 어떻게 진행되는 지 확인
- axios와 useEffect를 활용하여 비동기로 데이터를 받아 진행
- useEffect를 사용하였는데 계속해서 백엔드에 요청하는 문제가 발생
- AbortController로 처음 요청하면 호출을 종료하도록 구성
- 데이터가 변경되어 다른 요소에도 수정 필요
- 함수를 인자로 넘겨 하위 요소에서 함수 호출로 데이터 변경이 가능하도록 함
- useState를 활용하여 데이터가 변경되면 하위 요소에도 변경되도록 함
- 유사한 아이템 모델을 설계
- 아이템은 같이 구매되는 아이템이 있을 것이라 판단
- 유저에 대하여 아이템 sequence을 word2vec으로 임베딩
- 임베딩 값을 통해 아이템 간의 유사도를 계산
- 유사한 유저 모델을 설계
- word2vec로는 불가능
- 유저의 순서는 유저의 특성과 관련이 없음
- graph 모델으로 변경되어 짐
- 유저-아이템 쌍의 interaction 데이터라 node 구성하는 데 어려움이 있음
- 유저-아이템으로 node를 구성하면 유저에 대한 아이템이 나올 것이라 예상
- 아이템에 리뷰를 남긴 유저 쌍으로 node를 구성하는 데 메모리 부족
- A 아이템에 리뷰를 남긴 유저가 100명있다면 $_{100}C_2$의 가지수가 발생
- 아이템은 8만개, 리뷰 수는 1440만개
- 비교적 메모리에 부담이 적은 MF 모델을 사용하기로 하였고, 그 중 학습 시간이 짧은 ALS를 사용하기로 함
- Linux와 ALS 학습에 발생한 충돌을 해결함
- GCP(백엔드) 서버는 저렴한 서버를 사용하여 추천 모델을 돌리기에는 무거움
- 모델 서버에서 ALS를 학습하는 데 오류가 발생
- 윈도우에서 ALS을 학습, intent vector를 얻고 Annoy를 통해 간소화하여 사용
- Annoy는 build 함수를 사용하면 새로운 데이터를 학습할 수 없고 10분 이상 걸려 매번 Annoy를 build 할 수 없음
- ALS만 사용하여 구성해야 하는 필요성을 느낌
- OpenMP가 멀티 스레드를 지원하는 데 리눅스 버전에 따라 OpenBLAS에 멀티 스레드를 직접 설정해야 했음
- implicit 라이브러리의 ALS는 OpenMP를 사용함
- 명령어 export OMP_NUM_THREADS=1를 먼저 실행하여 스레드를 하나만 실행
- 결과적으로 모델 서버에서 ALS 학습이 가능해짐