keras 加载其他数据集时如何清理GPU内存

gajydyqb  于 2023-01-13  发布在  其他
关注(0)|答案(1)|浏览(174)

我正在训练CNN网络的音频声谱图,比较两种类型的输入数据(3秒和30秒),这导致了实验中不同的声谱图大小。
我用这个来获取数据:

def get_data(data_type, batch_size):
    assert data_type in ['3s', '30s'], "data_type shoulbe either 3s or 30s"
    if data_type == '3s':
        audio_dir = DATA_PATH / 'genres_3_seconds'
        max_signal_length_to_crop = 67_500
    elif data_type == '30s':
        audio_dir = DATA_PATH / 'genres_original'
        max_signal_length_to_crop = 660_000
    input_shape = (max_signal_length_to_crop, 1)

    train_ds, val_ds = tf.keras.utils.audio_dataset_from_directory(
        directory=audio_dir,
        batch_size=batch_size,
        validation_split=0.2,
        output_sequence_length=max_signal_length_to_crop,
        subset='both',
        label_mode='categorical'
    )
    test_ds = val_ds.shard(num_shards=2, index=0)
    val_ds = val_ds.shard(num_shards=2, index=1)
    return train_ds, val_ds, test_ds, input_shape

我用这个函数来创建模型。
x一个一个一个一个x一个一个二个x
我正在一个循环中运行几个不同架构的实验,这是我的训练循环:

for data_type in ['3s', '30s']:
    train_ds, val_ds, test_ds, input_shape = get_data(data_type=data_type, batch_size=30)
    for model_type in ['CNN_Basic', ...]:
        model = get_model(model_type, input_shape=input_shape, data_type=data_type)
        model.fit(train_ds, epochs=epochs, validation_data=val_ds)

我得到的错误:

Traceback (most recent call last):
  File "...\lib\site-packages\tensorflow\python\trackable\base.py", line 205, in _method_wrapper
    result = method(self, *args, **kwargs)
  File "...\lib\site-packages\keras\utils\traceback_utils.py", line 70, in error_handler
    raise e.with_traceback(filtered_tb) from None
  File "...\lib\site-packages\tensorflow\python\framework\ops.py", line 1969, in _create_c_op
    raise ValueError(e.message)
ValueError: Exception encountered when calling layer "dense" (type Dense).

Dimensions must be equal, but are 17024 and 6272 for '{{node dense/MatMul}} = MatMul[T=DT_FLOAT, transpose_a=false, transpose_b=false](Placeholder, dense/MatMul/ReadVariableOp)' with input shapes: [?,17024], [6272,128].

Call arguments received by layer "dense" (type Dense):
  • inputs=tf.Tensor(shape=(None, 17024), dtype=float32)

我认为这是由数据集的一些问题引起的,因为我只有在30秒的频谱图之后用3秒的频谱图运行实验时才遇到这个错误。我每次都创建新的模型,为了加载数据,我使用tf.keras.utils.audio_dataset_from_directory,并在接下来的循环迭代中将其加载到同一个变量中。

nfs0ujit

nfs0ujit1#

好的,我明白了。你不能像我的例子那样创建一个模型或模型的一部分,然后期望它在从字典中取出时像全新的一样工作。我通过创建一个函数来修复它,每次我构建新模型时都会调用这个函数,并返回层的新示例。使用字典我得到了“正确”的层,但它们被使用了一个,在拟合后它们改变了它们在内存中的状态。并且期望某种类型的输入数据,当我试图在另一组数据上再次运行它时。
因此,经验教训,不要创建变量(列表,字典等)与您的层时,你打算重用他们在不同的模型。

def get_internal_model(model_type):
    if model_type == 'CNN_Basic':
        internal_layers = [
            Conv2D(filters=8, kernel_size=3, activation='relu'),
            MaxPooling2D(2),
            Conv2D(filters=16, kernel_size=3, activation='relu'),
            MaxPooling2D(2),
            Conv2D(filters=32, kernel_size=3, activation='relu'),
            MaxPooling2D(2),
            Flatten(),
            Dense(units=128, activation='relu'),
        ]
    ...
    return internal_layers

def get_model(model_type, data_type, input_shape):
    specrtogram_layer = get_spectrogram_layer(input_shape, data_type)
    model = Sequential([
        specrtogram_layer,
        *get_internal_model(model_type), # HERE
        Dense(units=10, activation='softmax', name='last_dense')
    ])
    ...

相关问题