Как отобразить массив numpy в наборе данных tenorflow - PullRequest
0 голосов
/ 12 января 2020

Я пытаюсь загрузить в свой конвейер несколько файлов, каждый файл содержит 3 сигнала, а 3 сигнала упорядочены с интервалом в 10 минут. Когда я загружаю первый файл, он имеет эту форму (86, 75000,3). Я использую тензорный поток 1.14

Я попробовал следующий код, чтобы сделать его полезным для вас, я имитирую загрузку с нулями:

import numpy as np
import tensorflow as tf


def my_func(x):
    p = np.zeros([86, 75000, 3])
    return p

def load_sign(path):
    sign = tf.compat.v1.numpy_function(my_func, [path], tf.float64)
    return sign

s = [1, 2]  # list with filenames, these are paths, here i simulate with numbers

AUTOTUNE = tf.data.experimental.AUTOTUNE  
ds = tf.data.Dataset.from_tensor_slices(s)
ds = ds.map(load_sign, num_parallel_calls=AUTOTUNE)

itera = tf.data.make_one_shot_iterator(ds)
x = itera.get_next()

with tf.Session() as sess:
    # sess.run(itera.initializer)
    va_sign = sess.run([x])
    va = np.array(va_sign)
    print(va.shape)

Я получаю эту форму: (1, 86, 75000, 3) Хотя я хотел бы получить 3 разные переменные с каждой формой: (, 75000)

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

import numpy as np
import tensorflow as tf


def my_func(x):
    p = np.zeros([86, 75000, 3])
    x = p[:,:,0]
    y = p[:, :, 1]
    z = p[:, :, 2]
    return x, y, z

# load the signals, in my example it creates the signals using zeros
def load_sign(path):
    a, b, c = tf.compat.v1.numpy_function(my_func, [path], tf.float64)
    return tf.data.Dataset.zip((a,b,c))

s = [1, 2]  # list with filenames, these are paths, here i simulate with numbers

AUTOTUNE = tf.data.experimental.AUTOTUNE  
ds = tf.data.Dataset.from_tensor_slices(s)
ds = ds.map(load_sign, num_parallel_calls=AUTOTUNE)

itera = tf.data.make_one_shot_iterator(ds)
x, y, z = itera.get_next()

with tf.Session() as sess:
    # sess.run(itera.initializer)
    va_sign = sess.run([x])
    va = np.array(va_sign)
    print(va.shape)

, здесь я ожидал бы, что x имеет эту форму: (86, 75000), но вместо этого я получаю эту ошибку. Как я могу заставить это работать? И даже лучше, я могу получить x с этой формой (, 75000)

TypeError: Объекты Tensor могут повторяться только тогда, когда включено активное выполнение. Чтобы перебрать этот тензор, используйте tf.map_fn.

1 Ответ

1 голос
/ 12 января 2020

numpy_function:
a, b, c = tf.compat.v1.numpy_function(my_func, [path], tf.float64) должен возвращать функцию python, которую можно использовать в графической среде. Сами переменные возвращаются my_func. Таким образом, следующий код должен выглядеть следующим образом:

def my_func(x):
    p = np.zeros([86, 75000, 3])
    x = p[:,:,0]
    y = p[:, :, 1]
    z = p[:, :, 2]
    return x, y, z

def load_sign(path):
    func = tf.compat.v1.numpy_function(my_func, [path], [tf.float64, tf.float64, tf.float64])
    return func

Остальное в значительной степени совпадает с незначительными изменениями:

s = [1, 2]  

AUTOTUNE = tf.data.experimental.AUTOTUNE  
ds = tf.data.Dataset.from_tensor_slices(s)
ds = ds.map(load_sign, num_parallel_calls=AUTOTUNE)

itera = tf.data.make_one_shot_iterator(ds)
output = itera.get_next() # Returns tuple of 3: x,y,z from my_func

with tf.Session() as sess:
    va_sign = sess.run([output])[0] # Unnest single-element list
    for entry in va_sign:
      print(entry.shape)

Это даст 3 элемента, каждый из которых имеет форму (86, 75000) ,

Для дальнейшей предварительной обработки ваших данных и достижения (75000,) вы можете использовать tf.data.Dataset.unbatch():

AUTOTUNE = tf.data.experimental.AUTOTUNE  
ds = tf.data.Dataset.from_tensor_slices(s)
ds = ds.map(load_sign, num_parallel_calls=AUTOTUNE).unbatch()

itera = tf.data.make_one_shot_iterator(ds)
output = itera.get_next() # Returns tuple of 3: x,y,z from my_func

Та же итерация, что и выше, даст вам теперь три элемента размера ( 75000,).

...