Множественный ввод для API tf.data с генераторами - PullRequest
0 голосов
/ 13 февраля 2020

Я немного борюсь с API tf.data.dataset, когда пытаюсь иметь несколько входов для LSTM, то есть для каждой функции вектор длины n (шагов по времени ser ie) и с помощью let нам день, 5 функций. Таким образом, у меня есть список из 5 векторов с длиной, скажем, n = 3.

Например, у меня есть генератор, который на каждом шаге выдает данные со следующей структурой:

      [
       array( 
        [
         [5.00000000e-01, 5.00000000e-01, 5.00000000e-01],
         [9.00000000e+00, 9.00000000e+00, 9.00000000e+00],
         [7.00000000e+00, 9.00000000e+00, 1.00000000e+01],
         [6.30841636e-03, 4.22776321e-02, 1.49106372e-02],
         [4.00000000e+00, 1.00000000e+01, 2.20000000e+01]
        ]), 
       array(
        [
         [ 9,  9,  9],
         [13, 13, 13]
        ]
       )
      ]

и когда я пытаюсь поместить их в API с помощью строки кода:

tf.data.Dataset.from_generator(
            generator=lambda: generator,
            output_types=(
                (
                    (tf.float32, tf.float32, tf.float32),
                    (tf.int32, tf.int32, tf.int32),
                    (tf.int32, tf.int32, tf.int32),
                    (tf.float32, tf.float32, tf.float32),
                    (tf.int32, tf.int32, tf.int32)
                ),
                (
                    (tf.int32, tf.int32, tf.int32),
                    (tf.int32, tf.int32, tf.int32)
                )
            )
        )

Я получаю ошибку:

Ошибка типа: generator получен элемент, который не соответствует ожидаемой структуре. Ожидаемая структура была .... но полученным элементом было ....

Чего мне не хватает? Как правильно написать output_shape? Или нельзя дать генератору для tf.data вложенную структуру? Как обрабатывать несколько входов и выходов с помощью tf.data.dataset.from_generator?

Заранее спасибо за любую помощь.

1 Ответ

1 голос
/ 13 февраля 2020

Прежде всего, похоже, что from_generator не может обработать генератор, который выдает списки массивов, так как это приводит к следующему исключению:

TypeError: unhashable type: 'list'

Кажется простое переключение на генератор, который выдает кортежи массивов чтобы исправить эту ошибку.

Далее, согласно документации , в качестве output_types вы должны предоставить вложенную структуру из tf.DType объектов, соответствующих каждому компоненту элемента, выданного генератором .

В этом случае элементы, которые генерирует ваш генератор, являются кортежами двух массивов. Поэтому вы должны предоставить вложенную структуру из tf.DType объектов, соответствующих каждому компоненту / массиву. Или, другими словами, в качестве output_types вы должны предоставить кортеж, содержащий два tf.DType объекта, указывающих желаемый тип каждого массива (вместо попытки указать желаемый тип каждого значения в каждом массиве).

Следующий код может дать вам представление о том, как правильно использовать from_generator:

import numpy as np
import tensorflow as tf


def generator():
    for _ in range(10):
        yield (np.random.rand(5, 3), np.random.rand(2, 3))


dataset = tf.data.Dataset.from_generator(generator,
                                         output_types=(tf.float32, tf.float32))

...