数据挖掘领域十大经典算法初探 数据挖掘十大算法 ppt
以下就是从参加评选的18种候选算法中,最终决选出来的十大经典算法:一、C4.5C4.5,是机器学习算法中的一个分类决策树算法,它是决策树(决策树也就是做决策的节点间的组织方式像一棵树,其实是一个倒树)核心算法ID3的改进算法,所以基本上了解了一半决策树构造方法就能构造它。决策树构造方法其实就是每次选择一个好的特征以及分裂点作为当前节点的分类条件。C4.5相比于ID3改进的地方有:1、用信息增益率来选择属性。ID3选择属性用的是子树的信息增益,这里可以用很多方法来定义信息,ID3使用的是熵(entropy,熵是一种不纯度度量准则),也就是熵的变化值.而C4.5用的是信息增益率。对,区别就在于一个是信息增益,一个是信息增益率。一般来说率就是用来取平衡用的,就像方差起的作用差不多,比如有两个跑步的人,一个起点是10m/s的人、其10s后为20m/s;另一个人起速是1m/s、其1s后为2m/s。如果紧紧算差值那么两个差距就很大了,如果使用速度增加率(加速度,即都是为1m/s^2)来衡量,2个人就是一样的加速度。因此,C4.5克服了ID3用信息增益选择属性时偏向选择取值多的属性的不足。2、在树构造过程中进行剪枝,在构造决策树的时候,那些挂着几个元素的节点,不考虑最好,不然容易导致overfitting。3、对非离散数据也能处理。4、能够对不完整数据进行处理。
二、The k-means algorithm 即K-Means算法k-means algorithm算法是一个聚类算法,把n的对象根据他们的属性分为k个分割(k < n)。它与处理混合正态分布的最大期望算法(本十大算法第五条)很相似,因为他们都试图找到数据中自然聚类的中心。它假设对象属性来自于空间向量,并且目标是使各个群组内部的均方误差总和最小。
三、 Support vector machines支持向量机,英文为Support Vector Machine,简称SV机(论文中一般简称SVM)。它是一种监督式学习的方法,它广泛的应用于统计分类以及回归分析中。支持向量机将向量映射到一个更高维的空间里,在这个空间里建立有一个最大间隔超平面。在分开数据的超平面的两边建有两个互相平行的超平面,分隔超平面使两个平行超平面的距离最大化。假定平行超平面间的距离或差距越大,分类器的总误差越小。一个极好的指南是C.J.C Burges的《模式识别支持向量机指南》。van der Walt 和 Barnard 将支持向量机和其他分类器进行了比较。
四、The Apriori algorithmApriori算法是一种最有影响的挖掘布尔关联规则频繁项集的算法。其核心是基于两阶段频集思想的递推算法。该关联规则在分类上属于单维、单层、布尔关联规则。在这里,所有支持度大于最小支持度的项集称为频繁项集,简称频集。
五、最大期望(EM)算法在统计计算中,最大期望 (EM,Expectation–Maximization)算法是在概率(probabilistic)模型中寻找参数最大似然估计的算法,其中概率模型依赖于无法观测的隐藏变量(LatentVariabl)。最大期望经常用在机器学习和计算机视觉的数据集聚(Data Clustering)领域。
六、 PageRankPageRank是Google算法的重要内容。2001年9月被授予美国专利,专利人是Google创始人之一拉里•佩奇(LarryPage)。因此,PageRank里的page不是指网页,而是指佩奇,即这个等级方法是以佩奇来命名的。PageRank根据网站的外部链接和内部链接的数量和质量,衡量网站的价值。PageRank背后的概念是,每个到页面的链接都是对该页面的一次投票,被链接的越多,就意味着被其他网站投票越多。这个就是所谓的“链接流行度”——衡量多少人愿意将他们的网站和你的网站挂钩。PageRank这个概念引自学术中一篇论文的被引述的频度——即被别人引述的次数越多,一般判断这篇论文的权威性就越高。
七、AdaBoostAdaboost是一种迭代算法,其核心思想是针对同一个训练集训练不同的分类器(弱分类器),然后把这些弱分类器集合起来,构成一个更强的最终分类器 (强分类器)。其算法本身是通过改变数据分布来实现的,它根据每次训练集之中每个样本的分类是否正确,以及上次的总体分类的准确率,来确定每个样本的权值。将修改过权值的新数据集送给下层分类器进行训练,最后将每次训练得到的分类器融合起来,作为最后的决策分类器。
八、 kNN: k-nearest neighbor classificationK最近邻(k-NearestNeighbor,KNN)分类算法,是一个理论上比较成熟的方法,也是最简单的机器学习算法之一。该方法的思路是:如果一个样本在特征空间中的k个最相似(即特征空间中最邻近)的样本中的大多数属于某一个类别,则该样本也属于这个类别。
九、 Naive Bayes在众多的分类模型中,应用最为广泛的两种分类模型是决策树模型(Decision Tree Model)和朴素贝叶斯模型(Naive Bayesian Model,NBC)。朴素贝叶斯模型发源于古典数学理论,有着坚实的数学基础,以及稳定的分类效率。同时,NBC模型所需估计的参数很少,对缺失数据不太敏感,算法也比较简单。理论上,NBC模型与其他分类方法相比具有最小的误差率。但是实际上并非总是如此,这是因为NBC模型假设属性之间相互独立,这个假设在实际应用中往往是不成立的,这给NBC模型的正确分类带来了一定影响。在属性个数比较多或者属性之间相关性较大时,NBC模型的分类效率比不上决策树模型。而在属性相关性较小时,NBC模型的性能最为良好。
十、 CART: 分类与回归树CART, Classification and Regression Trees。在分类树下面有两个关键的思想:第一个是关于递归地划分自变量空间的想法;第二个想法是用验证数据进行剪枝。ok,日后择其一二详细研究、阐述,完。至于18种候选算法,可参考这里:http://www.cs.uvm.edu/~icdm/algorithms/CandidateList.shtml
作者声明:本人July对本博客所有文章和资料享有版权,转载或引用任何文章、资料请注明出处。谢谢。July、二零一一年一月十五日。
Mahout推荐算法API详解分类: C/C++(win32和linux) 搜索引擎开发(数据挖掘、海量数据处理、自然语言)转型——创业/经济/金融/投资/理财2013-10-28 17:54 13341人阅读 评论(2) 收藏 举报目录(?)[+]前言用Mahout来构建推荐系统,是一件既简单又困难的事情。简单是因为Mahout完整地封装了“协同过滤”算法,并实现了并行化,提供非常简单的API接口;困难是因为我们不了解算法细节,很难去根据业务的场景进行算法配置和调优。本文将深入算法API去解释Mahout推荐算法底层的一些事。目录Mahout推荐算法介绍算法评判标准:召回率与准确率Recommender.java的API接口测试程序:RecommenderTest.java基于用户的协同过滤算法UserCF基于物品的协同过滤算法ItemCFSlopeOne算法KNN Linear interpolation item–based推荐算法SVD推荐算法Tree Cluster-based 推荐算法Mahout推荐算法总结1. Mahout推荐算法介绍Mahoutt推荐算法,从数据处理能力上,可以划分为2类:单机内存算法实现
基于Hadoop的分步式算法实现
1). 单机内存算法实现单机内存算法实现:就是在单机下运行的算法,是由cf.taste项目实现的,像我的们熟悉的UserCF,ItemCF都支持单机内存运行,并且参数可以灵活配置。单机算法的基本实例,请参考文章:用Maven构建Mahout项目单机内存算法的问题在于,受限于单机的资源。对于中等规模的数据,像1G,10G的数据量,有能力进行计算,但是超过100G的数据量,对于单机来说是不可能完成的任务。2). 基于Hadoop的分步式算法实现基于Hadoop的分步式算法实现:就是把单机内存算法并行化,把任务分散到多台计算机一起运行。Mahout提供了ItemCF基于Hadoop并行化算法实现。基于Hadoop的分步式算法实现,请参考文章:Mahout分步式程序开发 基于物品的协同过滤ItemCF分步式并行算法的问题在于,如何让单机算法并行化。在单机算法中,我们只需要考虑算法,数据结构,内存,CPU就够了,但是分步式算法还要额外考虑很多的情况,比如多节点的数据合并,数据排序,网路通信的效率,节点宕机重算,数据分步式存储等等的很多问题。2. 算法评判标准:召回率(recall)与查准率(precision)Mahout提供了2个评估推荐器的指标,查准率和召回率(查全率),这两个指标是搜索引擎中经典的度量方法。
相关 不相关检索到 A C未检索到 B DA:检索到的,相关的 (搜到的也想要的)B:未检索到的,但是相关的 (没搜到,然而实际上想要的)C:检索到的,但是不相关的 (搜到的但没用的)D:未检索到的,也不相关的 (没搜到也没用的)被检索到的越多越好,这是追求“查全率”,即A/(A+B),越大越好。被检索到的,越相关的越多越好,不相关的越少越好,这是追求“查准率”,即A/(A+C),越大越好。在大规模数据集合中,这两个指标是相互制约的。当希望索引出更多的数据的时候,查准率就会下降,当希望索引更准确的时候,会索引更少的数据。3. Recommender的API接口1). 系统环境:Win7 64bitJava 1.6.0_45Maven 3Eclipse Juno Service Release 2Mahout 0.8Hadoop 1.1.22). Recommender接口文件:org.apache.mahout.cf.taste.recommender.Recommender.java
接口中方法的解释:recommend(long userID, int howMany):获得推荐结果,给userID推荐howMany个Itemrecommend(long userID, int howMany, IDRescorer rescorer):获得推荐结果,给userID推荐howMany个Item,可以根据rescorer对结构重新排序。estimatePreference(long userID, long itemID):当打分为空,估计用户对物品的打分setPreference(long userID, long itemID, float value):赋值用户,物品,打分removePreference(long userID, long itemID): 删除用户对物品的打分getDataModel(): 提取推荐数据通过Recommender接口,我可以猜出核心算法,应该会在子类的estimatePreference()方法中进行实现。3). 通过继承关系到Recommender接口的子类:
推荐算法实现类:GenericUserBasedRecommender: 基于用户的推荐算法GenericItemBasedRecommender: 基于物品的推荐算法KnnItemBasedRecommender: 基于物品的KNN推荐算法SlopeOneRecommender: Slope推荐算法SVDRecommender: SVD推荐算法TreeClusteringRecommender:TreeCluster推荐算法下面将分别介绍每种算法的实现。4. 测试程序:RecommenderTest.java测试数据集:item.csv
1,101,5.01,102,3.01,103,2.52,101,2.02,102,2.52,103,5.02,104,2.03,101,2.53,104,4.03,105,4.53,107,5.04,101,5.04,103,3.04,104,4.54,106,4.05,101,4.05,102,3.05,103,2.05,104,4.05,105,3.55,106,4.0测试程序:org.conan.mymahout.recommendation.job.RecommenderTest.java
package org.conan.mymahout.recommendation.job;
import java.io.IOException;import java.util.List;
import org.apache.mahout.cf.taste.common.TasteException;importorg.apache.mahout.cf.taste.eval.RecommenderBuilder;importorg.apache.mahout.cf.taste.impl.common.LongPrimitiveIterator;import org.apache.mahout.cf.taste.model.DataModel;importorg.apache.mahout.cf.taste.recommender.RecommendedItem;import org.apache.mahout.common.RandomUtils;
public class RecommenderTest {
final static intNEIGHBORHOOD_NUM = 2; final static intRECOMMENDER_NUM = 3;
public static voidmain(String[] args) throws TasteException, IOException { RandomUtils.useTestSeed(); String file = "datafile/item.csv"; DataModel dataModel =RecommendFactory.buildDataModel(file); slopeOne(dataModel); }
public static voiduserCF(DataModel dataModel) throws TasteException{} public static voiditemCF(DataModel dataModel) throws TasteException{} public static voidslopeOne(DataModel dataModel) throws TasteException{}
...
每种算法都一个单独的方法进行算法测试,如userCF(),itemCF(),slopeOne()….5. 基于用户的协同过滤算法UserCF基于用户的协同过滤,通过不同用户对物品的评分来评测用户之间的相似性,基于用户之间的相似性做出推荐。简单来讲就是:给用户推荐和他兴趣相似的其他用户喜欢的物品。举例说明:
基于用户的 CF的基本思想相当简单,基于用户对物品的偏好找到相邻邻居用户,然后将邻居用户喜欢的推荐给当前用户。计算上,就是将一个用户对所有物品的偏好作为一个向量来计算用户之间的相似度,找到K 邻居后,根据邻居的相似度权重以及他们对物品的偏好,预测当前用户没有偏好的未涉及物品,计算得到一个排序的物品列表作为推荐。图 2给出了一个例子,对于用户 A,根据用户的历史偏好,这里只计算得到一个邻居 – 用户 C,然后将用户 C 喜欢的物品 D 推荐给用户A。上文中图片和解释文字,摘自:https://www.ibm.com/developerworks/cn/web/1103_zhaoct_recommstudy2/算法API:org.apache.mahout.cf.taste.impl.recommender.GenericUserBasedRecommender
@Override public float estimatePreference(longuserID, long itemID) throws TasteException { DataModel model =getDataModel(); Float actualPref =model.getPreferenceValue(userID, itemID); if (actualPref != null){ return actualPref; } long[] theNeighborhood =neighborhood.getUserNeighborhood(userID); returndoEstimatePreference(userID, theNeighborhood, itemID); }
protected float doEstimatePreference(longtheUserID, long[] theNeighborhood, long itemID) throwsTasteException { if(theNeighborhood.length == 0) { return Float.NaN; } DataModel dataModel =getDataModel(); double preference =0.0; double totalSimilarity =0.0; int count = 0; for (long userID :theNeighborhood) { if(userID != theUserID) { // SeeGenericItemBasedRecommender.doEstimatePreference() too Float pref =dataModel.getPreferenceValue(userID, itemID); if (pref != null) { double theSimilarity =similarity.userSimilarity(theUserID, userID); if(!Double.isNaN(theSimilarity)) { preference+= theSimilarity * pref; totalSimilarity += theSimilarity; count++; } } } } // Throw out theestimate if it was based on no data points, of course, but also ifbased on // just one. This is abit of a band-aid on the 'stock' item-based algorithm for themoment. // The reason is that inthis case the estimate is, simply, the user's rating for oneitem // that happened to havea defined similarity. The similarity score doesn't matter, andthat // seems like a badsituation. if (count <= 1){ return Float.NaN; } float estimate = (float)(preference / totalSimilarity); if (capper != null){ estimate = capper.capEstimate(estimate); } return estimate; }测试程序:
public static voiduserCF(DataModel dataModel) throws TasteException { UserSimilarity userSimilarity =RecommendFactory.userSimilarity(RecommendFactory.SIMILARITY.EUCLIDEAN,dataModel); UserNeighborhood userNeighborhood =RecommendFactory.userNeighborhood(RecommendFactory.NEIGHBORHOOD.NEAREST,userSimilarity, dataModel, NEIGHBORHOOD_NUM); RecommenderBuilder recommenderBuilder =RecommendFactory.userRecommender(userSimilarity, userNeighborhood,true);
RecommendFactory.evaluate(RecommendFactory.EVALUATOR.AVERAGE_ABSOLUTE_DIFFERENCE,recommenderBuilder, null, dataModel, 0.7); RecommendFactory.statsEvaluator(recommenderBuilder, null,dataModel, 2);
LongPrimitiveIterator iter =dataModel.getUserIDs(); while (iter.hasNext()) { long uid =iter.nextLong(); List list= recommenderBuilder.buildRecommender(dataModel).recommend(uid,RECOMMENDER_NUM); RecommendFactory.showItems(uid, list, true); } }程序输出:
AVERAGE_ABSOLUTE_DIFFERENCE Evaluater Score:1.0Recommender IR Evaluator: [Precision:0.5,Recall:0.5]uid:1,(104,4.333333)(106,4.000000)uid:2,(105,4.049678)uid:3,(103,3.512787)(102,2.747869)uid:4,(102,3.000000)用R语言重写UserCF的实现,请参考文章:用R解析Mahout用户推荐协同过滤算法(UserCF)6. 基于物品的协同过滤算法ItemCF基于item的协同过滤,通过用户对不同item的评分来评测item之间的相似性,基于item之间的相似性做出推荐。简单来讲就是:给用户推荐和他之前喜欢的物品相似的物品。举例说明:
基于物品的 CF 的原理和基于用户的 CF类似,只是在计算邻居时采用物品本身,而不是从用户的角度,即基于用户对物品的偏好找到相似的物品,然后根据用户的历史偏好,推荐相似的物品给他。从计算的角度看,就是将所有用户对某个物品的偏好作为一个向量来计算物品之间的相似度,得到物品的相似物品后,根据用户历史的偏好预测当前用户还没有表示偏好的物品,计算得到一个排序的物品列表作为推荐。图3 给出了一个例子,对于物品 A,根据所有用户的历史偏好,喜欢物品 A 的用户都喜欢物品 C,得出物品 A 和物品 C比较相似,而用户 C 喜欢物品 A,那么可以推断出用户 C 可能也喜欢物品 C。上文中图片和解释文字,摘自:https://www.ibm.com/developerworks/cn/web/1103_zhaoct_recommstudy2/算法API:org.apache.mahout.cf.taste.impl.recommender.GenericItemBasedRecommender
@Override public float estimatePreference(longuserID, long itemID) throws TasteException { PreferenceArraypreferencesFromUser =getDataModel().getPreferencesFromUser(userID); Float actualPref =getPreferenceForItem(preferencesFromUser, itemID); if (actualPref != null){ return actualPref; } returndoEstimatePreference(userID, preferencesFromUser, itemID); }
protected float doEstimatePreference(long userID,PreferenceArray preferencesFromUser, long itemID) throws TasteException{ double preference =0.0; double totalSimilarity =0.0; int count = 0; double[] similarities =similarity.itemSimilarities(itemID,preferencesFromUser.getIDs()); for (int i = 0; i <similarities.length; i++) { double theSimilarity = similarities[i]; if(!Double.isNaN(theSimilarity)) { // Weights can be negative! preference += theSimilarity *preferencesFromUser.getValue(i); totalSimilarity += theSimilarity; count++; } } // Throw out theestimate if it was based on no data points, of course, but also ifbased on // just one. This is abit of a band-aid on the 'stock' item-based algorithm for themoment. // The reason is that inthis case the estimate is, simply, the user's rating for oneitem // that happened to havea defined similarity. The similarity score doesn't matter, andthat // seems like a badsituation. if (count <= 1){ return Float.NaN; } float estimate = (float)(preference / totalSimilarity); if (capper != null){ estimate = capper.capEstimate(estimate); } return estimate; }测试程序:
public static voiditemCF(DataModel dataModel) throws TasteException { ItemSimilarity itemSimilarity =RecommendFactory.itemSimilarity(RecommendFactory.SIMILARITY.EUCLIDEAN,dataModel); RecommenderBuilder recommenderBuilder =RecommendFactory.itemRecommender(itemSimilarity, true);
RecommendFactory.evaluate(RecommendFactory.EVALUATOR.AVERAGE_ABSOLUTE_DIFFERENCE,recommenderBuilder, null, dataModel, 0.7); RecommendFactory.statsEvaluator(recommenderBuilder, null,dataModel, 2);
LongPrimitiveIterator iter =dataModel.getUserIDs(); while (iter.hasNext()) { long uid =iter.nextLong(); List list= recommenderBuilder.buildRecommender(dataModel).recommend(uid,RECOMMENDER_NUM); RecommendFactory.showItems(uid, list, true); } }程序输出:
AVERAGE_ABSOLUTE_DIFFERENCE EvaluaterScore:0.8676552772521973Recommender IR Evaluator: [Precision:0.5,Recall:1.0]uid:1,(105,3.823529)(104,3.722222)(106,3.478261)uid:2,(106,2.984848)(105,2.537037)(107,2.000000)uid:3,(106,3.648649)(102,3.380000)(103,3.312500)uid:4,(107,4.722222)(105,4.313953)(102,4.025000)uid:5,(107,3.736842)7. SlopeOne算法这个算法在mahout-0.8版本中,已经被@Deprecated。SlopeOne是一种简单高效的协同过滤算法。通过均差计算进行评分。SlopeOne论文下载(PDF)1). 举例说明:用户X,Y,Z,对于物品A,B进行打分,如下表,求Z对B的打分是多少?Slope one算法认为:平均值可以代替某两个未知个体之间的打分差异,事物A对事物B的平均差是:((5 - 4) + (4- 2)) / 2 = 1.5,就得到Z对B的打分是,3-1.5 = 1.5。Slope one算法将用户的评分之间的关系看作简单的线性关系:Y = mX + b2). 平均加权计算:用户X,Y,Z,对于物品A,B,C进行打分,如下表,求Z对A的打分是多少?1. 计算A和B的平均差, ((5-3)+(3-4))/2=0.52. 计算A和C的平均差, (5-2)/1=33. Z对A的评分,通过AB得到, 2+0.5=2.54. Z对A的评分,通过AC得到,5+3=85. 通过加权平均计算Z对A的评分:A和B都有评价的用户数为2,A和C都有评价的用户数为1,权重为别是2和1,(2*2.5+1*8)/(2+1)=13/3=4.33通过这种简单的方式,我们可以快速计算出一个评分项,完成推荐过程!算法API:org.apache.mahout.cf.taste.impl.recommender.slopeone.SlopeOneRecommender
@Override public float estimatePreference(longuserID, long itemID) throws TasteException { DataModel model =getDataModel(); Float actualPref =model.getPreferenceValue(userID, itemID); if (actualPref != null){ return actualPref; } returndoEstimatePreference(userID, itemID); } private float doEstimatePreference(longuserID, long itemID) throws TasteException { double count =0.0; double totalPreference =0.0; PreferenceArray prefs =getDataModel().getPreferencesFromUser(userID); RunningAverage[]averages = diffStorage.getDiffs(userID, itemID, prefs); int size =prefs.length(); for (int i = 0; i <size; i++) { RunningAverage averageDiff = averages[i]; if(averageDiff != null) { double averageDiffValue =averageDiff.getAverage(); if (weighted) { double weight =averageDiff.getCount(); if (stdDevWeighted) { doublestdev = ((RunningAverageAndStdDev)averageDiff).getStandardDeviation(); if(!Double.isNaN(stdev)) { weight /= 1.0 + stdev; } // Ifstdev is NaN, then it is because count is 1. Because we'reweighting by count, // theweight is already relatively low. We effectively assume stdev is0.0 here and // that isreasonable enough. Otherwise, dividing by NaN would yield a weightof NaN // anddisqualify this pref entirely // (ThanksDaemmon) } totalPreference += weight *(prefs.getValue(i) + averageDiffValue); count += weight; } else { totalPreference +=prefs.getValue(i) + averageDiffValue; count += 1.0; } } } if (count <= 0.0){ RunningAverage itemAverage =diffStorage.getAverageItemPref(itemID); return itemAverage == null ? Float.NaN : (float)itemAverage.getAverage(); } else { return (float) (totalPreference / count); } }测试程序:
public static voidslopeOne(DataModel dataModel) throws TasteException { RecommenderBuilder recommenderBuilder =RecommendFactory.slopeOneRecommender();
RecommendFactory.evaluate(RecommendFactory.EVALUATOR.AVERAGE_ABSOLUTE_DIFFERENCE,recommenderBuilder, null, dataModel, 0.7); RecommendFactory.statsEvaluator(recommenderBuilder, null,dataModel, 2);
LongPrimitiveIterator iter =dataModel.getUserIDs(); while (iter.hasNext()) { long uid =iter.nextLong(); List list= recommenderBuilder.buildRecommender(dataModel).recommend(uid,RECOMMENDER_NUM); RecommendFactory.showItems(uid, list, true); } }程序输出:
AVERAGE_ABSOLUTE_DIFFERENCE EvaluaterScore:1.3333333333333333Recommender IR Evaluator: [Precision:0.25,Recall:0.5]uid:1,(105,5.750000)(104,5.250000)(106,4.500000)uid:2,(105,2.286115)(106,1.500000)uid:3,(106,2.000000)(102,1.666667)(103,1.625000)uid:4,(105,4.976859)(102,3.509071)8. KNN Linear interpolation item–based推荐算法这个算法在mahout-0.8版本中,已经被@Deprecated。算法来自论文:This algorithm is based in the paper of Robert M. Bell andYehuda Koren in ICDM '07.(TODO未完)算法API:org.apache.mahout.cf.taste.impl.recommender.knn.KnnItemBasedRecommender
@Override protected float doEstimatePreference(longtheUserID, PreferenceArray preferencesFromUser, long itemID) throws TasteException{ DataModel dataModel =getDataModel(); int size =preferencesFromUser.length(); FastIDSetpossibleItemIDs = new FastIDSet(size); for (int i = 0; i <size; i++) { possibleItemIDs.add(preferencesFromUser.getItemID(i)); } possibleItemIDs.remove(itemID); List mostSimilar =mostSimilarItems(itemID, possibleItemIDs.iterator(), neighborhoodSize, null); long[] theNeighborhood =new long[mostSimilar.size() + 1]; theNeighborhood[0] =-1; ListusersRatedNeighborhood = Lists.newArrayList(); int nOffset = 0; for (RecommendedItem rec: mostSimilar) { theNeighborhood[nOffset++] = rec.getItemID(); } if(!mostSimilar.isEmpty()) { theNeighborhood[mostSimilar.size()] = itemID; for(int i = 0; i < theNeighborhood.length; i++) { PreferenceArray usersNeighborhood =dataModel.getPreferencesForItem(theNeighborhood[i]); int size1 = usersRatedNeighborhood.isEmpty() ?usersNeighborhood.length() : usersRatedNeighborhood.size(); for (int j = 0; j < size1; j++) { if (i == 0) { usersRatedNeighborhood.add(usersNeighborhood.getUserID(j)); } else { if (j>= usersRatedNeighborhood.size()) { break; } long index= usersRatedNeighborhood.get(j); if(!usersNeighborhood.hasPrefWithUserID(index) || index == theUserID){ usersRatedNeighborhood.remove(index); j--; } } } } }
double[] weights =null; if(!mostSimilar.isEmpty()) { weights = getInterpolations(itemID, theNeighborhood,usersRatedNeighborhood); } int i = 0; double preference =0.0; double totalSimilarity =0.0; for (long jitem :theNeighborhood) { Floatpref = dataModel.getPreferenceValue(theUserID, jitem); if(pref != null) { double weight = weights[i]; preference += pref * weight; totalSimilarity += weight; } i++; } return totalSimilarity== 0.0 ? Float.NaN : (float) (preference / totalSimilarity); }}测试程序:
public static voiditemKNN(DataModel dataModel) throws TasteException { ItemSimilarity itemSimilarity =RecommendFactory.itemSimilarity(RecommendFactory.SIMILARITY.EUCLIDEAN,dataModel); RecommenderBuilder recommenderBuilder =RecommendFactory.itemKNNRecommender(itemSimilarity, newNonNegativeQuadraticOptimizer(), 10);
RecommendFactory.evaluate(RecommendFactory.EVALUATOR.AVERAGE_ABSOLUTE_DIFFERENCE,recommenderBuilder, null, dataModel, 0.7); RecommendFactory.statsEvaluator(recommenderBuilder, null,dataModel, 2);
LongPrimitiveIterator iter =dataModel.getUserIDs(); while (iter.hasNext()) { long uid =iter.nextLong(); List list= recommenderBuilder.buildRecommender(dataModel).recommend(uid,RECOMMENDER_NUM); RecommendFactory.showItems(uid, list, true); } }程序输出:
AVERAGE_ABSOLUTE_DIFFERENCE Evaluater Score:1.5Recommender IR Evaluator: [Precision:0.5,Recall:1.0]uid:1,(107,5.000000)(104,3.501168)(106,3.498198)uid:2,(105,2.878995)(106,2.878086)(107,2.000000)uid:3,(103,3.667444)(102,3.667161)(106,3.667019)uid:4,(107,4.750247)(102,4.122755)(105,4.122709)uid:5,(107,3.833621)9. SVD推荐算法(TODO未完)算法API:org.apache.mahout.cf.taste.impl.recommender.svd.SVDRecommender
@Override public float estimatePreference(longuserID, long itemID) throws TasteException { double[] userFeatures =factorization.getUserFeatures(userID); double[] itemFeatures =factorization.getItemFeatures(itemID); double estimate =0; for (int feature = 0;feature < userFeatures.length; feature++) { estimate += userFeatures[feature] * itemFeatures[feature]; } return (float)estimate; }测试程序:
public static voidsvd(DataModel dataModel) throws TasteException { RecommenderBuilder recommenderBuilder =RecommendFactory.svdRecommender(new ALSWRFactorizer(dataModel, 10,0.05, 10));
RecommendFactory.evaluate(RecommendFactory.EVALUATOR.AVERAGE_ABSOLUTE_DIFFERENCE,recommenderBuilder, null, dataModel, 0.7); RecommendFactory.statsEvaluator(recommenderBuilder, null,dataModel, 2);
LongPrimitiveIterator iter =dataModel.getUserIDs(); while (iter.hasNext()) { long uid =iter.nextLong(); List list= recommenderBuilder.buildRecommender(dataModel).recommend(uid,RECOMMENDER_NUM); RecommendFactory.showItems(uid, list, true); } }程序输出:
AVERAGE_ABSOLUTE_DIFFERENCE EvaluaterScore:0.09990564982096355Recommender IR Evaluator: [Precision:0.5,Recall:1.0]uid:1,(104,4.032909)(105,3.390885)(107,1.858541)uid:2,(105,3.761718)(106,2.951908)(107,1.561116)uid:3,(103,5.593422)(102,2.458930)(106,-0.091259)uid:4,(105,4.068329)(102,3.534025)(107,0.206257)uid:5,(107,0.105169)10. Tree Cluster-based 推荐算法这个算法在mahout-0.8版本中,已经被@Deprecated。(TODO未完)算法API:org.apache.mahout.cf.taste.impl.recommender.TreeClusteringRecommender
@Override public float estimatePreference(longuserID, long itemID) throws TasteException { DataModel model =getDataModel(); Float actualPref =model.getPreferenceValue(userID, itemID); if (actualPref != null){ return actualPref; } buildClusters(); List topRecsForUser =topRecsByUserID.get(userID); if (topRecsForUser !=null) { for(RecommendedItem item : topRecsForUser) { if (itemID == item.getItemID()) { return item.getValue(); } } } // Hmm, we have no idea.The item is not in the user's cluster return Float.NaN; }测试程序:
public static voidtreeCluster(DataModel dataModel) throws TasteException { UserSimilarity userSimilarity =RecommendFactory.userSimilarity(RecommendFactory.SIMILARITY.LOGLIKELIHOOD,dataModel); ClusterSimilarity clusterSimilarity =RecommendFactory.clusterSimilarity(RecommendFactory.SIMILARITY.FARTHEST_NEIGHBOR_CLUSTER,userSimilarity); RecommenderBuilder recommenderBuilder =RecommendFactory.treeClusterRecommender(clusterSimilarity,10);
RecommendFactory.evaluate(RecommendFactory.EVALUATOR.AVERAGE_ABSOLUTE_DIFFERENCE,recommenderBuilder, null, dataModel, 0.7); RecommendFactory.statsEvaluator(recommenderBuilder, null,dataModel, 2);
LongPrimitiveIterator iter =dataModel.getUserIDs(); while (iter.hasNext()) { long uid =iter.nextLong(); List list= recommenderBuilder.buildRecommender(dataModel).recommend(uid,RECOMMENDER_NUM); RecommendFactory.showItems(uid, list, true); } }程序输出:
AVERAGE_ABSOLUTE_DIFFERENCE Evaluater Score:NaNRecommender IR Evaluator: [Precision:NaN,Recall:0.0]11. Mahout推荐算法总结算法及适用场景:算法评分的结果:通过对上面几种算法的一平分比较:itemCF,itemKNN,SVD的Rrecision,Recall的评分值是最好的,并且itemCF和SVD的AVERAGE_ABSOLUTE_DIFFERENCE是最低的,所以,从算法的角度知道了,哪个算法是更准确的或者会索引到更多的数据集。另外的一些因素:1. 这3个指标,并不能直接决定计算结果一定itemCF,SVD好2. 各种算法的参数我们并没有调优3. 数据量和数据分布,是影响算法的评分WATERFU65转 译者:July 2015/1/22
更多阅读
积极人生的十种力量 积极人生十种力量ppt
在职场工作大半辈子,我见过许多才华横溢、能干精明的同事,他们既有大本领,也有大脾气。在一件又一件的成功事迹背后,他们也得罪了一批又一批的同事、战友、最终路越走越窄,怨恨有志难伸。英文里有一句话:Results and Relationships, and n
《奇怪的大石头》评课稿 奇怪的大石头ppt课件
评左旭日的《奇怪的大石头》前段时间听了几位教师的示范课,总的来说老师们的课堂是扎实高效的。对文本的把握到位,教学环节的丝丝入扣,使本篇课文重难点上的突破水到渠成。这是对教材的有效解读。其次,课堂上孩子们自主探究的学习方式
杨梅的吃法收集整理 数据的收集与整理ppt
夏日炎炎,正是杨梅成熟的季节。酸甜的杨梅不仅仅是有消暑的功能喔,让我们来看一下下面这段介绍吧。杨梅营养成份 杨梅每100克鲜果含水分91.l克,蛋白质0.9克,脂肪0.9克,碳水化合物5.2克,热量33千卡,粗纤维1.0克,灰分0.9克,钙11毫克,磷36毫克,铁1
《祭十二郎文》赏析 祭十二郎文ppt
《祭十二郎文》原文年、月、日,季父愈闻汝丧之七日,乃能衔哀致诚,使建中远具时羞之奠,告汝十二郎之灵:呜呼!吾少孤,及长,不省所怙,惟兄嫂是依。中年,兄殁南方,吾与汝俱幼,从嫂归葬河阳。既又与汝就食江南。零丁孤苦,未尝一日相离也。吾上有三兄,
金黄的大斗笠 金黄的大斗笠ppt
金黄的大斗笠教学目标:① 知识和技能:整体感悟课文内容,能用普通话正确、流利、有感情地朗读课文,能理解重点字词。② 过程和方法:学习并运用朗读的方法,运用自主合作探究的学习方法。③ 情感态度价值观:理解风雨画面的描写,体会姐弟俩