Я сохраняю предварительно обработанный звук в виде спектрограмм в TF.Record
файлах. Пока все хорошо.
Мои данные (один образец) имеют форму (64, 23)
. Мой набор данных для тестирования имеет форму (N, 64, 23)
, где N - количество образцов.
Вот мой код для сохранения набора данных в TF.Record
def folder_to_tfrecord(self, X, Y, output_file):
def _bytes_feature(value):
return tf.train.Feature(bytes_list=tf.train.BytesList(value=[value]))
def _int64_feature(value):
return tf.train.Feature(int64_list=tf.train.Int64List(value=[value]))
writer = tf.python_io.TFRecordWriter(output_file)
for i, (sample, label) in enumerate(zip(X, Y)):
print(f'Storing example #{i} with shape {sample.shape} and label {label}')
# Get Height and Width for future reconstruction
height, width = sample.shape
# Array to string
sample_raw = sample.astype(np.float32).tostring()
# Integer label
label_raw = label
example = tf.train.Example(features=tf.train.Features(feature={
'height': _int64_feature(height),
'width': _int64_feature(width),
'data': _bytes_feature(sample_raw),
'label': _int64_feature(label_raw)
}))
writer.write(example.SerializeToString())
writer.close()
Какой вывод правильный:
Storing example #0 with shape (64, 23) and label 0
Storing example #1 with shape (64, 23) and label 0
Storing example #2 with shape (64, 23) and label 0
Storing example #3 with shape (64, 23) and label 0
Storing example #4 with shape (64, 23) and label 0
Но когда я пытаюсь использовать запись в TF.Dataset
с активным исполнением (поэтому будут получены реальные данные), я получаю исключение (tensorflow keyerror
)
Я читаю данные так:
import tensorflow as tf
def _parse_function(example_proto):
keys_to_features = {
'height': tf.FixedLenFeature([], tf.int64),
'width': tf.FixedLenFeature([], tf.int64),
'data': tf.FixedLenFeature([64, 23], tf.string),
'label': tf.FixedLenFeature([], tf.int64)}
parsed_features = tf.parse_single_example(example_proto, keys_to_features)
return parsed_features['height'], \
parsed_features['width'], \
parsed_features['data'], \
parsed_features['label']
def create_dataset(filepath = './new.tfrecord', paralel: int = 0):
# This works with arrays as well
dataset = tf.data.TFRecordDataset(filepath)
# Maps the parser on every filepath in the array. You can set the number of parallel loaders here
dataset = dataset.map(_parse_function)
return dataset
sess = tf.Session()
ds = create_dataset()
it = ds.make_one_shot_iterator()
next_data = it.get_next()
while True:
try:
data, label = sess.run(next_data)
print(data)
print(label)
except tf.errors.OutOfRangeError:
print("End of dataset")
break
Я получил исключение tensorflow.python.framework.errors_impl.InvalidArgumentError: Key: data. Can't parse serialized Example.
Что я делаю не так? И есть ли возможность переформировать данные с учетом полей высоты и ширины?
EDIT:
Когда я не использую нетерпеливое выполнение, конвейер данных работает
>>> print(next_data)
(<tf.Tensor 'IteratorGetNext:0' shape=() dtype=int64>, <tf.Tensor 'IteratorGetNext:1' shape=() dtype=int64>, <tf.Tensor 'IteratorGetNext:2' shape=(64, 23) dtype=string>, <tf.Tensor 'IteratorGetNext:3' shape=() dtype=int64>)