问题 如何为所有用户推荐Spark ALS的十大产品?


我们怎样才能在PySpark中获得十大推荐产品。我知道有一些方法,例如recommendedProducts为单个用户推荐产品,而且预测全部用于预测{user,item}对的评级。但是有没有一种有效的方法可以为所有用户输出每个用户的前10项?


1504
2017-07-21 16:30


起源

使用Scala,您可以使用 recommendProductsForUser 但此时此功能未通过PySpark API公开。 - zero323


答案:


我编写了这个函数,它将用户功能和产品功能按分区相乘,以便分发,然后由用户获取每个产品的评级,并通过评级对其进行排序,并输出8个推荐产品的列表。

#Collect product feature matrix
 productFeatures = bestModel.productFeatures().collect() 
 productArray=[]
 productFeaturesArray=[]
 for x in productFeatures:
    productArray.append(x[0])
    productFeaturesArray.append(x[1])  
 matrix=np.matrix(productFeaturesArray)
 productArrayBroadCast=sc.broadcast(productArray)
 productFeaturesArraybroadcast=sc.broadcast(matrix.T)

 def func(iterator):
      userFeaturesArray = []
      userArray = []
      for x in iterator:
          userArray.append(x[0])
          userFeaturesArray.append(x[1])
          userFeatureMatrix = np.matrix(userFeaturesArray)
          userRecommendationArray = userFeatureMatrix*(productFeaturesArraybroadcast.value)
          mappedUserRecommendationArray = []
          #Extract ratings from the matrix
          i=0
          for i in range(0,len(userArray)):
              ratingdict={}
              j=0
              for j in range(0,len(productArrayBroadcast.value)):
                   ratingdict[str(productArrayBroadcast.value[j])]=userRecommendationArray.item((i,j))
                   j=j+1
              #Take the top 8 recommendations for the user
              sort_apps=sorted(ratingdict.keys(), key=lambda x: x[1])[:8]
              sort_apps='|'.join(sort_apps)
              mappedUserRecommendationArray.append((userArray[i],sort_apps))
              i=i+1
      return [x for x in mappedUserRecommendationArray]


recommendations=model.userFeatures().repartition(2000).mapPartitions(func)

5
2017-08-05 21:26





PySpark> = 1.6.0提供 MatrixFactorizationModel.recommendProductsForUsers

>> model.recommendProductsForUsers(3).take(2)
[(1,
  (Rating(user=1, product=2975, rating=0.003626774788608227),
   Rating(user=1, product=1322, rating=0.002494393082165332),
   Rating(user=1, product=8746, rating=0.002176665942528324))),
 (2,
  (Rating(user=2, product=4060, rating=0.011020947406565042),
   Rating(user=2, product=2332, rating=0.009479319983658458),
   Rating(user=2, product=1979, rating=0.004587168057824856)))]

4
2017-07-27 10:55



在隐式评级的情况下 - 用户没有明确评价产品 - 您可能不想过滤掉测试数据。 - hwaxxer
但是用户已经对该项目执行了操作(查看,购买等),我们是否要向他/她推荐? - tokland
我们不能假设必须从结果中删除任何“评级”项目。与项目交互的用户可能是他们喜欢该项目的强烈指示,并且应该向他们推荐,无论他们之前是否已经看过它。与推荐有关的业务逻辑(例如过滤掉某些项目)可能最好在推荐引擎之外完成。其他API让我们这样做,例如 predictAll。 - hwaxxer
好的,我会删除这些注释,不要混淆读者。 - tokland