【问题标题】:Tensorflow: Extracting image and label from TFRecords fileTensorflow:从 TFRecords 文件中提取图像和标签
【发布时间】:2019-07-10 10:59:19
【问题描述】:

我有一个 TFRecords 文件,其中包含带有标签、名称、大小等的图像。我的目标是将标签和图像提取为 numpy 数组。

我执行以下操作来加载文件:

def extract_fn(data_record):
    features = {
        # Extract features using the keys set during creation
        "image/class/label":    tf.FixedLenFeature([], tf.int64),
        "image/encoded":        tf.VarLenFeature(tf.string),
    }
    sample = tf.parse_single_example(data_record, features)
    #sample = tf.cast(sample["image/encoded"], tf.float32)
    return sample

filename = "path\train-00-of-10"
dataset = tf.data.TFRecordDataset(filename)
dataset = dataset.map(extract_fn)
iterator = dataset.make_one_shot_iterator()
next_element = iterator.get_next()

with tf.Session() as sess:
    while True:
        data_record = sess.run(next_element)
        print(data_record)

图像保存为字符串。如何将图像转换为float32?我试过sample = tf.cast(sample["image/encoded"], tf.float32) 不起作用。我希望 data_record 是一个列表,其中包含作为 numpy 数组的图像和作为 np.int32 数字的标签。我该怎么做?

现在data_record 看起来像这样:

{'image/encoded': SparseTensorValue(indices=array([[0]]), values=array([b'\xff\xd8\ ... 8G\xff\xd9'], dtype=object), dense_shape=array([1])), 'image/class/label': 394}

我不知道如何使用它。我会很感激任何帮助

编辑

如果我在extract_fn() 中打印samplesample['image/encoded'],我会得到以下信息:

print(sample) = {'image/encoded': <tensorflow.python.framework.sparse_tensor.SparseTensor object at 0x7fe41ec15978>, 'image/class/label': <tf.Tensor 'ParseSingleExample/ParseSingleExample:3' shape=() dtype=int64>}

print(sample['image/encoded'] = SparseTensor(indices=Tensor("ParseSingleExample/ParseSingleExample:0", shape=(?, 1), dtype=int64), values=Tensor("ParseSingleExample/ParseSingleExample:1", shape=(?,), dtype=string), dense_shape=Tensor("ParseSingleExample/ParseSingleExample:2", shape=(1,), dtype=int64))

似乎图像是稀疏张量,tf.image.decode_image 抛出错误。将图像提取为tf.float32 张量的正确方法是什么?

【问题讨论】:

  • 嘿伙计!这里的 data_record 是什么?那输入是什么?

标签: python tensorflow tensorflow-datasets


【解决方案1】:

我相信您存储编码为 JPEG 或 PNG 或其他格式的图像。所以,在阅读的时候,你必须对它们进行解码:

def extract_fn(data_record):
    features = {
        # Extract features using the keys set during creation
        "image/class/label":    tf.FixedLenFeature([], tf.int64),
        "image/encoded":        tf.VarLenFeature(tf.string),
    }
    sample = tf.parse_single_example(data_record, features)
    image = tf.image.decode_image(sample['image/encoded'], dtype=tf.float32) 
    label = sample['image/class/label']
    return image, label

...

with tf.Session() as sess:
    while True:
        image, label = sess.run(next_element)
        image = image.reshape(IMAGE_SHAPE)

更新: 看来您将数据作为稀疏张量中的单个单元格值。尝试将其转换回密集并在解码前后检查:

def extract_fn(data_record):
    features = {
        # Extract features using the keys set during creation
        "image/class/label":    tf.FixedLenFeature([], tf.int64),
        "image/encoded":        tf.VarLenFeature(tf.string),
    }
    sample = tf.parse_single_example(data_record, features)
    label = sample['image/class/label']
    dense = tf.sparse_tensor_to_dense(sample['image/encoded'])

    # Comment it if you got an error and inspect just dense:
    image = tf.image.decode_image(dense, dtype=tf.float32) 

    return dense, image, label

【讨论】:

  • 我用来自image = tf.image.decode_image(sample['image/encoded'], dtype=tf.float32) 的错误更新了我的问题。我还展示了sample['image/encoded'] 的组成部分。我希望你能帮助我。
  • 请向我们展示您用于创建 tfrecords 的代码。
  • 我只有 tfrecords 文件。我知道它由来自 Imagenet 的图像组成。这就是我所知道的。
  • 我仍然收到错误消息。有趣的是,我可以提取标签。但是,如果我使用 tf.sparse.to_dense(sample["image/encoded"]) 我会收到以下错误:TypeError: Expected string passed to parameter 'default_value' of op 'SparseToDense', got 0 of type 'int' instead.
  • tf.sparse.to_dense(sample["image/encoded"], default_value='')
【解决方案2】:

如果我的观点正确,您只需要numpy.fromstring

img_str = (example.features.feature['image_raw'].bytes_list.value)
image = np.fromstring(img_str, dtype=np.float32)

或者如果你需要tensorflow函数,你需要将tf.decode_raw添加到你的解析函数中,我会说最好将图像和标签分开

def extract_fn(data_record):
    features = {
        # Extract features using the keys set during creation
        "image/class/label":    tf.FixedLenFeature([], tf.int64),
        "image/encoded":        tf.VarLenFeature(tf.string),
    }
    sample = tf.parse_single_example(data_record, features)
    image = tf.decode_raw(sample['image/encoded'], tf.float32)
    label = sample['image/class/label']

    return image, label

【讨论】:

  • 如果我使用tf.decode_raw(): TypeError: Expected string passed to parameter 'bytes' of op 'DecodeRaw', got &lt;tensorflow.python.framework.sparse_tensor.SparseTensor object at 0x7fb19fbe1978&gt; of type 'SparseTensor' instead. 会出错。我还更新了我的问题,显示了 sample['image/encoded'] 的组成部分。
  • @Samuel,你试过用tf.python_io.tf_record_iterator检查文件吗?
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 2018-06-14
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多