也许您的问题的最佳答案是CRAN 提供的 R 的推荐实验室包。这是小插图的链接。它实现了 CF 算法和 Jaccard 系数。对于 0/1 用户反馈案例。
只有 base stats R 包中的相似度(距离)计算才有dist函数。但它仅限于少数距离测量。我知道当我在名为vegan的 R 包中搜索距离度量时,声称已实现了许多方法。但我从未使用过它。
恕我直言,最基本的推荐系统算法非常简单。值得花几分钟实施它,以更好地理解和直觉它是如何工作的。尽管如此,在我针对您的案例的快速而肮脏的基于用户的 kNN 实现之下。代码可以以更好的方式重写(Adv.R 是非常好的资源) - 但这只是用于学习目的的示例,我不对任何损害负责:-)
require(reshape2)
ratings <- read.csv(con <- textConnection('
User,Item,Rating
Anna,Apple,2
Bob,Apple,4
Carlos,Apple,1
Ethan,Apple,1
Gene,Apple,2
Anna,Banana,4
Dana,Banana,3
Ethan,Banana,5
Frank,Banana,5
Bob,Carrot,1
Ethan,Carrot,2
Gene,Carrot,4
'), header = T)
R <- ratings %>% dcast(Item ~ User)
ProductNames <- R[,1]
R <- R[,-1] # only ratings
# tanimoto similarity (~Jaccard coefficiet)
tanimoto <- function(v1,v2) length(intersect(v1,v2))/length(union(v1,v2))
# return top-k similar users
getKNN <- function(R, i, k, sim = tanimoto) {
similarity <- array(0,length(R))
for(j in 1:length(R)) {
if(i!=j) similarity[j] = sim(which(!is.na(R[,i])),which(!is.na(R[,j])))
}
idx <- order(similarity, decreasing = T)[1:k]
data.frame(idx = idx, similarity = similarity[idx])
}
kNNRecommender <- function(R, k) {
reco <- data.frame()
for(u in 1:length(R)) {
userItems <- which(!is.na(R[,u])) #items rated by user
nn <- getKNN(R,u, k) # get user neighbours
# rating prediction - wiegted by similarity
r <- array(0, c(dim(R)[1], k))
for(i in 1:k) {
r[,i] = R[,nn[i,]$idx] * nn[i,]$similarity
}
r[is.na(r)] <- 0
userReco <- rowSums(r) / sum(nn$similarity)
userRecoIdx <- order(userReco, decreasing = T)
# remove items already rated by user
userRecoIdx <- userRecoIdx[-userItems]
# add to recommendations result
reco <- rbind(reco, data.frame(
User=u,
Item=(if(length(userRecoIdx)==0) NA else userRecoIdx),
Prediction=(if(length(userRecoIdx)==0) NA else userReco[userRecoIdx])
))
}
reco
}
kNNRecommender(R, 2)