Mahout中主要核心的三大算法为推荐,聚类及分类算法,今天就最基本的推荐算法做总结,推荐中常用的两个推荐算法是”user_based”和”item_based”,前者主要通过和你兴趣相似的人来发现新的你感兴趣的东西,而后者则是发现一些和你所喜欢的事物相似的事物。此外,还有一种基于“contend_based”的推荐算法,它是根据事物所拥有的元数据出现进行事物的推荐,例如,如果你喜欢的电影是斯皮尔伯格导影的,那么你可以向你的朋友推荐他拍摄的其他影片,推荐的理由就是基于电影的一个属性——导演,这个就是基于内容的推荐。
下面将使用mahout来做一个小的推荐案例以供学习:
1.构建数据集
这里选取的常用的偏好来描述用户与项目之间的关联程度,一个偏好包含有用户ID,项目ID和偏好值,例如,用户对影片的评分值,评分值越大,代表用户对该影片的喜爱越好。
可以采用文本文件来保存该内容,如intro.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.5
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
2.建立简易推荐器
下面利用mathou提供的基本类包mahout-examples-0.10.0-job.jar来构建java代码程序,我们要实现的是根据用户的基本情况向User1推荐合适的影片,代码如下:
package com.recommeder.lg.example;
import org.apache.mahout.cf.taste.impl.model.file.*;
import org.apache.mahout.cf.taste.impl.neighborhood.*;
import org.apache.mahout.cf.taste.impl.recommender.*;
import org.apache.mahout.cf.taste.impl.similarity.*;
import org.apache.mahout.cf.taste.model.*;
import org.apache.mahout.cf.taste.neighborhood.*;
import org.apache.mahout.cf.taste.recommender.*;
import org.apache.mahout.cf.taste.similarity.*;
import java.io.*;
import java.util.*;
class RecommenderIntro {
public static void main(String[] args) throws Exception {
DataModel model = new FileDataModel(new File("/home/jinyu/Documents/intro.csv"));//加载数据文件
UserSimilarity similarity = new PearsonCorrelationSimilarity (model); //建立推荐模型
UserNeighborhood neighborhood = new NearestNUserNeighborhood (2, similarity, model);
Recommender recommender = new GenericUserBasedRecommender ( model, neighborhood, similarity);
List recommendations = recommender.recommend(1, 2); //给用户1推荐2个项目
for (RecommendedItem recommendation : recommendations) {
System.out.println(recommendation);
}
}
}
3.相关解释说明
该代码是基于用户推荐的基本流程,用图表示出来就是:
DataModel负责存储和提供用户、项目、偏好的计算所需要的数据。UserSimiliarity提供了一些基于某种
算法的用户相似度度量的方法。UserNeighborhood定义了一个和某指定用户相似的用户集合。最后,Recommender利用所有的组件来为一个用户产生一个推荐结果。
4.运行结果展示
利用eclipse运行该代码的结果如下所示:
可以看到该推荐器向用户1推荐了104,106这两部影片,其中104是推荐偏好量化值最高的一部
5.推荐器评估
高效准确地产生推荐结果是非常重要的,推荐的结果一般要求准、新、普,准要求推荐的结果可靠真实,新要求推荐的结果具有新奇性,不与往常重复,普则要求推荐的结果是为大众所接受的。评估的一般做法是将数据集分成训练集和测试集,然后选择指标进行评估说明。
常用的几个指标有:
下面利用差值平均数进行评估,代码如下:
import java.io.File;
import org.apache.mahout.cf.taste.common.TasteException;
import org.apache.mahout.cf.taste.eval.*;
import org.apache.mahout.cf.taste.impl.eval.*;
import org.apache.mahout.cf.taste.impl.model.file.*;
import org.apache.mahout.cf.taste.impl.neighborhood.*;
import org.apache.mahout.cf.taste.impl.recommender.*;
import org.apache.mahout.cf.taste.impl.similarity.*;
import org.apache.mahout.cf.taste.model.*;
import org.apache.mahout.cf.taste.neighborhood.*;
import org.apache.mahout.cf.taste.recommender.*;
import org.apache.mahout.cf.taste.similarity.*;
import org.apache.mahout.common.RandomUtils;
class RecommenderEvaluators {
public static void main(String[] args) throws Exception {
RandomUtils.useTestSeed();
DataModel model = new FileDataModel(new File("intro.csv"));//加载数据文件
RecommenderEvaluator evalutor= new AverageAbsoluteDifferenceRecommenderEvaluator();
RecommenderBuilder builder=new RecommenderBuilder() {
@Override
public Recommender buildRecommender(DataModel model) throws TasteException {
// TODO Auto-generated method stu
UserSimilarity similarity = new PearsonCorrelationSimilarity (model); //建立推荐模型
UserNeighborhood neighborhood = new NearestNUserNeighborhood (2, similarity, model);
return new GenericUserBasedRecommender (model,neighborhood,similarity);
}
};
double score =evalutor.evaluate(builder, null, model, 0.6, 1);
System.out.println(score);
}
}
最后的evaluate()函数为推荐器评分,分值越低,代表差异越小,评估的效果越准确,其中0.6表示训练集的百分比,1表示选取数据集的百分比。
6.分布式推荐计算
当数据量足够大时,单机环境已经不适用于做推荐计算了,这是可以考虑mahout提供的分布式推荐算法在hadoop平台下进行计算,可以把上述数据集上传到hdfs下的文件夹,然后利用recommenditembased命令进行分布式推荐计算,其适用的数据类型一般是偏好型,若是对向量数据进行相似度的计算,则可以考虑适用rowsimilarity命令,其主要参数可以使用mahout recommenditembased -h命令查看,运行命令如下:
mahout recommenditembased -i testdata/pre.data -o output/similar -s SIMILARITY_EUCLIDEAN_DISTANCE -n 3 -opfsm output/matrix
其中,-i 指出数据集存放地址,-o 存放推荐结果,-s 指出相似度计算的函数,-n 指出为每个用户推荐的数量,最后一个opfsm存放item间的相似度。
此外,hdfs下额外的产生的temp文件夹也有许多可查看文件,如下图:
不过,值得注意的事,尽管数据量很小,但是hadoop下的mapreduce过程仍然花费了一定的时间,还有,hadoop2.2与mahout1.0及以上版本搭配才可能不会出错的。