大数据AI

贪心学院初级机器学习训练营

来源:贪心学院,https://www.zhihu.com/people/tan-xin-xue-yuan/activities

一般情况可以直接用:

pip install numpy ##scikit-surprise需要依赖numpy,如果已经安装则不需要此步pip install scikit-surprise

贪心学院初级机器学习训练营

建议使用anconda的方式安装

conda install -c conda-forge scikit-surprise

镜像源问题

安装过程中很可能镜像源的问题经常出现HTTP请求连不上的问题。

这个时候请更换一下anconda的镜像源:

conda config –add channels https://mirrors.tuna.tsinghua.edu.cn/anaconda/pkgs/free/conda config –set show_channel_urls yes

矩阵分解

矩阵分解 (decomposition, factorization)是将矩阵拆解为数个矩阵的乘积,可分为三角分解、满秩分解、QR分解、Jordan分解和SVD(奇异值)分解等,常见的有三种:

三角分解法 (Triangular Factorization),QR 分解法 (QR Factorization)奇异值分解法 (Singular Value Decomposition)。

Surprise库本身没有提供纯粹的矩阵分解的算法, 在这里我们自己实现了基于Alternating Least Squares的矩阵分解, 使用梯度下降法优化

矩阵分解类MatrixFactorization继承了surprise.AlgoBase, 方便我们使用surpise库提供的其它功能

class MatrixFactorization(surprise.AlgoBase): '''基于矩阵分解的推荐.''' def __init__(self, learning_rate, n_epochs, n_factors, lmd): self.lr = learning_rate # 梯度下降法的学习率 self.n_epochs = n_epochs # 梯度下降法的迭代次数 self.n_factors = n_factors # 分解的矩阵的秩(rank) self.lmd = lmd # 防止过拟合的正则化的强度 def fit(self, trainset): '''通过梯度下降法训练, 得到所有 u_i 和 p_j 的值''' print('Fitting data with SGD…') # 随机初始化 user 和 item 矩阵. u = np.random.normal(0, .1, (trainset.n_users, self.n_factors)) p = np.random.normal(0, .1, (trainset.n_items, self.n_factors)) # 梯度下降法 for _ in range(self.n_epochs): for i, j, r_ij in trainset.all_ratings(): err = r_ij – np.dot(u[i], p[j]) # 利用梯度调整 u_i 和 p_j u[i] -= -self.lr * err * p[j] + self.lr * self.lmd * u[i] p[j] -= -self.lr * err * u[i] + self.lr * self.lmd * p[j] # 注意: 修正 p_j 时, 按照严格定义, 我们应该使用 u_i 修正之前的值, 但是实际上差别微乎其微 self.u, self.p = u, p self.trainset = trainset def estimate(self, i, j): '''预测 user i 对 item j 的评分.''' # 如果用户 i 和物品 j 是已知的值, 返回 u_i 和 p_j 的点积 # 否则使用全局平均评分rating值(cold start 冷启动问题) if self.trainset.knows_user(i) and self.trainset.knows_item(j): return np.dot(self.u[i], self.p[j]) else: return self.trainset.global_mean

解类实现短视频的推荐

from surprise import BaselineOnlyfrom surprise import Datasetfrom surprise import Readerfrom surprise import accuracyfrom surprise.model_selection import cross_validatefrom surprise.model_selection import train_test_splitimport os# 数据文件file_path = os.path.expanduser('./ml-100k/u.data')# 数据文件的格式如下:# 'user item rating timestamp', 使用制表符 '\t' 分割, rating值在1-5之间.reader = Reader(line_format='user item rating timestamp', sep='\t', rating_scale=(1, 5))data = Dataset.load_from_file(file_path, reader=reader)# 将数据随机分为训练和测试数据集trainset, testset = train_test_split(data, test_size=.25)# 初始化以上定义的矩阵分解类.algo = MatrixFactorization(learning_rate=.005, n_epochs=60, n_factors=2, lmd = 0.2)# 训练algo.fit(trainset)# 预测predictions = algo.test(testset)# 计算平均绝对误差accuracy.mae(predictions) # 0.7871327139440717

# 使用 surpise 内建的基于最近邻的方法做比较algo = surprise.KNNBasic()algo.fit(trainset)predictions = algo.test(testset)accuracy.mae(predictions) # 0.7827160139309475

# 使用 surpise 内建的基于 SVD 的方法做比较algo = surprise.SVD()algo.fit(trainset)predictions = algo.test(testset)accuracy.mae(predictions)# 0.7450633876817936

Similar Posts

发表评论

邮箱地址不会被公开。 必填项已用*标注