推荐系统如何开发

推荐系统实现了基于协同过滤的推荐功能

  1. 支持两种推荐模式:

    • 基于用户的协同过滤(寻找相似用户喜欢的物品)
    • 基于物品的协同过滤(寻找相似物品)
  2. 主要功能:

    • 数据加载(支持自定义数据或内置的 MovieLens 数据集)
    • 模型训练
    • 模型评估(计算 RMSE 和 MAE 指标)
    • 为指定用户生成推荐列表
  3. 使用前需要安装依赖库:

pip install surprise pandas numpy
  1. 可以通过修改sim_options参数来调整相似度计算方法,支持余弦相似度、皮尔逊相关系数等多种方式。

import numpy as np
import pandas as pd
from surprise import Dataset, Reader, KNNBasic
from surprise.model_selection import train_test_split
from surprise import accuracy

class SimpleRecommender:
    def __init__(self, sim_options={'name': 'cosine', 'user_based': True}):
        """
        初始化推荐系统
        :param sim_options: 相似度计算选项,默认为基于用户的余弦相似度
        """
        self.sim_options = sim_options
        self.model = None
        self.trainset = None
        self.testset = None
        
    def load_data(self, data=None, rating_scale=(1, 5)):
        """
        加载数据
        :param data: 包含user_id, item_id, rating的DataFrame
        :param rating_scale: 评分范围
        """
        # 如果没有提供数据,使用内置的movielens-100k数据集
        if data is None:
            self.data = Dataset.load_builtin('ml-100k')
        else:
            # 验证数据格式
            required_columns = ['user_id', 'item_id', 'rating']
            if not set(required_columns).issubset(data.columns):
                raise ValueError("数据必须包含'user_id', 'item_id', 'rating'列")
            
            reader = Reader(rating_scale=rating_scale)
            self.data = Dataset.load_from_df(data[required_columns], reader)
        
        # 分割训练集和测试集
        self.trainset, self.testset = train_test_split(self.data, test_size=0.25)
        
    def train(self):
        """训练推荐模型"""
        self.model = KNNBasic(sim_options=self.sim_options)
        self.model.fit(self.trainset)
        print("模型训练完成!")
        
    def evaluate(self):
        """评估模型性能"""
        if self.model is None:
            raise ValueError("请先训练模型")
            
        predictions = self.model.test(self.testset)
        rmse = accuracy.rmse(predictions)
        mae = accuracy.mae(predictions)
        return rmse, mae
        
    def get_recommendations(self, user_id, n=5):
        """
        为指定用户推荐物品
        :param user_id: 用户ID
        :param n: 推荐物品数量
        :return: 推荐的物品ID列表及预测评分
        """
        if self.model is None:
            raise ValueError("请先训练模型")
            
        # 获取所有物品ID
        all_items = set(self.trainset.all_items())
        
        # 获取用户已评分的物品
        user_items = set([item for (user, item, _) in self.trainset.all_ratings() 
                         if user == self.trainset.to_inner_uid(user_id)])
        
        # 找出用户未评分的物品
        items_to_predict = all_items - user_items
        
        # 预测评分
        predictions = []
        for item in items_to_predict:
            inner_item_id = self.trainset.to_raw_iid(item)
            pred = self.model.predict(user_id, inner_item_id)
            predictions.append((inner_item_id, pred.est))
        
        # 按预测评分排序并返回前n个
        predictions.sort(key=lambda x: x[1], reverse=True)
        return predictions[:n]

# 示例用法
if __name__ == "__main__":
    # 创建推荐系统实例 - 基于用户的协同过滤
    user_based_recommender = SimpleRecommender(
        sim_options={'name': 'cosine', 'user_based': True}
    )
    
    # 加载数据
    print("加载数据中...")
    user_based_recommender.load_data()
    
    # 训练模型
    print("训练模型中...")
    user_based_recommender.train()
    
    # 评估模型
    print("\n评估模型性能:")
    user_based_recommender.evaluate()
    
    # 为用户196推荐5个物品
    user_id = '196'
    print(f"\n为用户 {user_id} 推荐的物品:")
    recommendations = user_based_recommender.get_recommendations(user_id, n=5)
    
    for i, (item_id, rating) in enumerate(recommendations, 1):
        print(f"{i}. 物品ID: {item_id}, 预测评分: {rating:.2f}")
    
    # 也可以创建基于物品的协同过滤推荐系统
    print("\n----- 基于物品的推荐 -----")
    item_based_recommender = SimpleRecommender(
        sim_options={'name': 'pearson_baseline', 'user_based': False}
    )
    item_based_recommender.load_data()
    item_based_recommender.train()
    print(f"为用户 {user_id} 推荐的物品:")
    recommendations = item_based_recommender.get_recommendations(user_id, n=5)
    
    for i, (item_id, rating) in enumerate(recommendations, 1):
        print(f"{i}. 物品ID: {item_id}, 预测评分: {rating:.2f}")
    

 

你可能感兴趣的:(python,人工智能,推荐系统)