我正在尝试在Caffe中训练一个网络,这是一个略微修改的SegNet-basic
模型。
我明白我得到的Check failed: error == cudaSuccess (2 vs. 0) out of memory
错误是由于我耗尽了GPU内存。然而,令我困惑的是:
我的“旧”训练尝试很好。网络初始化并运行,具有以下内容:
Memory required for data: 1800929300
的过滤器。令我惊讶的是,我的“新”网络内存不足,我不明白是什么保留了额外的内存,因为我降低了批量大小:
4x
(=样本量)参数的数量由7x7
计算,通过总计通过乘以每层中的维数得到的分层参数。
假设每个参数需要4个字节的内存,那么与新的Memory required for data: 1175184180
相比,我的旧设置this script仍然会给data_memory+num_param*4
更高的内存要求。
我已经接受了在某个地方可能需要额外的内存,并且如果我找不到具有更多内存的GPU,我将不得不重新考虑我的新设置和下采样我的输入,但是我真的想了解哪里需要额外的内存以及为什么我的新设置内存不足。
编辑:每个请求,这里是每个网络的层维度加上通过它的数据大小:
“旧”网络:
memory_old = 1806602004 = 1.68GB
对于“新”网络,前几个层不同,其余部分完全相同,只是批量大小为1而不是4:
memory_new = 1181659956 = 1.10GB
这会跳过池和上采样层。这是“新”网络的 Top shape: 4 4 384 512 (3145728)
('conv1', (64, 4, 7, 7)) --> 4 64 384 512 (50331648)
('conv1_bn', (1, 64, 1, 1)) --> 4 64 384 512 (50331648)
('conv2', (64, 64, 7, 7)) --> 4 64 192 256 (12582912)
('conv2_bn', (1, 64, 1, 1)) --> 4 64 192 256 (12582912)
('conv3', (64, 64, 7, 7)) --> 4 64 96 128 (3145728)
('conv3_bn', (1, 64, 1, 1)) --> 4 64 96 128 (3145728)
('conv4', (64, 64, 7, 7)) --> 4 64 48 64 (786432)
('conv4_bn', (1, 64, 1, 1)) --> 4 64 48 64 (786432)
('conv_decode4', (64, 64, 7, 7)) --> 4 64 48 64 (786432)
('conv_decode4_bn', (1, 64, 1, 1)) --> 4 64 48 64 (786432)
('conv_decode3', (64, 64, 7, 7)) --> 4 64 96 128 (3145728)
('conv_decode3_bn', (1, 64, 1, 1)) --> 4 64 96 128 (3145728)
('conv_decode2', (64, 64, 7, 7)) --> 4 64 192 256 (12582912)
('conv_decode2_bn', (1, 64, 1, 1)) --> 4 64 192 256 (12582912)
('conv_decode1', (64, 64, 7, 7)) --> 4 64 384 512 (50331648)
('conv_decode1_bn', (1, 64, 1, 1)) --> 4 64 384 512 (50331648)
('conv_classifier', (3, 64, 1, 1))
。旧网络没有层 Top shape: 1 4 769 1025 (3152900)
('conv0', (64, 4, 7, 7)) --> 1 4 769 1025 (3152900)
('conv0_bn', (1, 64, 1, 1)) --> 1 64 769 1025 (50446400)
('conv1', (64, 4, 7, 7)) --> 1 64 384 512 (12582912)
('conv1_bn', (1, 64, 1, 1)) --> 1 64 384 512 (12582912)
('conv2', (64, 64, 7, 7)) --> 1 64 192 256 (3145728)
('conv2_bn', (1, 64, 1, 1)) --> 1 64 192 256 (3145728)
('conv3', (64, 64, 7, 7)) --> 1 64 96 128 (786432)
('conv3_bn', (1, 64, 1, 1)) --> 1 64 96 128 (786432)
('conv4', (64, 64, 7, 7)) --> 1 64 48 64 (196608)
('conv4_bn', (1, 64, 1, 1)) --> 1 64 48 64 (196608)
('conv_decode4', (64, 64, 7, 7)) --> 1 64 48 64 (196608)
('conv_decode4_bn', (1, 64, 1, 1)) --> 1 64 48 64 (196608)
('conv_decode3', (64, 64, 7, 7)) --> 1 64 96 128 (786432)
('conv_decode3_bn', (1, 64, 1, 1)) --> 1 64 96 128 (786432)
('conv_decode2', (64, 64, 7, 7)) --> 1 64 192 256 (3145728)
('conv_decode2_bn', (1, 64, 1, 1)) --> 1 64 192 256 (3145728)
('conv_decode1', (64, 64, 7, 7)) --> 1 64 384 512 (12582912)
('conv_decode1_bn', (1, 64, 1, 1)) --> 1 64 384 512 (12582912)
('conv_classifier', (3, 64, 1, 1))
,train.prototxt
和conv0
,而其他层是相同的。 “旧”网络也有conv0_bn
设置为pool0
而不是batch_size
。
EDIT2:每个请求,更多信息:
4
,所以总是1
输入。769x1025
:正如你所看到的,我在网络初始化后得到了4x769x1025
。没有一次迭代运行。请记住,caffe实际上为两个网络副本分配了空间:“火车阶段”网和“测试阶段”网。因此,如果数据需要1.1GB,则需要将此空间加倍。 而且,您需要为参数分配空间。每个参数都需要存储其渐变。此外,求解器跟踪每个参数的“动量”(有时甚至是第二时刻,例如,在ADAM求解器中)。因此,即使增加很少量的参数也会导致训练系统的内存占用量显着增加。