深度学习:IMDB分类示例中嵌入架构表现逊于简单基线
IMDB电影评论二分类任务:两种网络架构性能对比
本任务出自《Deep Learning With Python》第三章
数据加载
# num_words表示仅使用词汇表中最常见的`n`个词 (train_data,train_labels),(test_data,test_labels) = imdb.load_data(num_words=10_000) train_xs = torch.vstack([multi_vectorize(t) for t in train_data]).to(torch.float) train_ys = torch.tensor(train_labels).unsqueeze(dim=1).to(torch.float) # 250k -> (250k,1) 适配训练需求 ## 训练/验证集划分 val_xs = train_xs[0:10_000] val_ys = train_ys[0:10_000] partial_train_xs = train_xs[10_000:] partial_train_ys = train_ys[10_000:]
书中采用的简单全连接序列网络架构
Sequential( (0): Linear(in_features=10000, out_features=16, bias=True) (1): ReLU() (2): Linear(in_features=16, out_features=16, bias=True) (3): ReLU() (4): Linear(in_features=16, out_features=1, bias=True) (5): Sigmoid() )
该网络输入为多热编码文本片段,仅能表示词的存在与否,会忽略重复词。
由于嵌入层常用于NLP任务,我构建了含嵌入层的模型,预期性能会有所提升,但实际结果相反:
添加嵌入层的模型实现
将输入统一长度后构建维度为(10001,3)的嵌入层,模型结构如下:
## 统一所有令牌列表的长度 MAX_INPUT_LEN = len(max(train_data,key=len)) ## 词汇表已包含0,最大令牌为VOCAB_SZ - 1(零索引),因此用VOCAB_SZ作为新特殊令牌的起始 PAD_TOKEN = VOCAB_SZ def lpad(x,maxlen=MAX_INPUT_LEN,pad_token=PAD_TOKEN): padlen = maxlen - len(x) if padlen > 0: return [pad_token] * padlen + x return x EMB_SZ = 3 NUM_EMBED = VOCAB_SZ + 1 # 特殊填充字符(10,000) emb_model = nn.Sequential( nn.Embedding(NUM_EMBED,EMB_SZ), nn.Flatten(), nn.Linear(EMB_SZ * MAX_INPUT_LEN,16), nn.ReLU(), nn.Linear(16,16), nn.ReLU(), nn.Linear(16,1), nn.Sigmoid() )
问题
含嵌入层的网络训练速度慢一个数量级(10轮需30秒,全连接版本仅3秒),且验证准确率最高仅约82%(需80轮),远低于全连接版本的90%(10轮)。请解析:
- 为何嵌入层模型训练速度大幅变慢?
- 为何其性能反而更差?
内容的提问来源于stack exchange,提问作者Solaxun
相关产品推荐
相关产品推荐

