推荐系统设计

当一个做推荐系统的部门开始重视【数据清理,数据标柱,效果评测,数据统计,数据分析】这些所谓的脏活累活,这样的推荐系统才会有救。

推荐系统特征

首先需要明确的就是推荐系统的目标,一般来说不外乎以下几个:

  • 用户满意性:首当其冲的,推荐系统主要就是为了满足用户的需求,因此准确率是评判一个推荐系统好坏的最关键指标。

  • 多样性:虽然推荐系统最主要还是满足用户的兴趣,但是也要兼顾内容的多样性,对于权重不同的兴趣都要做到兼顾。

  • 新颖性:用户看到的内容是那些他们之前没有听说过的物品。简单的做法就是在推荐列表去掉用户之前有过行为的那些内容。

  • 惊喜度:和新颖性类似,但新颖性只是用户没看到过的但是确实是和他行为是相关的,而惊喜度是用户既没有看过和他之前的行为也不相关,但用户看到后的确是喜欢的。

  • 实时性:推荐系统要根据用户的上下文来实时更新推荐内容,用户的兴趣也是随着时间而改变的,需要实时更新。 

  • 推荐透明度:对于用户看到的最终结果,要让用户知道推荐此内容的原因。比如,“买过这本书的人同时也买过”、”你购买过的xx和此商品类似”。 

  • 覆盖率:挖掘长尾内容也是推荐系统很重要的目标。因此,推荐的内容覆盖到的内容越多越好。

推荐方式

基于这些目标,推荐系统包括四种推荐方式:

  • 热门推荐:就是热门排行榜的概念。这种推荐方式不仅仅在IT系统,在平常的生活中也是处处存在的。这应该是效果最好的一种推荐方式,毕竟热门推荐的物品都是位于曝光量比较高的位置的。 

  • 人工推荐:人工干预的推荐内容。相比于依赖热门和算法来进行推荐。一些热点时事如世界杯、nba总决赛等就需要人工加入推荐列表。另一方面,热点新闻带来的推荐效果也是很高的。 

  • 相关推荐:相关推荐有点类似于关联规则的个性化推荐,就是在你阅读一个内容的时候,会提示你阅读与此相关的内容。

  • 个性化推荐:基于用户的历史行为做出的内容推荐。 

其中,前三者是和机器学习没有任何关系的,但却是推荐效果最好的三种方式。一般说来,这部分内容应该占到总的推荐内容的80%左右,另外20%则是个性化推荐。

个性化推荐系统

个性化推荐是机器学习应用的一个典型场景。在本质上和搜索引擎是一样的,同样是为了解决信息过载的问题。搜索引擎某种意义上也是一个个性化推荐系统,但是其输入特征是可以从搜索关键字直接可以得到的,而一般的推荐系统,输入特征则是需要机器学习才能得到

个性化推荐系统一般由日志系统推荐算法内容展示UI三部分组成。

  • 日志系统:这是推荐系统的输入源,是一个推荐系统所有信息的源头。

  • 推荐算法:这是推荐系统的核心,根据输入数据得出最终的推荐结果的具体过程就在这里。 

  • 内容展示UI:对于推荐结果如何展示,也是一个值得权衡的地方。以更好地满足推荐系统的目标,并能更好的收集用户的行为信息等。

其中,个性化推荐中最为核心的推荐算法,目前比较流行的有以下几种:

  • 基于内容的推荐:根据内容本身的属性(特征向量)所作的推荐。 

  • 基于关联规则的推荐:“啤酒与尿布”的方式,是一种动态的推荐,能够实时对用户的行为作出推荐。是基于物品之间的特征关联性所做的推荐,在某种情况下会退化为物品协同过滤推荐。 

  • 协同过滤推荐:与基于关联规则的推荐相比是一种静态方式的推荐,是根据用户已有的历史行为作分析的基础上做的推荐。可分为物品协同过滤用户协同过滤基于模型的协同过滤。其中,基于模型的协同又可以分为以下几种类型:基于距离的协同过滤;基于矩阵分解的协同过滤,即Latent Factor Model(SVD);基于图模型协同,即Graph,也叫社会网络图模型。

基于内容的推荐

通过用户历史感兴趣的信息,抽象信息内容共性(特征向量),根据内容共性推荐其他信息。

如何给一用户推荐租房信息,简要步骤如下

  • 找到用户A最近一个月内浏览过的租房信息集合

  • 找到租房集合的具化内容(价格,平方,地理位置等)

  • 抽象具化内容的共性内容 -- (2000每月,50平方,下城区)

  • 由这些共性内容作为推荐条件查找其他租房信息,并实施推荐

如果查询的结果集过小,可以缩小条件(降低抽象具化内容的共性内容的标准)召回,例如可以将查询条件缩小为(2000每月,50平方,无限制)或(2000每月,无限制,无限制)。

协同过滤

通过找到兴趣相投,或者有共同经验的群体,来向用户推荐感兴趣的信息。

如何通过协同过滤对用户A进行电影推荐?简要步骤如下

  • 找到用户A(user_id_1)的兴趣爱好

  • 找到与用户A(user_id_1)具有相同电影兴趣爱好的用户群体集合Set<user_id>

  • 找到该群体喜欢的电影集合Set<movie_id>

  • 将这些电影Set<Movie_id>推荐给用户A(user_id_1)

相似性推荐

“协同过滤(Collaborative Filtering)”和“基于内容的推荐(Content-based Recommendation)”,都必须分析用户的历史行为数据。如果系统没有用户的历史行为数据积累,如何实施推荐呢?对于新用户A,没有ta的历史行为数据,在ta点击了item-X的场景下,可以将与item-X最相似的item集合推荐给新用户A。问题可以转化为如何用一种通用的方法,表达item之间的相似性?

譬如租房有价格,地理位置,设施配套,大小,周边交通等属性,假设这里是5个属性,可以把它看做一个五维空间中的点。

点击了《戈雅公寓10幢304室》假设为点N {价格:5000,地理位置:浦沿,大小:50m2,设置配套:空调洗衣机衣柜,周边交通:地铁}

给每个属性设置权重,价格相同加5分,地理位置相近加3分,大小匹配加1分等。

求与点N距离最近的10个点,点《戈雅公寓10幢305室》的distance = f1(价格) + f2(地理位置) + … +f5(大小)=5 + 3 + … + 1=9

相似性推荐,原理大致如上,要说明的是:

  • 由于没有用户历史行为积累,不是个性化推荐,所以所有用户的推荐结果都是相同的

  • 一般来说,距离公式确实是线性的

  • 一般来说,每个维度的权重不一样

  • 这个线性公式,以及维度的权重,都可以通过机器学习训练出来

关联规则

关联规则是数据挖掘中的概念,通过分析数据,找到数据之间的关联。电商中经常用来分析购买物品之间的相关性,例如,“购买尿布的用户,有大概率购买啤酒”,这就是一个关联规则。关联规则推荐的目标,是希望达到“将尿布放入购物车之后,再推荐啤酒”“直接推荐啤酒”获取有更好的售卖效果

关联规则A->B推荐,目标是,在“用户将A放入购物车时,推荐B”比“单独推荐B”获取更好的效果

  • A->B的支持度,是用户同时购买A和B概率

  • A->B的置信度,是用户购买A的同时,有多大概率购买B

  • A->B的提升度,是“用户购买A的同时,有多大概率购买B”与“直接购买B的概率”的比值

    • 这个值大于1时,说明A->B有正向效果
    • 这个值等于1时,说明A和B是独立事件
    • 这个值小于1时,说明A->B有负向效果

支持度(support)

s(A)=3/5,s(B)=3/5,s(c)=1,s(D)=2/5,s(AB)=2/5,s(AC)=3/5。s(AB)等于同时购买A和B的数量除以总订单量。

支持度评估商品包含在订单中的“概率”,一个订单,有多大概率包含这个商品。一般会先对支持度高的商品实施推荐,如果先实优化支持度低的商品,即使推荐效果翻倍,总体订单提升效果也会很有限。

置信度(confidence):c(A->B) = s(AB)/s(A)= (2/5)/(3/5) = 2/3

  • 分子:s(AB)是同时购买AB的比例

  • 分母:s(A)是只购买A的比例

二者相除,得到“购买了A,有多大概率购买B”,置信度的本质是条件概率

c(C->B) = s(BC)/s(C)= (3/5)/(1) = 3/5  购买了C,有多大概率购买B

c(B->C) = s(BC)/s(B)= (3/5)/(3/5) = 1   购买了B,有多大概率购买C

c(B->C)=1,即:如果用户购买商品B,100%会买C,那是不是意味着,如果用户将商品B放入购物车,就可以向用户推荐商品C呢?

结合关联规则的目标,虽然c(B->C)=1购买商品B,100%会买C,但s(C)=1直接推荐C,用户也100%会买C。购买B与购买C是独立事件,用户买不买C和用户买不买B没有直接关系。这里的关联规则推荐,并没有比直接推荐获取更好的效果。用什么指标来评估关联规则推荐的效果呢?提升度!

提升度(lift):l(A->B) =c(A->B)/s(B)

  • 分子:c(A->B),购买A时,有多大概率同时购买B

  • 分母:s(B),有多大概率直接购买B

A->B关联规则推荐c(A->B),与s(B)直接推荐B,的比值,可以用来评估推荐效果:

  • 大于1,说明有效,在购买A时推荐B,比直接推荐B,效果更好

  • 等于1,说明无关,购买A与购买B,是独立事件

  • 小于1,说明负相关,购买A时推荐B,效果还不如直接推荐B

个性化推荐典型流程

可知,一个推荐系统主要有以下模块组成

  • 用户行为日志:此部分主要是用户行为日志的存储,属于数据统计的一部分, 存储在hive中。 

  • 数据ETL-1:将用户日志转换为推荐算法所需要的数据格式。对原始的用户行为等数据进行清洗、加工,如字段、属性、格式化等,作为下一步推荐算法的输入。

  • 推荐算法:是个性化推荐最主要的部分,包括通过用户行为计算相关内容以及推荐结果等。 

  • 数据ETL-2: 将推荐算法得到的结果进一步加工为存储模块的输入数据。对推荐算法产生的结果进行清洗、格式化等,作为下一步存储模块的输入。

  • 用户画像存储:存储用户的偏好以及行为数据,如对内容关键字的偏好、点击过哪些内容等。

  • 推荐结果存储:存储各种推荐算法产生的推荐结果,可以分为两部分:{用户 : itemList}推荐结果,为用户推荐的内容列表;{item : itemList}推荐结果,与item相关的内容列表。

  • 服务调用模块:整合推荐结构,对外提供提供推荐的调用接口。

用户行为日志接入

在线业务系统的日志接入数据高速公路,再由数据高速公路迅速运转到离线数据处理平台和在线流计算平台;离线数据处理平台周期性地以批处理方式加工过去一段时间的数据,得到人群标签和其他模型参数,存放在高速缓存中,供在线业务系统使用,与此同时,在线流计算平台实时对线上的日志数据做处理,对离线计算出的数据进行补充、修正等;在线业务系统综合离线特征和在线特征使用一定的逻辑得到输出供业务使用,产生的日志流入数据高速公路。

推荐算法

对于个性化推荐系统来说,推荐算法应该是其最核心的部分。目前有很多流行的算法,比如:

  • 基于内容和用户画像的推荐:此种算法,http://www.rowkey.me/blog/2016/04/07/up-recommend/。

  • 基于矩阵分解的推荐: 基于SVD/ALS算法对用户进行内容推荐。相比起SVD,ALS更加适合解决稀疏矩阵的问题。Spark mlib中已经集成了对als算法的实现,需要做的就是在etl-1中把数据转换为als需要的数据格式以及调整als算法的各种参数。有一篇文章比较具体地描述了如何使用spark来做基于ALS的推荐:http://colobu.com/2015/11/30/movie-recommendation-for-douban-users-by-spark-mllib/。

  • 用户&物品协同过滤推荐:包括UserBased CF和ItemBased CF。对于这两者,需要根据业务的不同来选择不同的算法。当用户非常多的时候,考虑到维护用户矩阵的成本,一般是不推荐选择用户协同过滤的,而对于候选item很多的时候,则不推荐使用物品协同过滤。

推荐算法的输出结果一般是一个用户对应一个item列表或者是一个item对应一个item列表。此部分主要考虑的是算法的时间复杂度,不管是哪一种算法,一旦用户或者内容数据上了百万级别,都需要通过分布式计算如MapReduce、Spark等来进行解决。

推荐算法的基本流程如下图所示:

用户画像存储

存储用户的偏好以及行为数据等信息。对于偏好,采用标签量化来表示,是一种随着时间衰减的值。对于用户画像,是批量写入、实时读取,所以存储要着重考虑读的性能。可以选择使用Redis集群作为技术方案,能够最大满足读的性能,缺点是Redis的成本昂贵且不支持auto index。也可使用Hbase作为存储,使用ElasricSearch构建二级索引,以应对根据多种维度聚集用户的需求(比如过滤某一个标签下的所有用户)。

推荐结果存储

对各种推荐算法计算出的推荐结果的存储。存储空间要求大,格式复杂。对于存储的容量和读写性能要求都比较高。可以选择使用Redis集群作为此部分的存储方案。

服务调用

整合用户画像和推荐结果两部分数据,向外提供推荐调用的接口。主要是数据库IO调用开销。

  • 根据用户id,获取推荐的item列表。

  • 根据item,获取相关联的item列表。

  • 根据用户id, 获取用户画像。

该模块需要采取一定的策略聚合多种推荐算法的推荐结果,直接面向业务。策略由于会随着面向的业务不同而不同,需要可配置化。同时也提供对外暴露用户画像的接口,使得业务方可以使用用户画像做针对性的处理。可以采用RPC机制对外暴露服务接口。

关注问题

实时性问题

由于计算用户、item矩阵或者进行矩阵分解是需要离线进行且比较耗时,因此协同的推荐算法是很难达到实时性的。实时部分的推荐主要依靠基于用户画像的推荐来进行。最终的推荐列表是根据一定的策略对这两部分进行聚合的结果。

时效性内容问题

时效性内容指的是那些与时间强相关的内容,比如新闻、时事等。如果一条10天前xx球员获得冠军的新闻现在被推荐了出来,可想用户肯定是莫名其妙或者是很失望的。因此,对于时效性内容,需要与普通的待推荐的内容区分开,做单独的推荐或者不走个性化推荐。

冷启动问题 

不管使用何种推荐算法,都会面临冷启动问题:当用户是新用户,如何给用户推荐item呢?当内容是新内容,如何推荐给用户?

  • 对于新用户,可以采取的一种策略就是采用热门推荐或者人工推荐,把绝大多人关心的内容推荐出来。

  • 对于内容,可以将内容分为新内容池和待推荐内容池。新内容产生时,首先进入新内容池。每次推荐的时候,先从新内容池做候选推荐,并给此内容的传播度+1,直到其传播度大于一个阈值的时候,将其移至待推荐内容池。这样既可以解决新内容的冷启动问题也在一定程度上可以保证新内容的曝光量。 

多样性问题 

在基于用户画像的推荐算法中,取出用户的多个标签,然后根据相关度从不同的标签中取不同数量的内容,这样既兼顾了用户的多种兴趣也能够在一定程度上解决多样性的问题。

如:用户具有tag:A B C D,相关度为wA wB wC wD,Total推荐为总共需要推荐的条数,那么

RecommendList(u) = A[Total推荐 * wA] + B[Total推荐 * wB] + C[Total推荐 * wC] + D[Total推荐 * wD]

内容质量 

不管是热门推荐、人工推荐还是取某一标签下的内容列表都牵扯到的一个问题就是:如何给内容排序?

当用户对内容的喜好不一样,可以按照兴趣度来排序;但当无法区分兴趣度的时候(比如:用户是新用户;内容都是新内容;用户对于某一标签下的内容兴趣度一样),可以使用内容质量来做排序。click/pv是一种评判内容质量的方式。此外,使用卷积神经网络相关算法也可以构建内容质量模型。

惊喜问题

推荐系统的惊喜目标一直是一个难题,被称作EE(Exploit & Explore)问题,bandit算法是解决这个问题的一个派系,就是估计置信区间的做法,然后按照置信区间的上界来进行推荐,以UCB、LinUCB为代表的。简单点说就是先不考虑你喜不喜欢就把质量高的内容推荐给你,后面根据用户的行为反馈对推荐内容作调整。 

 

posted @ 2017-01-31 18:46  wade&luffy  阅读(9619)  评论(0编辑  收藏  举报