-
[Recommendation] 유사도와 KNN을 활용한 예측값 계산 및 추천 목록 생성ML/Recommendation 2020. 3. 6. 18:46
유사도를 구하는 것까지 구현을 해봤으니, 이제 추천 목록을 생성해보자!
-
유사도 구현? 관련 포스팅> 유클리디안 ① https://dokylee.tistory.com/26 // MSD, Cosine, Pearson ② https://dokylee.tistory.com/27
유사도와 KNN을 활용한 예측값 계산 및 추천 목록 생성 기법
- 사용자들 간의 유사도를 이용하여 모든 아이템에 대한 예측 평점을 계산하고, 높은 값을 갖는 상위 N개의 추천 목록 생성
- Nearest Neighbors(KNN) 가중치 예측 기법
- 사용자(또는 아이템)와 유사도가 큰 k개의 사용자(또는 아이템) 벡터를 사용해 가중 평균을 구해서 가중치를 예측
KNN Basic
평점들을 단순히 가중 평균Nk는 유사도가 큰 벡터 상위 k개의 집합
- Python 구현
ratings_expand = { '마동석': { '택시운전사': 3.5, '남한산성': 1.5, '킹스맨:골든서클': 3.0, '범죄도시': 3.5, '아이 캔 스피크': 2.5, '꾼': 3.0, }, '이정재': { '택시운전사': 5.0, '남한산성': 4.5, '킹스맨:골든서클': 0.5, '범죄도시': 1.5, '아이 캔 스피크': 4.5, '꾼': 5.0, }, '윤계상': { '택시운전사': 3.0, '남한산성': 2.5, '킹스맨:골든서클': 1.5, '범죄도시': 3.0, '꾼': 3.0, '아이 캔 스피크': 3.5, }, '설경구': { '택시운전사': 2.5, '남한산성': 3.0, '범죄도시': 4.5, '꾼': 4.0, }, '최홍만': { '남한산성': 4.5, '킹스맨:골든서클': 3.0, '꾼': 4.5, '범죄도시': 3.0, '아이 캔 스피크': 2.5, }, '홍수환': { '택시운전사': 3.0, '남한산성': 4.0, '킹스맨:골든서클': 1.0, '범죄도시': 3.0, '꾼': 3.5, '아이 캔 스피크': 2.0, }, '나원탁': { '택시운전사': 3.0, '남한산성': 4.0, '꾼': 3.0, '범죄도시': 5.0, '아이 캔 스피크': 3.5, }, '소이현': { '남한산성': 4.5, '아이 캔 스피크': 1.0, '범죄도시': 4.0 } }
def get_KNN_recommend(data, name, n=3, sim_function=sim_pearson): result = top_match(data, name, n, sim_function) score_dic = dict() sim_dic = dict() li = [] for sim, user in result: print(sim, user) if sim<0: continue for title in data[user]: if title not in data[name]: score = sim * data[user][title] score_dic.setdefault(title, 0) score_dic[title] += score sim_dic.setdefault(title, 0) sim_dic[title] += sim for title in score_dic: score_dic[title] /= sim_dic[title] li.append((score_dic[title], title)) # (예측평점, 영화제목) li.sort(reverse=True) print('\n** Recommendation') for rating, score in enumerate(li): print(rating+1, '등: ', score[1], ', ', score[0], '점') return li
get_KNN_recommend(ratings_expand, '소이현')
Out:
...
** Recommendation
1 등: 꾼 , 3.6903300787431923 점
2 등: 택시운전사 , 3.0 점
3 등: 킹스맨:골든서클 , 1.9168062051113846 점KNN with Means
평점들을 평균값 기준으로 가중 평균
- Python 구현
sum = 0 count = 0 for name in ratings_expand: for title in ratings_expand[name]: sum += ratings_expand[name][title] count += 1 ratings_expand[name]['avg'] = sum/count ratings_expand
Out:
{'마동석': {'택시운전사': 3.5,
'남한산성': 1.5,
'킹스맨:골든서클': 3.0,
'범죄도시': 3.5,
'아이 캔 스피크': 2.5,
'꾼': 3.0,
'avg': 2.8333333333333335},
'이정재': {'택시운전사': 5.0,
'남한산성': 4.5,
'킹스맨:골든서클': 0.5,
'범죄도시': 1.5,
'아이 캔 스피크': 4.5,
'꾼': 5.0,
'avg': 3.1666666666666665},
'윤계상': {'택시운전사': 3.0,
'남한산성': 2.5,
'킹스맨:골든서클': 1.5,
'범죄도시': 3.0,
'꾼': 3.0,
'아이 캔 스피크': 3.5,
'avg': 3.0277777777777777},
'설경구': {'택시운전사': 2.5,
'남한산성': 3.0,
'범죄도시': 4.5,
'꾼': 4.0,
'avg': 3.1136363636363638},
'최홍만': {'남한산성': 4.5,
'킹스맨:골든서클': 3.0,
'꾼': 4.5,
'범죄도시': 3.0,
'아이 캔 스피크': 2.5,
'avg': 3.185185185185185},
'홍수환': {'택시운전사': 3.0,
'남한산성': 4.0,
'킹스맨:골든서클': 1.0,
'범죄도시': 3.0,
'꾼': 3.5,
'아이 캔 스피크': 2.0,
'avg': 3.106060606060606},
'나원탁': {'택시운전사': 3.0,
'남한산성': 4.0,
'꾼': 3.0,
'범죄도시': 5.0,
'아이 캔 스피크': 3.5,
'avg': 3.1842105263157894},
'소이현': {'남한산성': 4.5,
'아이 캔 스피크': 1.0,
'범죄도시': 4.0,
'avg': 3.182926829268293}}def get_KNNmeans_recommend(data, name, n=3, sim_function=sim_pearson): result = top_match(data, name, n, sim_function) score_dic = dict() sim_dic = dict() li = [] for sim, user in result: print(sim, user) if sim<0: continue for title in data[user]: if title not in data[name]: score = sim * (data[user][title]-data[user]['avg']) score_dic.setdefault(title, 0) score_dic[title] += score sim_dic.setdefault(title, 0) sim_dic[title] += sim for title in score_dic: score_dic[title] = data[name]['avg']+(score_dic[title]/sim_dic[title]) li.append((score_dic[title], title)) # (예측평점, 영화제목) li.sort(reverse=True) print('\n** Recommendation') for rating, score in enumerate(li): print(rating+1, '등: ', score[1], ', ', score[0], '점') return li
get_KNNmeans_recommend(ratings_expand, '소이현')
Out:
...
** Recommendation
1 등: 꾼 , 3.765320026911711 점
2 등: 택시운전사 , 3.0487901210241017 점
3 등: 킹스맨:골든서클 , 1.9561449029750133 점'ML > Recommendation' 카테고리의 다른 글
[Recommendation] Collaborative Filtering : MSD, Cosine, Pearson 유사도 (0) 2020.03.06 [Recommendation] 추천 알고리즘 Python 구현 : Collaborative Filtering w/ 유클리디안 유사도 (0) 2020.03.06 -