我想在Pytorch中实现字符级的CNN。
我的输入有 4 个维度:
(批量大小,seq_length,papped_character_length,embedding_dim)
我想知道是否应该合并两个维度并在现有维度上使用Conv1D
层,或者使用Conv2D
层。
鉴于输入的尺寸在技术上都可以正常工作,因此我也看到了这两个版本的实现。所以我想知道哪种方法更好。
这两种方法中的一种是否比另一种有特殊的优势?
答案 0 :(得分:1)
在Conv1D和Conv2D中没有什么是最好的。
通常,Conv1D用于文本数据,而Conv2D用于图像数据。
考虑到您将实现字符级CNN,使用Conv1D更有意义。
答案 1 :(得分:1)
我同意Venkatesh的观点,即1D可能对您的实现更有意义。我通常不使用合并,而是使用Keras中的TimeDistributed层。这需要一层并将其应用于时间范围。这样做的好处是,您可以将每个维度中的要素分开,直到要合并它们为止。
如果您正在使用填充(如前所述),则在时间维度上应用相同的图层而不是合并图层并在实际字符之间创建尴尬的填充空间会更有意义。 TimeDistributed层解决了这个问题。
我搜索了一下,发现有人尝试在PyTorch中实现此功能,至少可以帮助您入门。
要进一步扩展我的用法。我的最新模型有5个,12小时周期,每个12小时周期都有零星活动,因此将其填充到标准长度为30,因此最终输入形状为(?,5,30,embedding_size)。我使用TimeDistributed 1D CNN在单个时间段内生成特征 ,然后将这些特征最大化,并连接以创建新的形状(?,5,n_feats),现在有5套特征图。我再次使用不同的1D CNN层(遍历5、12小时周期)遍历该数据。每个周期中的填充都是彼此独立的,所以我不能简单地使用2D CNN,因为具有相同索引的元素不能代表跨周期的相同时间。
编辑:
我认为Keras的实现稍微复杂一些,但这应该很接近。他们的文档说:“该包装器将一层应用于输入的每个时间片。”如果到达那里需要合并,然后再还原,则可能是围绕功能图的一些考虑。例如,如果过滤器大小为2,则第一个要素图中的最后一项(在重塑后)将包括两个时间片之间的最后一个要素和第一个要素。
此处one more link讨论PyTorch中的此功能可能会有所帮助。
答案 2 :(得分:0)
我只是想回到这里,因为我已经尝试了两种变体,使用 Conv2D 和 Conv1D 和 TimeDistributed 。
经过几次实验,我将保留一个 Conv2D 层,因为这样可以大大提高设置效果。
我认为结果确实取决于特定的实现,但是我不能支持 Conv1D 层通常更适合字符级CNN的说法。
因此 Conv2D 层绝对值得为此应用程序考虑!