推荐算法学习系列 4:从VQ-VAE生成模型到生成式推荐

3,403 阅读14分钟

想到VAE大家一般会想到计算机视觉相关任务,但最近许多生成式推荐都前沿工作也开始使用类似的思想。

在这篇文章中,我将先以易懂的逻辑带领大家一步一步领悟VQ-VAE的核心思想,再介绍VQ-VAE中关键算法的具体形式,最后对RQ-VAE在生成式推荐中的应用进行讲解。

从AE到VQ-VAE

AE

AE是一类能够把图片压缩成较短的向量的神经网络模型,其结构如下图所示。AE包含一个编码器和一个解码器。在训练时,输入图像会被编码成一个较短的向量,再被解码回另一幅长得差不多的图像。网络的学习目标是让重建出来的图像和原图像尽可能相似。

image.png

解码器可以把一个向量解码成图片。换一个角度看,解码器就是一个图像生成模型,因为它可以根据向量来生成图片。那么,AE可不可以用来做图像生成呢?很可惜,AE的编码器编码出来的向量空间是不规整的。也就是说,解码器只认识经编码器编出来的向量,而不认识其他的向量。如果你把自己随机生成出来的向量输入给解码器,解码器是生成不出有意义的图片的。AE不能够随机生成图片,所以它不能很好地完成图像生成任务,只能起到把图像压缩的作用。

VAE

AE离图像生成只差一步了。只要AE的编码空间比较规整,符合某个简单的数学分布(比如最常见的标准正态分布),那我们就可以从这个分布里随机采样向量,再让解码器根据这个向量来完成随机图片生成了。VAE就是这样一种改进版的AE。它用一些巧妙的方法约束了编码向量,使得满足标准正态分布。这样,解码器不仅认识编码器编出的向量,还认识其他来自标准正态分布的向量。训练完成后,我们就可以扔掉编码器,用来自标准正态分布的随机向量和解码器来实现随机图像生成了。

image.png

VAE的实现细节就不在这里赘述了,是否理解它对理解VQ-VAE没有影响。我们只需知道VAE可以把图片编码成符合标准正态分布的向量即可。让向量符合标准正态分布的原因是方便随机采样。同时,需要强调的是,VAE编码出来的向量是连续向量,也就是向量的每一维都是浮点数。如果把向量的某一维稍微改动0.0001,解码器还是认得这个向量,并且会生成一张和原向量对应图片差不多的图片。

VQ-VAE

但是,VAE生成出来的图片都不是很好看。VQ-VAE的作者认为,VAE的生成图片之所以质量不高,是因为图片被编码成了连续向量。而实际上,把图片编码成离散向量会更加自然。比如我们想让画家画一个人,我们会说这个是男是女,年龄是偏老还是偏年轻,体型是胖还是壮,而不会说这个人性别是0.5,年龄是0.6,体型是0.7。因此,VQ-VAE会把图片编码成离散向量,如下图所示。

image.png

把图像编码成离散向量后,又会带来两个新的问题。第一个问题是,神经网络会默认输入满足一个连续的分布,而不善于处理离散的输入。如果你直接输入0, 1, 2这些数字,神经网络会默认1是一个处于0, 2中间的一种状态。为了解决这一问题,我们可以借鉴NLP中对于离散单词的处理方法。为了处理离散的输入单词,NLP模型的第一层一般都是词嵌入层,它可以把每个输入单词都映射到一个独一无二的连续向量上。这样,每个离散的数字都变成了一个特别的连续向量了。我们可以把类似的嵌入层加到VQ-VAE的解码器前。这个嵌入层在VQ-VAE里叫做embedding space(嵌入空间),在下文中则被称作codebook

image.png

离散向量的另一个问题是它不好采样。VAE之所以把图片编码成符合正态分布的连续向量,就是为了能在图像生成时把编码器扔掉,让随机采样出的向量也能通过解码器变成图片。现在倒好,VQ-VAE把图片编码了一个离散向量,这个离散向量构成的空间是不好采样的。

VQ-VAE面临着和AE一样的问题,这个问题是无解的。因此,VQ-VAE根本不是一个图像生成模型。它和AE一样,只能很好地完成图像压缩,把图像变成一个短得多的向量,而不支持随机图像生成。VQ-VAE和AE的唯一区别,就是VQ-VAE会编码出离散向量,而AE会编码出连续向量。

因此,VQ-VAE不是一个VAE,而是一个AE。它的目的是把图像压缩成离散向量。或者换个角度说,它提供了把大图像翻译成「小图像」的方法,也提供了把「小图像」翻译成大图像的方法。这样,一个随机生成大图像的问题,就被转换成了一个等价的随机生成一个较小的「图像」的问题。

VQ-VAE的相关计算可以看苏神讲解,个人觉得很好很清楚,建议看完这个再看RQ-VAE,会便于理解。🔗:www.spaces.ac.cn/archives/67…

从RQ-VAE到生成式推荐

然而,大图像压缩成小图像的方法在推荐系统中非常适用。基于 LLM 的推荐系统中,采用原始的物品 ID将导致词汇表非常大,因此一个首要问题是如何使用索引 ID 表示物品,并将这些物品索引集成到 LLM 中。

一个好的物品索引构建方法至少应满足两个标准:1)保持合适的长度以减轻文本生成的难度。 2)将先验信息集成到物品索引结构中,以确保相似项目在可区分的同时共享最多的token,不相似项目共享最少的token。

在此之前有几种构造item标识符的方法,一种的数字ID,一种是文本元数据,这两种方法存在一定的缺陷。例如,数字ID不能很好的解决冷启问题,文本元数据对于一词多义现象不能很好区分。

那么有没有一种方法能够满足以上两个标准呢?Recommender Systems with Generative Retrieval提供了一种很好的思路:使用RQ-VAE模型进行Semantic ID的生成

RQ-VAE & Semantic ID

具体来说,我们将LLM编码的物品文本嵌入作为输入,然后训练残差量化变分自动编码器(Residual-Quantized Variational AutoEncoder,RQ-VAE)来生成物品索引。残差量化变分自动编码器(RQ-VAE)是一种多级向量量化器,它将残差矢量从粗到细递归量化,以生成一组码字 (也就是物品索引)。其核心思想是,相似的物品共享一部分语义索引,这样每个语义索引都可以与某种潜在的语义对齐

image.png

针对物品的嵌入方式 ee,RQ-VAE 首先将它编码到潜在语义空间 zz。在每索引的一级hh,我们有一个codebook Ch={vkh}k=1K\mathcal{C}^{h}=\{\mathbf{v}_{k}^{h}\}_{k=1}^{K},其中每个码本向量 vkh{v}_{k}^{h} 是一个可学习的聚类中心。则残差量化过程可以表示为:

ci=argminkrivki22,ri+1=rivcii,\begin{aligned}&c_{i}=\arg\min_{k}||\mathbf{r}_{i}-\mathbf{v}_{k}^{i}||_{2}^{2},\\&\mathbf{r}_{i+1}=\mathbf{r}_{i}-\mathbf{v}_{c_{i}}^{i},\end{aligned}

其中cic_i是物品索引的第ii个码字,ri\mathbf{r}_i是第ii个RQ 级别中的残差向量,r1=z\mathbf{r}_1=\mathbf{z}。当我们有HH级的codebook 时,则可该过程递归地重复HH次,以获得表示语义ID的HH个码字的元组,可根据z^=i=1Hvcii\hat{\mathbf{z}}=\sum_{i=1}^H\mathbf{v}_{c_i}^i获得z\mathbf{z}的量化表示。接下来z^\hat{\mathbf{z}}将用作解码器输入以重构物品嵌入 ee 。最终损失函数如下:

LRECON=ee^22,LRQ=i=1Hsg[ri]vcii22+βrisg[vcii]22,LRQVAE=LRECON+LRQ,\begin{aligned} \mathcal{L}_{\mathrm{RECON}}& =||\mathbf{e}-\hat{\mathbf{e}}||_{2}^{2}, \\ \mathcal{L}_{\mathrm{RQ}}& =\sum_{i=1}^{H}||\mathrm{sg}[\mathbf{r}_{i}]-\mathbf{v}_{c_{i}}^{i}||_{2}^{2}+\beta ||\mathbf{r}_{i}-\mathrm{sg}[\mathbf{v}_{c_{i}}^{i}]||_{2}^{2}, \\ \mathcal{L}_{\mathrm{RQ-VAE}}& =\mathcal{L}_{\mathrm{RECON}}+\mathcal{L}_{\mathrm{RQ}}, \end{aligned}

其中e^\hat{\mathrm{e}}表示解码器的输出,sg[·] 表示梯度停止(stop gradient),β\beta是一个损失系数,通常设置为 0.25。总体损失分为两部分,LRECON\mathcal{L}_\mathrm{RECON}是 AutoEncoder 的重构损失,LRQ\mathcal{L}_\mathrm{RQ}用于最小化码本向量和残差矢量之间的距离。

请注意,我们选择为HH个级别中的每个级别使用大小为K的单独码本,而不是使用单个大小为HKHK的码本。这样做是因为残差的范数往往随着级别的增加而减小,因此允许不同级别的不同粒度。

为了防止RQ-VAE发生码本崩溃(大多数输入仅映射到少数码本向量),使用k均值聚类来初始化码本,将k-means算法应用于第一个训练批次(first training batch),并使用质心作为初始化。当然除了使用RQ-VAE,也可以使用其他的向量化方法,如LSH等 而是使用矢量量化(Vector Quantization,VQ)技术来表示具有离散索引的物品。

对于以上过程,还有一点需要考虑,即冲突数据问题,上述从粗到细的量化方法产生了树结构的物品索引,但这可能会导致同一叶子节点内的物品产生索引冲突。

对于冲突的解决,现有方法主要有:

  • TIGER等采取的方案:对有冲突的商品增加随机的一维,使得一个SID唯一对应一个商品。需要维护一个将语义ID映射到相应item的查找表。
  • LC-Rec等采取的方案:通过均匀语义映射缓解冲突,这个方法具体可以看论文,这里不详细赘述

生成式推荐

语义对齐

Semantic ID用于LLM做生成式推荐之前,还有一个问题需要考虑:这些物品索引本质上是 LLM 的 Out-Of-Vocabulary(OOV)Token,因此需要进行语言和协同语义的对齐。语义对齐任务主要包括以下:包括序列物品预测、显式索引-语言对齐(通过其索引识别相应物品),以及面向推荐的隐式对齐(增强 LLM 对语言和协同语义的理解)。

image.png

  • 序列物品预测

由于我们的目标任务是序列推荐,因此以序列物品预测作为主要微调目标,根据用户当前的历史交互构建个性化推荐指令,LLM预测用户可能交互的下一个物品。

指令示例如下:

{
    "instruction": "该用户性别为女,年龄为46-55岁,婚姻状况为已婚,有无子女状况为未知。用户已按时间顺序点击了如下商品:<a_112><b_238><c_33><d_113>, <a_73><b_50><c_228><d_128>, <a_20><b_251><c_30><d_178>, <a_142><b_216><c_7><d_136>, <a_190><b_171><c_15><d_201>, <a_72><b_160><c_20><d_248>, <a_158><b_101><c_54><d_107>, <a_175><b_4><c_75><d_138>, <a_142><b_20><c_175><d_136>, <a_210><b_166><c_67><d_44>, <a_10><b_89><c_96><d_143>, <a_27><b_45><c_21><d_212>, <a_142><b_27><c_192><d_159>,你能预测用户下一个可能点击的商品吗?",
    "response": "<a_96><b_113><c_49><d_174>"
}

然而,简单地将 LLM 在上述目标任务上微调,往往仅能建立索引到索引的协同语义关系,并未实现 LLM 中语言和协同语义的对齐。为此,下面我们从两个方面增强语言语义和协同语义的集成。

  • 显式索引-语言对齐

尽管我们的物品索引是基于物品的标题和描述构建的,但它们仅依赖于共享部分前缀索引以在具有相似语言语义的物品之间建立弱相关性。为了进一步赋予物品索引语言语义,我们提出了两个显式索引-语言对齐任务:

  1. 基于相关的标题或描述准确地识别物品索引
{
    "instruction": "哪个商品的标题是‘ss109威震天变形MP威震玩具天金刚飞机威男孩机器人战机模型合金 震天战机(战损涂装版)’?",
    "response": "<a_91><b_24><c_66><d_5>"
}
  1. 基于物品索引捕获相关物品信息
{
    "instruction": "商品<a_99><b_225><c_67><d_242>的标题是什么?",
    "response": "ThinkPad 联想ThinkBook 14+ 2024 14.5英寸轻薄本英特尔酷睿ultra AI全能本高性能独显商务办公笔记本电脑 Ultra5 125H 32G 1T 3K屏 高刷屏"
}
  • 面向推荐的隐式对齐

在这一部分中,我们进一步通过面向推荐的对齐任务来增强模型能力,以便LLM能够更好地利用语言和协同语义。具体而言,我们设计了以下三个对齐任务:

  1. 非对称物品预测

对于序列物品预测,交互历史(条件)和目标物品都以物品索引的形式表示,为了进一步增强语义对齐,我们通过改变条件和目标的表示形式来增加预测难度,迫使 LLM 统一物品索引、语言语义和协同语义来完成推荐任务:

{
    "instruction": "该用户性别为女,年龄为46-55岁,婚姻状况为已婚,有无子女状况为未知。用户已按时间顺序点击了如下商品:<a_112><b_238><c_33><d_113>, <a_73><b_50><c_228><d_128>, <a_20><b_251><c_30><d_178>, <a_142><b_216><c_7><d_136>, <a_190><b_171><c_15><d_201>,你能预测用户下一个可能点击的商品的标题吗?",
    "response": "ss109威震天变形MP威震玩具天金刚飞机威男孩机器人战机模型合金 震天战机(战损涂装版)"
}
{
    "instruction": "该用户性别为女,年龄为46-55岁,婚姻状况为已婚,有无子女状况为未知。用户已按时间顺序点击了如下商品:‘ThinkPad 联想ThinkBook 14+ 2024 14.5英寸轻薄本英特尔酷睿ultra AI全能本高性能独显商务办公笔记本电脑 Ultra5 125H 32G 1T 3K屏 高刷屏’、...,你能预测用户下一个可能点击的商品吗?",
    "response": "<a_96><b_113><c_49><d_174>"
}
  1. 基于用户意图的物品预测

现实生活中的推荐系统应该具备理解用户实际意图并提供高质量推荐的能力,参考 InstructRec (Recommendation as Instruction Following) 中的方法,我们从目标物品的相关评论中提取用户意图(使用 GPT-3.5),然后基于用户意图实现物品预测:

{
    "instruction": "某件商品的评论中存在如下描述:'一直很喜欢联想品牌的产品,购买这台联想电脑独显商务本,14.5英寸大小合适,笔记本轻薄便携',根据以上描述推测是哪款商品",
    "response": "<a_99><b_225><c_67><d_242>"
}
  1. 个性化偏好推断

用户的交互历史可以反映他/她的个性化偏好,而数据集中通常没有明确的偏好信息,因此,我们同样使用 GPT-3.5 从用户过去交互过的物品标题中推断其偏好,之后利用我们的模型基于历史交互物品的索引序列而不是标题序列来推断用户偏好:

{
    "instruction": "该用户性别为女,年龄为46-55岁,婚姻状况为已婚,有无子女状况为未知。用户已按时间顺序点击了如下商品:<a_112><b_238><c_33><d_113>, <a_73><b_50><c_228><d_128>, <a_20><b_251><c_30><d_178>, <a_142><b_216><c_7><d_136>, <a_190><b_171><c_15><d_201>,你能分析一下用户的偏好吗",
    "response": "用户偏向于购置家庭产品,包括家居日用品和儿童玩具类产品..."
}

受限生成

为了实现物料推荐,生成式推荐系统在推理阶段需要对生成结果进行定位,即实现生成的物料标识符与数据集中物料的有效关联。给定用户输入表示,生成式推荐系统首先通过束搜索自回归地生成物料标识符。这里的生成方式分为两种:自由生成和受限生成。

  • 自由生成:在每一个解码步中,模型在整个词表中搜索,并选择概率最高的前K个token(K值取决于束搜索中定义的束大小)作为下一步生成的输入。然而,在整个词表上的搜索可能会导致生成不在数据集中的标识符,从而使推荐无效。

  • 受限生成:为了解决这个问题,早期工作使用精确匹配进行物料定位,即进行自由生成并简单地丢弃无效的标识符。尽管如此,它们仍然由于无效标识符而导致准确率低,特别是对于基于文本元数据的标识符。为了提高准确性,BIGRec提出将生成的标识符通过生成的token序列的表示和物料表示之间的L2距离来定位到有效物料上。如此,每个生成的标识符都确保被定位到有效的物料上。与此同时,受限生成也在推理阶段被使用,例如,使用Trie(prefix tree)或者FM-index进行受限生成,保证标识符的有效生成。

此外,序列物品预测过程中,除了预测下一个物料这样的典型推荐任务之外,也可充分利用自由生成产生新的物料描述或预测接下来N个物料。

参考文献