FM系列算法解读(FM+FFM+DeepFM)

综述

  在计算广告中,CTR是非常重要的一环。对于特征组合来说,业界通用的做法主要有两大类:FM系列和Tree系列。这里我们来介绍一下FM系列。
  在传统的线性模型中,每个特征都是独立的,如果需要考虑特征与特征之间的相互作用,可能需要人工对特征进行交叉组合。非线性SVM可以对特征进行核变换,但是在特征高度稀疏的情况下,并不能很好的进行学习。现在有很多分解模型可以学习到特征之间的交互隐藏关系,基本上每个模型都只适用于特定的输入和场景。推荐系统是一个高度系数的数据场景,由此产生了FM系列算法。
  本文主要涉及三种FM系列算法:FM,FFM,DeepFM

一、FM算法(Factorization Machines)

背景

FM(Factorization Machine)主要是为了解决数据稀疏的情况下,特征怎样组合的问题。已一个广告分类的问题为例,根据用户与广告位的一些特征,来预测用户是否会点击广告。数据如下:


这里写图片描述

对于ctr点击的分类预测中,有些特征是分类变量,一般进行one-hot编码,以下是对组合特征的one-hot:


这里写图片描述

one-hot会带来数据的稀疏性,使得特征空间变大。

另外,对于普通的线性模型,我们将各个特征独立考虑,并没有考虑特征与特征之间的关系,因此有很多方法对特征进行组合,数据模型上表达特征xi,xj的组合用xixj表示,即所说的多项式模型,通常情况下只考虑两阶多项式模型,也就是特征两两组合的问题,模型表达如下:

y=w0+i=1nwixi+i=1n1j=i+1nwijxixj y = w 0 + ∑ i = 1 n w i x i + ∑ i = 1 n − 1 ∑ j = i + 1 n w i j x i x j

其中n表示样本的特征数量,这里的特征是离散化后的特征。与线性模型相比,FM的模型多了后面的特征组合的部分。

FM求解

Wij求解的思路是通过矩阵分解的方法,为了求解Wij,我们队每一个特征分量xi引入辅助向量 Vi=(vi1,vi2,...,vik) V i = ( v i 1 , v i 2 , . . . , v i k )


这里写图片描述

然后用 vivTj v i v j T wij w i j 进行求解


这里写图片描述

从上式可以看出二项式的参数数量由原来的 n(n1)2 n ( n − 1 ) 2 个减少为nk个wik,远少于多项式模型的参数数量。另外,参数因子化使得 xhxi

  • 52
    点赞
  • 325
    收藏
    觉得还不错? 一键收藏
  • 3
    评论
FM(因子分解机)是一种经典的推荐算法,它可以用于处理稀疏数据并且具有较好的预测性能。下面是使用PyTorch实现FM算法的基本步骤: 1. 导入需要的库: ```python import torch import torch.nn as nn import torch.optim as optim ``` 2. 定义FM模型 ```python class FM(nn.Module): def __init__(self, input_dim, k): super(FM, self).__init__() self.k = k self.linear = nn.Linear(input_dim, 1) self.v = nn.Parameter(torch.randn(input_dim, k)) def forward(self, x): linear_part = self.linear(x) inter_part1 = torch.matmul(x, self.v) inter_part2 = torch.matmul(torch.pow(x, 2), torch.pow(self.v, 2)) inter_part = 0.5 * torch.sum(torch.sub(inter_part1, inter_part2), 1, keepdim=True) output = linear_part + inter_part return output ``` 3. 定义训练函数 ```python def train(model, dataloader, optimizer, criterion): model.train() train_loss = 0 for batch_idx, (data, target) in enumerate(dataloader): optimizer.zero_grad() output = model(data) loss = criterion(output, target) train_loss += loss.item() loss.backward() optimizer.step() return train_loss / len(dataloader.dataset) ``` 4. 定义测试函数 ```python def test(model, dataloader, criterion): model.eval() test_loss = 0 with torch.no_grad(): for data, target in dataloader: output = model(data) test_loss += criterion(output, target).item() return test_loss / len(dataloader.dataset) ``` 5. 加载数据集和设置超参数 ```python from torch.utils.data import DataLoader, Dataset class CustomDataset(Dataset): def __init__(self, x, y): self.x = x self.y = y def __getitem__(self, index): return self.x[index], self.y[index] def __len__(self): return len(self.x) X_train, y_train = ... X_test, y_test = ... train_dataset = CustomDataset(X_train, y_train) test_dataset = CustomDataset(X_test, y_test) batch_size = 64 train_dataloader = DataLoader(train_dataset, batch_size=batch_size, shuffle=True) test_dataloader = DataLoader(test_dataset, batch_size=batch_size, shuffle=False) input_dim = X_train.shape[1] k = 10 lr = 0.01 num_epochs = 50 ``` 6. 训练模型 ```python model = FM(input_dim, k) optimizer = optim.SGD(model.parameters(), lr=lr) criterion = nn.MSELoss() for epoch in range(num_epochs): train_loss = train(model, train_dataloader, optimizer, criterion) test_loss = test(model, test_dataloader, criterion) print(f'Epoch {epoch+1}, Train Loss: {train_loss:.4f}, Test Loss: {test_loss:.4f}') ``` 这样就可以使用PyTorch实现FM算法了。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 3
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值