R实现MapReduce的协同过滤算法

算法篇--协同过滤 文章目录一、长尾理论二、协同过滤介绍1.基于用户的协同过滤算法(User-based CF,简称UserCF) 一、长尾理论 wiki链接:https://wiki.mbalib.com/wiki/%E9%95%BF%E5%B0%BE%E7%90%86%E8%AE%BA   长尾头部的商品往往代表了绝大多数用户的需求而长尾中的商品往往代表了一小部分用户的个性化需求。因此如果要通过发掘长尾来提高销售额就必须充分研究用户的个性化兴趣。而这正是个性化推荐系统主要解决的问题。   推荐系统通过发掘用户的行为找到用户 阅读详情

由于rmr2的对hadoop操作有一些特殊性,代码实现有一定难度。需要深入学习的同学,请多尝试并思考key/value值的设计。

本文难度为中高级。

第三篇 R实现MapReduce的协同过滤算法,分为3个章节。

1.基于物品推荐的协同过滤算法介绍
2.R本地程序实现
3.R基于Hadoop分步式程序实现

每一章节,都会分为”文字说明部分”和”代码部分”,保持文字说明与代码的连贯性。

注:Hadoop环境及RHadoop的环境,请查看同系列前二篇文章,此文将不再介绍。

1. 基于物品推荐的协同过滤算法介绍

文字说明部分:

越来越多的互联网应用,都开始使用推荐算法(协同过滤算法)。根据用户活跃度和物品流行度,可以分为”基于用户的协同过滤算法”和”基于物品的协同过滤算法”。

基于用户的协同过滤算法,是给用户推荐和他兴趣相似的其他用户喜欢的物品。
基于物品的协同过滤算法,是给用户推荐和他之前喜欢的物品相似的物品。
基于物品的协同过滤算法,是目前广泛使用的一种推荐算法,像Netflix, YouTube, Amazon等。

算法主要分为两步:
1. 计算物品之间的相似度
2. 根据物品的相似度和用户的历史行为给用户生成推荐列表

有关算法的细节请参考:”Mahout In Action”和”推荐系统实践”两本书。

为开发方便,我们选择一组很小的测试数据集。

测试数据,来自于”Mahout In Action” P49
原第8行,3,101,2.5 改为 3,101,2.0
每行3个字段,依次是用户ID,物品ID,对物品的评分

代码部分:

在服务上创建测试数据文件small.csv

~ pwd

/root/R

~ vi small.csv

1,101,5.0
1,102,3.0
1,103,2.5
2,101,2.0
2,102,2.5
2,103,5.0
2,104,2.0
3,101,2.0
3,104,4.0
3,105,4.5
3,107,5.0
4,101,5.0
4,103,3.0
4,104,4.5
4,106,4.0
5,101,4.0
5,102,3.0
5,103,2.0
5,104,4.0
5,105,3.5
5,106,4.0

~ ls

small.csv

2. R本地程序实现

首先,通过R语言实现基于物品的协同过滤算法,为和RHadoop实现进行对比。这里我使用”Mahout In Action”书里,第一章第六节介绍的分步式基于物品的协同过滤算法进行实现。Chapter 6: Distributing recommendation computations

算法的思想:
1. 建立物品的同现矩阵
2. 建立用户对物品的评分矩阵
3. 矩阵计算推荐结果

文字说明部分:

1. 建立物品的同现矩阵

按用户分组,找到每个用户所选的物品,单独出现计数,及两两一组计数。

例如:用户ID为3的用户,分别给101,104,105,107,这4个物品打分。
1) (101,101),(104,104),(105,105),(107,107),单独出现计算各加1。
2) (101,104),(101,105),(101,107),(104,105),(104,107),(105,107),两个一组计数各加1。
3) 把所有用户的计算结果求和,生成一个三角矩阵,再补全三角矩阵,就建立了物品的同现矩阵。

如下面矩阵所示:


      [101] [102] [103] [104] [105] [106] [107]
[101]   5     3     4     4     2     2     1
[102]   3     3     3     2     1     1     0
[103]   4     3     4     3     1     2     0
[104]   4     2     3     4     2     2     1
[105]   2     1     1     2     2     1     1
[106]   2     1     2     2     1     2     0
[107]   1     0     0     1     1     0     1

2. 建立用户对物品的评分矩阵

按用户分组,找到每个用户所选的物品及评分

例如:用户ID为3的用户,分别给(3,101,2.0),(3,104,4.0),(3,105,4.5),(3,107,5.0),这4个物品打分。
1) 找到物品评分(3,101,2.0),(3,104,4.0),(3,105,4.5),(3,107,5.0)
2) 建立用户对物品的评分矩阵


       U3
[101] 2.0
[102] 0.0
[103] 0.0
[104] 4.0
[105] 4.5
[106] 0.0
[107] 5.0

3. 矩阵计算推荐结果

同现矩阵*评分矩阵=推荐结果

alogrithm_1

图片摘自”Mahout In Action”

推荐给用户ID为3的用户的结果是(103,24.5),(102,18.5),(106,16.5)

代码部分:


#引用plyr包
library(plyr)

#读取数据集
train<-read.csv(file="small.csv",header=FALSE)
names(train)<-c("user","item","pref") 

> train
  user item pref
1 1 101 5.0
2 1 102 3.0
3 1 103 2.5
4 2 101 2.0
5 2 102 2.5
6 2 103 5.0
7 2 104 2.0
8 3 101 2.0
9 3 104 4.0
10 3 105 4.5
11 3 107 5.0
12 4 101 5.0
13 4 103 3.0
14 4 104 4.5
15 4 106 4.0
16 5 101 4.0
17 5 102 3.0
18 5 103 2.0
19 5 104 4.0
20 5 105 3.5
21 5 106 4.0

#计算用户列表
usersUnique<-function(){
  users<-unique(train$user)
  users[order(users)]
}

#计算商品列表方法
itemsUnique<-function(){
  items<-unique(train$item)
  items[order(items)]
}

# 用户列表
users<-usersUnique() 
> users
[1] 1 2 3 4 5

# 商品列表
items<-itemsUnique() 
> items
[1] 101 102 103 104 105 106 107

#建立商品列表索引
index<-function(x) which(items %in% x)
data<-ddply(train,.(user,item,pref),summarize,idx=index(item)) 

> data
 user item pref idx
1 1 101 5.0 1
2 1 102 3.0 2
3 1 103 2.5 3
4 2 101 2.0 1
5 2 102 2.5 2
6 2 103 5.0 3
7 2 104 2.0 4
8 3 101 2.0 1
9 3 104 4.0 4
10 3 105 4.5 5
11 3 107 5.0 7
12 4 101 5.0 1
13 4 103 3.0 3
14 4 104 4.5 4
15 4 106 4.0 6
16 5 101 4.0 1
17 5 102 3.0 2
18 5 103 2.0 3
19 5 104 4.0 4
20 5 105 3.5 5
21 5 106 4.0 6

#同现矩阵
cooccurrence<-function(data){
  n<-length(items)
  co<-matrix(rep(0,n*n),nrow=n)
  for(u in users){
    idx<-index(data$item[which(data$user==u)])
    m<-merge(idx,idx)
    for(i in 1:nrow(m)){
      co[m$x[i],m$y[i]]=co[m$x[i],m$y[i]]+1
    }
  }
  return(co)
}

#推荐算法
recommend<-function(udata=udata,co=coMatrix,num=0){
  n<-length(items)

  # all of pref
  pref<-rep(0,n)
  pref[udata$idx]<-udata$pref

  # 用户评分矩阵
  userx<-matrix(pref,nrow=n)

  # 同现矩阵*评分矩阵
  r<-co %*% userx

  # 推荐结果排序
   r[udata$idx]<-0
  idx<-order(r,decreasing=TRUE)
  topn<-data.frame(user=rep(udata$user[1],length(idx)),item=items[idx],val=r[idx])
  topn<-topn[which(topn$val>0),]

  # 推荐结果取前num个
  if(num>0){
    topn<-head(topn,num)
  }

  #返回结果
  return(topn)
}

#生成同现矩阵
co<-cooccurrence(data) 
> co
    [,1] [,2] [,3] [,4] [,5] [,6] [,7]
[1,]  5    3    4    4    2    2    1
[2,]  3    3    3    2    1    1    0
[3,]  4    3    4    3    1    2    0
[4,]  4    2    3    4    2    2    1
[5,]  2    1    1    2    2    1    1
[6,]  2    1    2    2    1    2    0
[7,]  1    0    0    1    1    0    1

#计算推荐结果
recommendation<-data.frame()
for(i in 1:length(users)){
  udata<-data[which(data$user==users[i]),]
  recommendation<-rbind(recommendation,recommend(udata,co,0)) 
} 

> recommendation
  user item val
1 1 104 33.5
2 1 106 18.0
3 1 105 15.5
4 1 107 5.0
5 2 106 20.5
6 2 105 15.5
7 2 107 4.0
8 3 103 24.5
9 3 102 18.5
10 3 106 16.5
11 4 102 37.0
12 4 105 26.0
13 4 107 9.5
14 5 107 11.5

3. R基于Hadoop分步式程序实现

R语言实现的MapReduce算法,可以基于R的数据对象实现,不必如JAVA一样使用文本存储。

算法思想同上面R语言实现思想,略有复杂。

算法的思想:
1. 建立物品的同现矩阵
1) 按用户分组,得到所有物品出现的组合列表。
2) 对物品组合列表进行计数,建立物品的同现矩阵
2. 建立用户对物品的评分矩阵
3. 合并同现矩阵和评分矩阵
4. 计算推荐结果列表
5. 按输入格式得到推荐评分列表

通过MapReduce实现时,所有操作都要使用Map和Reduce的任务完成,程序实现过程略有变化。

aglorithm_2

图片摘自”Mahout In Action”

文字说明部分:

1. 建立物品的同现矩阵

1) 按用户分组,得到所有物品出现的组合列表。

key:物品列表向量
val:物品组合向量


$key
[1] 101 101 101 101 101 101 101 101 101 101 101 101 101 101 101 102 102 102 102
[20] 102 102 102 103 103 103 103 103 103 103 103 103 103 103 104 104 104 104 104
[39] 104 104 104 104 104 104 104 105 105 105 105 106 106 106 106 107 107 107 107
[58] 101 101 101 101 101 101 102 102 102 102 102 102 103 103 103 103 103 103 104
[77] 104 104 104 104 104 105 105 105 105 105 105 106 106 106 106 106 106

$val
[1] 101 102 103 101 102 103 104 101 104 105 107 101 103 104 106 101 102 103 101
[20] 102 103 104 101 102 103 101 102 103 104 101 103 104 106 101 102 103 104 101
[39] 104 105 107 101 103 104 106 101 104 105 107 101 103 104 106 101 104 105 107
[58] 101 102 103 104 105 106 101 102 103 104 105 106 101 102 103 104 105 106 101
[77] 102 103 104 105 106 101 102 103 104 105 106 101 102 103 104 105 106

2) 对物品组合列表进行计数,建立物品的同现矩阵

key:物品列表向量
val:同现矩阵的数据框值(item,item,Freq)
矩阵格式,要与”2. 建立用户对物品的评分矩阵”的格式一致,把异构的两种数据源,合并为同一种数据格式,为”3. 合并 同现矩阵 和 评分矩阵”做数据基础。


$key
[1] 101 101 101 101 101 101 101 102 102 102 102 102 102 103 103 103 103 103 103
[20] 104 104 104 104 104 104 104 105 105 105 105 105 105 105 106 106 106 106 106
[39] 106 107 107 107 107

$val
k v freq
1 101 101 5
2 101 102 3
3 101 103 4
4 101 104 4
5 101 105 2
6 101 106 2
7 101 107 1
8 102 101 3
9 102 102 3
10 102 103 3
11 102 104 2
12 102 105 1
13 102 106 1
14 103 101 4
15 103 102 3
16 103 103 4
17 103 104 3
18 103 105 1
19 103 106 2
20 104 101 4
21 104 102 2
22 104 103 3
23 104 104 4
24 104 105 2
25 104 106 2
26 104 107 1
27 105 101 2
28 105 102 1
29 105 103 1
30 105 104 2
31 105 105 2
32 105 106 1
33 105 107 1
34 106 101 2
35 106 102 1
36 106 103 2
37 106 104 2
38 106 105 1
39 106 106 2
40 107 101 1
41 107 104 1
42 107 105 1
43 107 107 1

2. 建立用户对物品的评分矩阵

key:物品列表
val:用户对物品打分矩阵
矩阵格式,要与”2) 对物品组合列表进行计数,建立物品的同现矩阵”的格式一致,把异构的两种数据源,合并为同一种数据格式,为”3. 合并 同现矩阵 和 评分矩阵”做数据基础


$key
[1] 101 101 101 101 101 102 102 102 103 103 103 103 104 104 104 104 105 105 106
[20] 106 107

$val
item user pref
1 101 1 5.0
2 101 2 2.0
3 101 3 2.0
4 101 4 5.0
5 101 5 4.0
6 102 1 3.0
7 102 2 2.5
8 102 5 3.0
9 103 1 2.5
10 103 2 5.0
11 103 4 3.0
12 103 5 2.0
13 104 2 2.0
14 104 3 4.0
15 104 4 4.5
16 104 5 4.0
17 105 3 4.5
18 105 5 3.5
19 106 4 4.0
20 106 5 4.0
21 107 3 5.0

3. 合并 同现矩阵 和 评分矩阵

这一步操作是MapReduce比较特殊的,因为数据源是两个异构数据源,进行MapReduce的操作。
在之前,我们已经把两种格式合并为一样的。使用equijoin这个rmr2包的函数,进行矩阵合并。
key:NULL
val:合并的数据框


$key
NULL

$val
k.l v.l freq.l item.r user.r pref.r
1 103 101 4 103 1 2.5
2 103 102 3 103 1 2.5
3 103 103 4 103 1 2.5
4 103 104 3 103 1 2.5
5 103 105 1 103 1 2.5
6 103 106 2 103 1 2.5
7 103 101 4 103 2 5.0
8 103 102 3 103 2 5.0
9 103 103 4 103 2 5.0
10 103 104 3 103 2 5.0
11 103 105 1 103 2 5.0
12 103 106 2 103 2 5.0
13 103 101 4 103 4 3.0
....

4. 计算推荐结果列表

把第三步中的矩阵,进行合并计算,得到推荐结果列表
key:物品列表
val:推荐结果数据框


$key
[1] 101 101 101 101 101 101 101 101 101 101 101 101 101 101 101 101 101 101
[19] 101 101 101 101 101 101 101 101 101 101 101 101 101 101 101 101 101 102
[37] 102 102 102 102 102 102 102 102 102 102 102 102 102 102 102 102 102 103
[55] 103 103 103 103 103 103 103 103 103 103 103 103 103 103 103 103 103 103
[73] 103 103 103 103 103 104 104 104 104 104 104 104 104 104 104 104 104 104
[91] 104 104 104 104 104 104 104 104 104 104 104 104 104 104 104 105 105 105
[109] 105 105 105 105 105 105 105 105 105 105 105 106 106 106 106 106 106 106
[127] 106 106 106 106 106 107 107 107 107

$val
k.l v.l user.r v
1 101 101 1 25.0
2 101 101 2 10.0
3 101 101 3 10.0
4 101 101 4 25.0
5 101 101 5 20.0
6 101 102 1 15.0
7 101 102 2 6.0
8 101 102 3 6.0
9 101 102 4 15.0
10 101 102 5 12.0
11 101 103 1 20.0
12 101 103 2 8.0
13 101 103 3 8.0
14 101 103 4 20.0
15 101 103 5 16.0
16 101 104 1 20.0
17 101 104 2 8.0
18 101 104 3 8.0
....

5. 按输入格式得到推荐评分列表

对推荐结果列表,进行排序处理,输出排序后的推荐结果。
key:用户ID
val:推荐结果数据框


$key
[1] 1 1 1 1 1 1 1 2 2 2 2 2 2 2 3 3 3 3 3 3 3 4 4 4 4 4 4 4 5 5 5 5 5 5 5

$val
user item pref
1 1 101 44.0
2 1 103 39.0
3 1 104 33.5
4 1 102 31.5
5 1 106 18.0
6 1 105 15.5
7 1 107 5.0
8 2 101 45.5
9 2 103 41.5
10 2 104 36.0
11 2 102 32.5
12 2 106 20.5
13 2 105 15.5
14 2 107 4.0
15 3 101 40.0
16 3 104 38.0
17 3 105 26.0
18 3 103 24.5
19 3 102 18.5
20 3 106 16.5
21 3 107 15.5
22 4 101 63.0
23 4 104 55.0
24 4 103 53.5
25 4 102 37.0
26 4 106 33.0
27 4 105 26.0
28 4 107 9.5
29 5 101 68.0
30 5 104 59.0
31 5 103 56.5
32 5 102 42.5
33 5 106 34.5
34 5 105 32.0
35 5 107 11.5

rmr2使用提示:

1) rmr.options(backend = ‘hadoop’)

这里backend有两个值,hadoop,local。hadoop是默认值,使用hadoop环境运行程序。local是一个本地测试的设置,已经不建议再使用。我在开发时,试过local设置,运行速度非常快,模拟了hadoop的运行环境。但是,local模式下的代码,不能和hadoop模式下完全兼容,变动也比较大,因此不建议大家使用。

2) equijoin(…,outer=c(‘left’))

这里outer包括了4个值,c(“”, “left”, “right”, “full”),非常像数据库中两个表的join操作

3) keyval(k,v)

mapReduce的操作,需要key和valve保存数据。如果直接输出,或者输出的未加key,会有一个警告Converting to.dfs argument to keyval with a NULL key。再上一篇文章中,rmr2的例子中就有类似的情况,请大家注意修改代码。


> to.dfs(1:10)

Warning message:
In to.dfs(1:10) : Converting to.dfs argument to keyval with a NULL key
代码部分:
#加载rmr2包
library(rmr2)

#输入数据文件
train<-read.csv(file="small.csv",header=FALSE)
names(train)<-c("user","item","pref")

#使用rmr的hadoop格式,hadoop是默认设置。
rmr.options(backend = 'hadoop')

#把数据集存入HDFS
train.hdfs = to.dfs(keyval(train$user,train))
from.dfs(train.hdfs)

> from.dfs(train.hdfs)

    13/04/07 14:35:44 INFO util.NativeCodeLoader: Loaded the native-hadoop library
    13/04/07 14:35:44 INFO zlib.ZlibFactory: Successfully loaded & initialized native-zlib library
    13/04/07 14:35:44 INFO compress.CodecPool: Got brand-new decompressor
    $key
     [1] 1 1 1 2 2 2 2 3 3 3 3 4 4 4 4 5 5 5 5 5 5

    $val
       user item pref
    1     1  101  5.0
    2     1  102  3.0
    3     1  103  2.5
    4     2  101  2.0
    5     2  102  2.5
    6     2  103  5.0
    7     2  104  2.0
    8     3  101  2.0
    9     3  104  4.0
    10    3  105  4.5
    11    3  107  5.0
    12    4  101  5.0
    13    4  103  3.0
    14    4  104  4.5
    15    4  106  4.0
    16    5  101  4.0
    17    5  102  3.0
    18    5  103  2.0
    19    5  104  4.0
    20    5  105  3.5
    21    5  106  4.0

#STEP 1, 建立物品的同现矩阵
# 1) 按用户分组,得到所有物品出现的组合列表。
train.mr<-mapreduce(
  train.hdfs, 
  map = function(k, v) {
    keyval(k,v$item)
  }
  ,reduce=function(k,v){
    m<-merge(v,v)
    keyval(m$x,m$y)
  }
)

from.dfs(train.mr)

    $key
     [1] 101 101 101 101 101 101 101 101 101 101 101 101 101 101 101 102 102 102 102
    [20] 102 102 102 103 103 103 103 103 103 103 103 103 103 103 104 104 104 104 104
    [39] 104 104 104 104 104 104 104 105 105 105 105 106 106 106 106 107 107 107 107
    [58] 101 101 101 101 101 101 102 102 102 102 102 102 103 103 103 103 103 103 104
    [77] 104 104 104 104 104 105 105 105 105 105 105 106 106 106 106 106 106

    $val
     [1] 101 102 103 101 102 103 104 101 104 105 107 101 103 104 106 101 102 103 101
    [20] 102 103 104 101 102 103 101 102 103 104 101 103 104 106 101 102 103 104 101
    [39] 104 105 107 101 103 104 106 101 104 105 107 101 103 104 106 101 104 105 107
    [58] 101 102 103 104 105 106 101 102 103 104 105 106 101 102 103 104 105 106 101
    [77] 102 103 104 105 106 101 102 103 104 105 106 101 102 103 104 105 106

# 2) 对物品组合列表进行计数,建立物品的同现矩阵
step2.mr<-mapreduce(
  train.mr,
  map = function(k, v) {
    d<-data.frame(k,v)
    d2<-ddply(d,.(k,v),count)

    key<-d2$k
    val<-d2
    keyval(key,val)
  }
)
from.dfs(step2.mr)

    $key
     [1] 101 101 101 101 101 101 101 102 102 102 102 102 102 103 103 103 103 103 103
    [20] 104 104 104 104 104 104 104 105 105 105 105 105 105 105 106 106 106 106 106
    [39] 106 107 107 107 107

    $val
         k   v freq
    1  101 101    5
    2  101 102    3
    3  101 103    4
    4  101 104    4
    5  101 105    2
    6  101 106    2
    7  101 107    1
    8  102 101    3
    9  102 102    3
    10 102 103    3
    11 102 104    2
    12 102 105    1
    13 102 106    1
    14 103 101    4
    15 103 102    3
    16 103 103    4
    17 103 104    3
    18 103 105    1
    19 103 106    2
    20 104 101    4
    21 104 102    2
    22 104 103    3
    23 104 104    4
    24 104 105    2
    25 104 106    2
    26 104 107    1
    27 105 101    2
    28 105 102    1
    29 105 103    1
    30 105 104    2
    31 105 105    2
    32 105 106    1
    33 105 107    1
    34 106 101    2
    35 106 102    1
    36 106 103    2
    37 106 104    2
    38 106 105    1
    39 106 106    2
    40 107 101    1
    41 107 104    1
    42 107 105    1
    43 107 107    1    

# 2. 建立用户对物品的评分矩阵

train2.mr<-mapreduce(
  train.hdfs, 
  map = function(k, v) {
    #df<-v[which(v$user==3),]
    df<-v
    key<-df$item
    val<-data.frame(item=df$item,user=df$user,pref=df$pref)
    keyval(key,val)
  }
)
from.dfs(train2.mr)

    $key
     [1] 101 101 101 101 101 102 102 102 103 103 103 103 104 104 104 104 105 105 106
    [20] 106 107

    $val
       item user pref
    1   101    1  5.0
    2   101    2  2.0
    3   101    3  2.0
    4   101    4  5.0
    5   101    5  4.0
    6   102    1  3.0
    7   102    2  2.5
    8   102    5  3.0
    9   103    1  2.5
    10  103    2  5.0
    11  103    4  3.0
    12  103    5  2.0
    13  104    2  2.0
    14  104    3  4.0
    15  104    4  4.5
    16  104    5  4.0
    17  105    3  4.5
    18  105    5  3.5
    19  106    4  4.0
    20  106    5  4.0
    21  107    3  5.0

#3. 合并同现矩阵 和 评分矩阵
eq.hdfs<-equijoin(
  left.input=step2.mr, 
  right.input=train2.mr,
  map.left=function(k,v){
    keyval(k,v)
  },
  map.right=function(k,v){
    keyval(k,v)
  },
  outer = c("left")
)
from.dfs(eq.hdfs)

    $key
    NULL

    $val
        k.l v.l freq.l item.r user.r pref.r
    1   103 101      4    103      1    2.5
    2   103 102      3    103      1    2.5
    3   103 103      4    103      1    2.5
    4   103 104      3    103      1    2.5
    5   103 105      1    103      1    2.5
    6   103 106      2    103      1    2.5
    7   103 101      4    103      2    5.0
    8   103 102      3    103      2    5.0
    9   103 103      4    103      2    5.0
    10  103 104      3    103      2    5.0
    11  103 105      1    103      2    5.0
    12  103 106      2    103      2    5.0
    13  103 101      4    103      4    3.0
    14  103 102      3    103      4    3.0
    15  103 103      4    103      4    3.0
    16  103 104      3    103      4    3.0
    17  103 105      1    103      4    3.0
    18  103 106      2    103      4    3.0
    19  103 101      4    103      5    2.0
    20  103 102      3    103      5    2.0
    21  103 103      4    103      5    2.0
    22  103 104      3    103      5    2.0
    23  103 105      1    103      5    2.0
    24  103 106      2    103      5    2.0
    25  101 101      5    101      1    5.0
    26  101 102      3    101      1    5.0
    27  101 103      4    101      1    5.0
    28  101 104      4    101      1    5.0
    29  101 105      2    101      1    5.0
    30  101 106      2    101      1    5.0
    31  101 107      1    101      1    5.0
    32  101 101      5    101      2    2.0
    33  101 102      3    101      2    2.0
    34  101 103      4    101      2    2.0
    35  101 104      4    101      2    2.0
    36  101 105      2    101      2    2.0
    37  101 106      2    101      2    2.0
    38  101 107      1    101      2    2.0
    39  101 101      5    101      3    2.0
    40  101 102      3    101      3    2.0
    41  101 103      4    101      3    2.0
    42  101 104      4    101      3    2.0
    43  101 105      2    101      3    2.0
    44  101 106      2    101      3    2.0
    45  101 107      1    101      3    2.0
    46  101 101      5    101      4    5.0
    47  101 102      3    101      4    5.0
    48  101 103      4    101      4    5.0
    49  101 104      4    101      4    5.0
    50  101 105      2    101      4    5.0
    51  101 106      2    101      4    5.0
    52  101 107      1    101      4    5.0
    53  101 101      5    101      5    4.0
    54  101 102      3    101      5    4.0
    55  101 103      4    101      5    4.0
    56  101 104      4    101      5    4.0
    57  101 105      2    101      5    4.0
    58  101 106      2    101      5    4.0
    59  101 107      1    101      5    4.0
    60  105 101      2    105      3    4.5
    61  105 102      1    105      3    4.5
    62  105 103      1    105      3    4.5
    63  105 104      2    105      3    4.5
    64  105 105      2    105      3    4.5
    65  105 106      1    105      3    4.5
    66  105 107      1    105      3    4.5
    67  105 101      2    105      5    3.5
    68  105 102      1    105      5    3.5
    69  105 103      1    105      5    3.5
    70  105 104      2    105      5    3.5
    71  105 105      2    105      5    3.5
    72  105 106      1    105      5    3.5
    73  105 107      1    105      5    3.5
    74  106 101      2    106      4    4.0
    75  106 102      1    106      4    4.0
    76  106 103      2    106      4    4.0
    77  106 104      2    106      4    4.0
    78  106 105      1    106      4    4.0
    79  106 106      2    106      4    4.0
    80  106 101      2    106      5    4.0
    81  106 102      1    106      5    4.0
    82  106 103      2    106      5    4.0
    83  106 104      2    106      5    4.0
    84  106 105      1    106      5    4.0
    85  106 106      2    106      5    4.0
    86  104 101      4    104      2    2.0
    87  104 102      2    104      2    2.0
    88  104 103      3    104      2    2.0
    89  104 104      4    104      2    2.0
    90  104 105      2    104      2    2.0
    91  104 106      2    104      2    2.0
    92  104 107      1    104      2    2.0
    93  104 101      4    104      3    4.0
    94  104 102      2    104      3    4.0
    95  104 103      3    104      3    4.0
    96  104 104      4    104      3    4.0
    97  104 105      2    104      3    4.0
    98  104 106      2    104      3    4.0
    99  104 107      1    104      3    4.0
    100 104 101      4    104      4    4.5
    101 104 102      2    104      4    4.5
    102 104 103      3    104      4    4.5
    103 104 104      4    104      4    4.5
    104 104 105      2    104      4    4.5
    105 104 106      2    104      4    4.5
    106 104 107      1    104      4    4.5
    107 104 101      4    104      5    4.0
    108 104 102      2    104      5    4.0
    109 104 103      3    104      5    4.0
    110 104 104      4    104      5    4.0
    111 104 105      2    104      5    4.0
    112 104 106      2    104      5    4.0
    113 104 107      1    104      5    4.0
    114 102 101      3    102      1    3.0
    115 102 102      3    102      1    3.0
    116 102 103      3    102      1    3.0
    117 102 104      2    102      1    3.0
    118 102 105      1    102      1    3.0
    119 102 106      1    102      1    3.0
    120 102 101      3    102      2    2.5
    121 102 102      3    102      2    2.5
    122 102 103      3    102      2    2.5
    123 102 104      2    102      2    2.5
    124 102 105      1    102      2    2.5
    125 102 106      1    102      2    2.5
    126 102 101      3    102      5    3.0
    127 102 102      3    102      5    3.0
    128 102 103      3    102      5    3.0
    129 102 104      2    102      5    3.0
    130 102 105      1    102      5    3.0
    131 102 106      1    102      5    3.0
    132 107 101      1    107      3    5.0
    133 107 104      1    107      3    5.0
    134 107 105      1    107      3    5.0
    135 107 107      1    107      3    5.0

#4. 计算推荐结果列表
cal.mr<-mapreduce(
  input=eq.hdfs,
  map=function(k,v){
    val<-v
    na<-is.na(v$user.r)
    if(length(which(na))>0) val<-v[-which(is.na(v$user.r)),]
    keyval(val$k.l,val)
  }
  ,reduce=function(k,v){
    val<-ddply(v,.(k.l,v.l,user.r),summarize,v=freq.l*pref.r)
    keyval(val$k.l,val)
  }
)
from.dfs(cal.mr)

    $key
      [1] 101 101 101 101 101 101 101 101 101 101 101 101 101 101 101 101 101 101
     [19] 101 101 101 101 101 101 101 101 101 101 101 101 101 101 101 101 101 102
     [37] 102 102 102 102 102 102 102 102 102 102 102 102 102 102 102 102 102 103
     [55] 103 103 103 103 103 103 103 103 103 103 103 103 103 103 103 103 103 103
     [73] 103 103 103 103 103 104 104 104 104 104 104 104 104 104 104 104 104 104
     [91] 104 104 104 104 104 104 104 104 104 104 104 104 104 104 104 105 105 105
    [109] 105 105 105 105 105 105 105 105 105 105 105 106 106 106 106 106 106 106
    [127] 106 106 106 106 106 107 107 107 107

    $val
        k.l v.l user.r    v
    1   101 101      1 25.0
    2   101 101      2 10.0
    3   101 101      3 10.0
    4   101 101      4 25.0
    5   101 101      5 20.0
    6   101 102      1 15.0
    7   101 102      2  6.0
    8   101 102      3  6.0
    9   101 102      4 15.0
    10  101 102      5 12.0
    11  101 103      1 20.0
    12  101 103      2  8.0
    13  101 103      3  8.0
    14  101 103      4 20.0
    15  101 103      5 16.0
    16  101 104      1 20.0
    17  101 104      2  8.0
    18  101 104      3  8.0
    19  101 104      4 20.0
    20  101 104      5 16.0
    21  101 105      1 10.0
    22  101 105      2  4.0
    23  101 105      3  4.0
    24  101 105      4 10.0
    25  101 105      5  8.0
    26  101 106      1 10.0
    27  101 106      2  4.0
    28  101 106      3  4.0
    29  101 106      4 10.0
    30  101 106      5  8.0
    31  101 107      1  5.0
    32  101 107      2  2.0
    33  101 107      3  2.0
    34  101 107      4  5.0
    35  101 107      5  4.0
    36  102 101      1  9.0
    37  102 101      2  7.5
    38  102 101      5  9.0
    39  102 102      1  9.0
    40  102 102      2  7.5
    41  102 102      5  9.0
    42  102 103      1  9.0
    43  102 103      2  7.5
    44  102 103      5  9.0
    45  102 104      1  6.0
    46  102 104      2  5.0
    47  102 104      5  6.0
    48  102 105      1  3.0
    49  102 105      2  2.5
    50  102 105      5  3.0
    51  102 106      1  3.0
    52  102 106      2  2.5
    53  102 106      5  3.0
    54  103 101      1 10.0
    55  103 101      2 20.0
    56  103 101      4 12.0
    57  103 101      5  8.0
    58  103 102      1  7.5
    59  103 102      2 15.0
    60  103 102      4  9.0
    61  103 102      5  6.0
    62  103 103      1 10.0
    63  103 103      2 20.0
    64  103 103      4 12.0
    65  103 103      5  8.0
    66  103 104      1  7.5
    67  103 104      2 15.0
    68  103 104      4  9.0
    69  103 104      5  6.0
    70  103 105      1  2.5
    71  103 105      2  5.0
    72  103 105      4  3.0
    73  103 105      5  2.0
    74  103 106      1  5.0
    75  103 106      2 10.0
    76  103 106      4  6.0
    77  103 106      5  4.0
    78  104 101      2  8.0
    79  104 101      3 16.0
    80  104 101      4 18.0
    81  104 101      5 16.0
    82  104 102      2  4.0
    83  104 102      3  8.0
    84  104 102      4  9.0
    85  104 102      5  8.0
    86  104 103      2  6.0
    87  104 103      3 12.0
    88  104 103      4 13.5
    89  104 103      5 12.0
    90  104 104      2  8.0
    91  104 104      3 16.0
    92  104 104      4 18.0
    93  104 104      5 16.0
    94  104 105      2  4.0
    95  104 105      3  8.0
    96  104 105      4  9.0
    97  104 105      5  8.0
    98  104 106      2  4.0
    99  104 106      3  8.0
    100 104 106      4  9.0
    101 104 106      5  8.0
    102 104 107      2  2.0
    103 104 107      3  4.0
    104 104 107      4  4.5
    105 104 107      5  4.0
    106 105 101      3  9.0
    107 105 101      5  7.0
    108 105 102      3  4.5
    109 105 102      5  3.5
    110 105 103      3  4.5
    111 105 103      5  3.5
    112 105 104      3  9.0
    113 105 104      5  7.0
    114 105 105      3  9.0
    115 105 105      5  7.0
    116 105 106      3  4.5
    117 105 106      5  3.5
    118 105 107      3  4.5
    119 105 107      5  3.5
    120 106 101      4  8.0
    121 106 101      5  8.0
    122 106 102      4  4.0
    123 106 102      5  4.0
    124 106 103      4  8.0
    125 106 103      5  8.0
    126 106 104      4  8.0
    127 106 104      5  8.0
    128 106 105      4  4.0
    129 106 105      5  4.0
    130 106 106      4  8.0
    131 106 106      5  8.0
    132 107 101      3  5.0
    133 107 104      3  5.0
    134 107 105      3  5.0
    135 107 107      3  5.0

#5. 按输入格式得到推荐评分列表
result.mr<-mapreduce(
  input=cal.mr,
  map=function(k,v){
    keyval(v$user.r,v)
  }
  ,reduce=function(k,v){
    val<-ddply(v,.(user.r,v.l),summarize,v=sum(v))
    val2<-val[order(val$v,decreasing=TRUE),]
    names(val2)<-c("user","item","pref")
    keyval(val2$user,val2)
  }
)
from.dfs(result.mr)

    $key
     [1] 1 1 1 1 1 1 1 2 2 2 2 2 2 2 3 3 3 3 3 3 3 4 4 4 4 4 4 4 5 5 5 5 5 5 5

    $val
       user item pref
    1     1  101 44.0
    2     1  103 39.0
    3     1  104 33.5
    4     1  102 31.5
    5     1  106 18.0
    6     1  105 15.5
    7     1  107  5.0
    8     2  101 45.5
    9     2  103 41.5
    10    2  104 36.0
    11    2  102 32.5
    12    2  106 20.5
    13    2  105 15.5
    14    2  107  4.0
    15    3  101 40.0
    16    3  104 38.0
    17    3  105 26.0
    18    3  103 24.5
    19    3  102 18.5
    20    3  106 16.5
    21    3  107 15.5
    22    4  101 63.0
    23    4  104 55.0
    24    4  103 53.5
    25    4  102 37.0
    26    4  106 33.0
    27    4  105 26.0
    28    4  107  9.5
    29    5  101 68.0
    30    5  104 59.0
    31    5  103 56.5
    32    5  102 42.5
    33    5  106 34.5
    34    5  105 32.0
    35    5  107 11.5
文章中提供了R用MapReduce方法,实现协同过滤算法的一种思路。
基于MapReduce的基于用户的协同过滤算法代码及其使用 立即下载

相关推荐

基于map reduce的协同过滤实现

基于mapreduce的协同过滤实现。代码注释清晰。公式解释明确。使用utf-8编码

RHadoop实践系列之三 R实现MapReduce的协同过滤算法

RHadoop实践系列文章,包含了R语言与Hadoop结合进行海量数据分析。Hadoop主要用来存储海量数据,R语言完成MapReduce 算法,用来替代Java的MapReduce实现。有了RHadoop可以让广大的R语言爱好者,有更强大的工具处理大数据1G, 10G, 100G, TB, PB。 由于大数据所带来的单机性能问题,可能会一...

fens的博客 462

MapReduce基于物品的协同过滤算法实现电影推荐系统

本文档主要是协同过滤算法实现的电影推荐系统源码,对应本人博客MapReduce基于物品的协同过滤算法实现电影推荐系统。欢迎大家关注数据科学,关注我。谢谢

基于MapReduce实现物品协同过滤算法(ItemCF)

一、背景电子商务网站是个性化推荐系统重要地应用的领域之一,亚马逊就是个性化推荐系统的积极应用者和推广者,亚马逊的推荐系统深入到网站的各类商品,为亚马逊带来了至少30%的销售额。二、ItemCF简介基于item的协同过滤,通过用户对不同item的评分来评测item之间的相似性,基于item之间的相似性做出推荐。简单来讲就是:给用户推荐和他之前喜欢的物品相似的物品。如下说明:注:基于物品的协同过滤算法...

xl.zhang的博客 1万+

Android Studio打包全攻略---从入门到精通

初出茅庐 手动打包怎么手动打包项目写完了,现在需要把应用上传到市场,问题出现—怎么把代码变成.apk(Android的可安装文件)。 1. 创建签名文件 2. 填写好签名参数 3. 生成APK 注意:签名的密码和密匙的密码注意保管,不要忘了,签名文件别泄漏了,也别搞丢了为什么要打包我最开始就有这个疑问,我们的代码不是点了下运行按钮就直接安装到手机上了吗,我们在在项目Project

我早就想,要这样载着你,翻山越岭 2万+

MQTT与物联网平台(一):基础知识和设备接入物联网平台的实现(以华为云为例)

本文简单介绍了MQTT的基础知识和使用方法,以蓝牙WIFI双模芯片W801作为硬件设备,接入到华为云。

weixin_50622833的博客 1万+

R中协同过滤算法

协同过滤(Collaborative Filtering,简称CF)协同过滤常常被用于分辨某位特定顾客可能感兴趣的东西,这些结论来自于其他相似顾客对哪些产品感兴趣的分析。数据结构 协同过滤,主要收集每个用户对使用过的物品的评价。 评价可以理解为经常在电商网站上出现的,五星级的评分。 注意:不同用户的评分标准不同,所以需要对评分进行标准化处理。 标准化为0-1之间的值。①用户评分向量 ②商品

Erin的博客 2508

鸿蒙日历组件进阶:教你打造个性化日程管理界面(支持月份切换)

本文深入探讨了鸿蒙应用开发中自定义日历组件的构建方法。通过详解基于Grid的布局设计、核心日期算法、月份切换逻辑以及事件管理集成,指导开发者打造支持个性化日程管理的高性能日历界面,提升应用交互体验。

weixin_29207149的博客 66

通过mapReduce实现基于项目的协同过滤推荐

通过mapReduce实现基于项目的协同过滤推荐 需求介绍 协同过滤推荐网上有很多种介绍,我这里主要介绍的是基于项目的协同过滤。基于项目的协同过滤推荐基于这样的假设:一个用户会喜欢他之前喜欢的项目相似的项目。因此,基于项目的协同过滤推荐关键在于计算物品之间的相似度。 数据介绍 我选用的数据集合如下: 1,101,5.0 1,102,3.0 1,103,2.5 2,101,2.0 2,1

pardy原创 3756

《数据结构》04-树4 是否同一棵二叉搜索树

题目 给定一个插入序列就可以唯一确定一棵二叉搜索树。然而,一棵给定的二叉搜索树却可以由多种不同的插入序列得到。例如分别按照序列{2, 1, 3}和{2, 3, 1}插入初始为空的二叉搜索树,都得到一样的结果。于是对于输入的各种插入序列,你需要判断它们是否能生成一样的二叉搜索树。 输入格式: 输入包含若干组测试数据。每组数据的第1行给出两个正整数N (≤10)和L,分别是每个序列插入元素的个数和需要...

叫我皮卡丘 2012

2026年广东省职业院校技能大赛中职组“大数据应用与服务”样题一完整参考答案

2026年广东省职业院校技能大赛中职组“大数据应用与服务”样题一完整参考答案

我是网络安全兼技能大赛工程师,专注网络安全技术学习与技能大赛实战!持续分享最新的技术文章,帮你少走弯路,一起在技术赛道上进步~ 753

R语言实现MapReduce的协同过滤算法

原文地址:http://www.tuicool.com/articles/63Ejqi Author:张丹(Conan)  Date: 2013-04-07 Weibo: @Conan_Z  Email: bsspirit@gmail.com  Blog: http://www.fens.me/blog APPs:  @晒粉丝 http://www.fens.me  @

张小琦的博客专栏 1906

AI 赋能 DBA:如何用 DeepSeek 等大模型简化数据库管理工作

数据库管理员(DBA)的工作涉及 SQL 优化、故障排查、性能监控等复杂任务。而 DeepSeek、ChatGPT 等大模型可以大幅减少重复劳动,提高 DBA 的工作效率。:某电商平台的订单查询 SQL 执行缓慢(平均 5s),DBA 需要优化。:DBA 需要监控 MySQL 的慢查询,但不想手动写脚本。:某金融系统频繁出现数据库死锁,DBA 需要快速定位原因。:大模型可分析 SQL 执行计划,推荐索引优化方案。:用日常语言查询数据库,无需写复杂 SQL。:一键生成监控、备份、数据迁移脚本。

专注于编程、AI、人工智能等多个领域内容研究和分析 565

R实现mapreduce的协同过滤算法

算法的思想: 建立物品的同现矩阵 建立用户对物品的评分矩阵 矩阵计算推荐结果文字说明部分: 1.建立物品的同现矩阵 按用户分组,找到每个用户所选的去被,单独出现计数,和两两一组计数。例如:用户id为3的用户,分别给101,104,105,107,这四个物品打分。 1) (101,101),(104,104),(105,105),(107,107),单独出现计算各加1。 2) (101,

左手coding,右手cooking 688

AI 时代嵌入式工程师的能力模型与学习路线:全系列收官

AI 时代嵌入式工程师的能力模型与学习路线:全系列收官

weixin_42162924的博客 40

Holosoma 开源人形机器人强化学习训练部署框架

Holosoma是一个综合性人形机器人框架,支持强化学习策略的训练、部署和动作重定位。该框架兼容多种模拟器(IsaacGym、IsaacSim、MuJoCo等)和机器人(Unitree G1、Booster T1),提供运动控制和全身追踪功能。主要特性包括:跨模拟器训练评估、Wandb集成、多GPU支持、自定义奖励权重和观测噪声配置。推理模块支持实体机器人部署和MuJoCo仿真测试。动作重定位工具可将人体动作数据转换为机器人动作,支持单序列和批量处理。文档详细介绍了训练配置、评估方法和高级功能,如课程学习和

2506_90492529的博客 1829

协同过滤算法 R/mapreduce/spark mllib多语言实现

用户电影评分数据集下载http://grouplens.org/datasets/movielens/1) Item-Based,非个性化的,每个人看到的都一样2) User-Based,个性化的,每个人看到的不一样对用户的行为分析得到用户的喜好后,可以根据用户的喜好计算相似用户和物品,然后可以基于相似用户或物品进行推荐。这就是协同过滤中的两个分支了,基于用户的和基于物品的协同过滤。在计算用户之间

jethai的博客 1020

VB摄像头监控

该VB模块可对摄像头捕获的画面进行录像等,可在创建的窗口进行控制

RHadoop实践系列文章

发现一个很好的博客,主要讲R与hadoop的结合的文章 RHadoop实践系列文章

独家记忆 3221

win10 跳过U8环境检测的IE WebControls.rar

win10 安装u8的时候 提示IE WebControls 不通过,这个工具可以欺骗u8的检查。 跳过U8环境检测的IE WebControls。提示导入失败后,重新检测通过。

RU DOS版、EFI版32bit/64bit BIOS常用工具

DOS版、EFI版的RU工具,可用来查看IO、MEM、PCI、SMBIOS等资源。亲测在EFI SHELL下可用。

用R解析Mahout用户推荐协同过滤算法(UserCF)

用R解析Mahout用户推荐协同过滤算法(UserCF) RHadoop实践系列文章,包含了R语言与Hadoop结合进行海量数据分析。Hadoop主要用来存储海量数据,R语言完成MapReduce 算法,用来替代Java的MapReduce实现。有了RHadoop可以让广大的R语言爱好者,有更强大的工具处理大数据1G, 10G, 100G, TB, PB。 由于大数据所带来的单机性能问题,可

lzz360的专栏 923

汉书HE8,好用的汇编代码编写工具

汉书HE8,好用的汇编代码编写工具早期编写汇编代码所用功能强大

ChinaHadoop大会 2103: R语言为Hadoop注入统计血脉

跨界知识聚会系列文章,“知识是用来分享和传承的”,各种会议、论坛、沙龙都是分享知识的绝佳场所。我也有幸作为演讲嘉宾参加了一些国内的大型会议,向大家展示我所做的一些成果。从听众到演讲感觉是不一样的,把知识分享出来,你才能收获更多。 关于作者 张丹(Conan), 程序员Java,R,PHP,Javascript weibo:@Conan_Z...

fens的博客 208
上一篇: RHbase 命令
下一篇: RHive
hxpjava1
博客等级 码龄19年 1365粉丝 511原创
评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

个

红包个数最小为10个

元

红包金额最低5元

当前余额3.43元 前往充值 >
需支付:10.00元
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付元
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值