超级详细的协同过滤推荐系统+完整Python实现及结果

发布时间:2025-01-07 14:25

Python入门书籍推荐:《Python编程:从入门到实践》 #生活知识# #编程教程#

协同过滤推荐系统在我们的日常生活之中无处不在,例如,在电子商城购物,系统会根据用户的记录或者其他的

信息来推荐相应的产品给客户,是一种智能的生活方式。之所以交协同过滤,是因为在实现过滤推荐的时候是根据

其他人的行为来做预测的,基于相似用户的喜好来实现用户的喜好预测。

简要介绍:         

通过找到兴趣相投,或者有共同经验的群体,来向用户推荐感兴趣的信息。

举例,如何协同过滤,来对用户A进行电影推荐?

答:简要步骤如下

找到用户A(user_id_1)的兴趣爱好

找到与用户A(user_id_1)具有相同电影兴趣爱好的用户群体集合Set<user_id>

找到该群体喜欢的电影集合Set<movie_id>

将这些电影Set<Movie_id>推荐给用户A(user_id_1)

具体实施步骤如何?

答:简要步骤如下

(1)画一个大表格,横坐标是所有的movie_id,纵坐标所有的user_id,交叉处代表这个用户喜爱这部电影

Move_id_1

Move_id_2

Move_id_3

Move_id_4

Move_id_5

……

Move_id_110w

User_id_1

1

1

1

User_id_2

1

1

1

1

User_id_3

1

1

1

1

………….

………….

User_id_10w

1

1

1

如上表:

横坐标,假设有10w部电影,所以横坐标有10w个movie_id,数据来源自数据库

纵坐标,假设有100w个用户,所以纵坐标有100w个user_id,数据也来自数据库

交叉处,“1”代表用户喜爱这部电影,数据来自日志

画外音:什么是“喜欢”,需要人为定义,例如浏览过,查找过,点赞过,反正日志里有这些数据

(2)找到用户A(user_id_1)的兴趣爱好

如上表,可以看到,用户A喜欢电影{m1, m2, m3}

(3)找到与用户A(user_id_1)具有相同电影兴趣爱好的用户群体集合Set<user_id>

如上表,可以看到,喜欢{m1, m2, m3}的用户,除了u1,还有{u2, u3}

(4)找到该群体喜欢的电影集合Set<movie_id>

如上表,具备相同喜好的用户群里{u2, u3},还喜好的电影集合是{m4, m5}

画外音:“协同”就体现在这里。

(5)未来用户A(use_id_1)来访问网站时,要推荐电影{m4, m5}给ta。

具体实现步骤:

第一步:计算两者之间的相似度

                       通常会先把二维表格绘制在一个图中总,每个用户数据表示一个点。

                       度量相似度计算的方法:a.曼哈顿距离计算(计算迅速,节省时间)

                                                               b.欧氏距离计算(计算两个点之间的直线距离)

数据预处理:

去网站:https://grouplens.org/datasets/movielens/           下载movieLen数据集

              或者

                      ml-latest-small(1MB): http://files.grouplens.org/datasets/movielens/ml-latest-small.zip
                      ml-latest(234.2MB): http://files.grouplens.org/datasets/movielens/ml-latest.zip

解压读取movies.csv和ratings.csv文件

两个文件的数据格式如下:

通过如下程序提取数据:

"""

@Company:华中科技大学电气学院聚变与等离子研究所

@version: V1.0

@author: YEXIN

@contact: 1650996069@qq.com or yexin@hust.edu.cn 2018--2020

@software: PyCharm

@file: recommend.py

@time: 2018/8/19 17:32

@Desc:读取用户的电影数据和评分数据

"""

import pandas as pd

movies = pd.read_csv("E:\PycharmWorks\ML\CollaborativeFiltering\ml-latest\movies.csv")

ratings = pd.read_csv("E:\PycharmWorks\ML\CollaborativeFiltering\ml-latest\\ratings.csv")

data = pd.merge(movies,ratings,on = 'movieId')

data[['userId','rating','movieId','title']].sort_values('userId').to_csv('E:\PycharmWorks\ML\CollaborativeFiltering\ml-latest\data.csv',index=False)

结果:

采用python字典来表示每位用户评论的电影和评分

"""

@Company:华中科技大学电气学院聚变与等离子研究所

@version: V1.0

@author: YEXIN

@contact: 1650996069@qq.com or yexin@hust.edu.cn 2018--2020

@software: PyCharm

@file: movie_rating_user.py

@time: 2018/8/19 17:50

@Desc:采用python字典来表示每位用户评论的电影和评分

"""

file = open("E:\PycharmWorks\ML\CollaborativeFiltering\ml-latest\data.csv",'r', encoding='UTF-8')

data = {}

for line in file.readlines()[1:100]:

line = line.strip().split(',')

if not line[0] in data.keys():

data[line[0]] = {line[3]:line[1]}

else:

data[line[0]][line[3]] = line[1]

print(data)

结果(部分):

计算任何两位用户之间的相似度,由于每位用户评论的电影不完全一样,所以兽先要找到两位用户共同评论过的电影

然后计算两者之间的欧式距离,最后算出两者之间的相似度。

"""

@Company:华中科技大学电气学院聚变与等离子研究所

@version: V1.0

@author: YEXIN

@contact: 1650996069@qq.com or yexin@hust.edu.cn 2018--2020

@software: PyCharm

@file: movie_rating_user.py

@time: 2018/8/19 17:50

@Desc:采用python字典来表示每位用户评论的电影和评分

"""

file = open("E:\PycharmWorks\ML\CollaborativeFiltering\ml-latest\data.csv",'r', encoding='UTF-8')

data = {}

for line in file.readlines()[1:100]:

line = line.strip().split(',')

if not line[0] in data.keys():

data[line[0]] = {line[3]:line[1]}

else:

data[line[0]][line[3]] = line[1]

"""计算任何两位用户之间的相似度,由于每位用户评论的电影不完全一样,所以兽先要找到两位用户共同评论过的电影

然后计算两者之间的欧式距离,最后算出两者之间的相似度

"""

from math import *

def Euclidean(user1,user2):

user1_data=data[user1]

user2_data=data[user2]

distance = 0

for key in user1_data.keys():

if key in user2_data.keys():

distance += pow(float(user1_data[key])-float(user2_data[key]),2)

return 1/(1+sqrt(distance))

def top10_simliar(userID):

res = []

for userid in data.keys():

if not userid == userID:

simliar = Euclidean(userID,userid)

res.append((userid,simliar))

res.sort(key=lambda val:val[1])

return res[:4]

RES = top10_simliar('1')

print(RES)

用户之间相似度结果:0表示两位的影评几乎一样,1表示没有共同的影评

根据相似度来推荐用户:

def recommend(user):

top_sim_user = top10_simliar(user)[0][0]

items = data[top_sim_user]

recommendations = []

for item in items.keys():

if item not in data[user].keys():

recommendations.append((item,items[item]))

recommendations.sort(key=lambda val:val[1],reverse=True)

return recommendations[:10]

Recommendations = recommend('1')

print(Recommendations)

推荐结果:

==================================================================================

但有时我们会碰到因为两个用户之间数据由于数据膨胀,一方数据大,一方数据小,但是两者称明显的线性关系

我们引入Pearson相关系数来衡量两个变量之间的线性相关性。

Pearson:-1~1   -1:完全负相关  1:完全正相关  0:不相关              

相关系数 0.8-1.0 极强相关

0.6-0.8 强相关

0.4-0.6 中等程度相关

0.2-0.4 弱相关

0.0-0.2 极弱相关或无相关

公式:

python代码:

def pearson_sim(user1,user2):

user1_data = data[user1]

user2_data = data[user2]

distance = 0

common = {}

for key in user1_data.keys():

if key in user2_data.keys():

common[key] = 1

if len(common) == 0:

return 0

n = len(common)

print(n,common)

sum1 = sum([float(user1_data[movie]) for movie in common])

sum2 = sum([float(user2_data[movie]) for movie in common])

sum1Sq = sum([pow(float(user1_data[movie]),2) for movie in common])

sum2Sq = sum([pow(float(user2_data[movie]),2) for movie in common])

PSum = sum([float(user1_data[it])*float(user2_data[it]) for it in common])

num = PSum - (sum1*sum2/n)

den = sqrt((sum1Sq-pow(sum1,2)/n)*(sum2Sq-pow(sum2,2)/n))

if den == 0:

return 0

r = num/den

return r

R = pearson_sim('1','3')

print(R)

pearson系数结果:

注意:通过Pearson系数得到用户的相似度和通过欧式距离得到结果可能不一样

网址:超级详细的协同过滤推荐系统+完整Python实现及结果 https://www.yuejiaxmz.com/news/view/663331

相关内容

python毕设 基于协同过滤算法的居民健康生活引导系统的设计与实现程序+论文
基于协同过滤的校内餐厅推荐系统设计与实现(源码+论文)
基于协同过滤算法的美食推荐系统研究与实现
Python推荐系统实战:构建个性化推荐系统
推荐系统的个性化推荐:如何实现用户特征的精细化
Python实现个性化美食推荐系统:从算法到实战全解析
教育推荐系统的设计与实现
探索美食新世界:基于Python的美食推荐系统
springboot毕设基于协同过滤的个性化旅游推荐系统论文+程序+部署
个性化推荐系统中协同过滤方法的研究

随便看看