โหลด tfrecord ภายนอกด้วย TFDS

จัดทุกอย่างให้เป็นระเบียบอยู่เสมอด้วยคอลเล็กชัน บันทึกและจัดหมวดหมู่เนื้อหาตามค่ากำหนดของคุณ

หากคุณมี tf.train.Example proto (ภายใน .tfrecord , .riegeli ,...) ซึ่งสร้างขึ้นโดยเครื่องมือของบุคคลที่สาม ซึ่งคุณต้องการโหลดโดยตรงด้วย tfds API หน้านี้เหมาะสำหรับคุณ

ในการโหลดไฟล์ .tfrecord ของคุณ คุณจะต้อง:

  • ปฏิบัติตามหลักการตั้งชื่อ TFDS
  • เพิ่มไฟล์ข้อมูลเมตา ( dataset_info.json , features.json ) ไปพร้อมกับไฟล์ tfrecord ของคุณ

ข้อจำกัด:

หลักการตั้งชื่อไฟล์

TFDS รองรับการกำหนดเทมเพลตสำหรับชื่อไฟล์ ซึ่งให้ความยืดหยุ่นในการใช้รูปแบบการตั้งชื่อไฟล์ที่แตกต่างกัน เทมเพลตนี้แสดงโดย tfds.core.ShardedFileTemplate และรองรับตัวแปรต่อไปนี้: {DATASET} , {SPLIT} , {FILEFORMAT} , {SHARD_INDEX} , {NUM_SHARDS} และ {SHARD_X_OF_Y} ตัวอย่างเช่น รูปแบบการตั้งชื่อไฟล์เริ่มต้นของ TFDS คือ: {DATASET}-{SPLIT}.{FILEFORMAT}-{SHARD_X_OF_Y} สำหรับ MNIST นี่หมายความว่า ชื่อไฟล์ มีลักษณะดังนี้:

  • mnist-test.tfrecord-00000-of-00001
  • mnist-train.tfrecord-00000-of-00001

เพิ่มข้อมูลเมตา

ให้โครงสร้างคุณสมบัติ

เพื่อให้ TFDS สามารถถอดรหัสโปรโต tf.train.Example คุณต้องระบุโครงสร้าง tfds.features ที่ตรงกับข้อกำหนดของคุณ ตัวอย่างเช่น:

features = tfds.features.FeaturesDict({
    'image':
        tfds.features.Image(
            shape=(256, 256, 3),
            doc='Picture taken by smartphone, downscaled.'),
    'label':
        tfds.features.ClassLabel(names=['dog', 'cat']),
    'objects':
        tfds.features.Sequence({
            'camera/K': tfds.features.Tensor(shape=(3,), dtype=tf.float32),
        }),
})

สอดคล้องกับข้อกำหนด tf.train.Example ต่อไปนี้:

{
    'image': tf.io.FixedLenFeature(shape=(), dtype=tf.string),
    'label': tf.io.FixedLenFeature(shape=(), dtype=tf.int64),
    'objects/camera/K': tf.io.FixedLenSequenceFeature(shape=(3,), dtype=tf.int64),
}

การระบุคุณสมบัติทำให้ TFDS สามารถถอดรหัสรูปภาพ วิดีโอ... เช่นเดียวกับชุดข้อมูล TFDS อื่นๆ ข้อมูลเมตาของคุณสมบัติ (เช่น ชื่อป้ายกำกับ...) จะถูกเปิดเผยต่อผู้ใช้ (เช่น info.features['label'].names ).

หากคุณควบคุมไปป์ไลน์การสร้าง

หากคุณสร้างชุดข้อมูลนอก TFDS แต่ยังคงควบคุมไปป์ไลน์การสร้าง คุณสามารถใช้ tfds.features.FeatureConnector.serialize_example เพื่อเข้ารหัสข้อมูลของคุณจาก dict[np.ndarray] ถึง tf.train.Example proto bytes :

with tf.io.TFRecordWriter('path/to/file.tfrecord') as writer:
  for ex in all_exs:
    ex_bytes = features.serialize_example(data)
    writer.write(ex_bytes)

เพื่อให้แน่ใจว่าคุณลักษณะนี้จะเข้ากันได้กับ TFDS

ในทำนองเดียวกัน feature.deserialize_example มีอยู่เพื่อถอดรหัสโปรโต ( example )

หากคุณไม่ได้ควบคุมไปป์ไลน์การสร้าง

หากคุณต้องการดูว่า tfds.features แสดงใน tf.train.Example อย่างไร คุณสามารถตรวจสอบได้ใน colab:

  • หากต้องการแปล tfds.features เป็นโครงสร้างที่มนุษย์อ่านได้ของ tf.train.Example คุณสามารถเรียก features.get_serialized_info()
  • ในการรับ FixedLenFeature ,... spec ที่ส่งผ่านไปยัง tf.io.parse_single_example คุณสามารถใช้ spec = features.tf_example_spec

รับสถิติการแบ่ง

TFDS ต้องการทราบจำนวนตัวอย่างที่แน่นอนในแต่ละชาร์ด สิ่งนี้จำเป็นสำหรับคุณสมบัติเช่น len(ds) หรือ subplit API : split='train[75%:]'

  • หากคุณมีข้อมูลนี้ คุณสามารถสร้างรายการ tfds.core.SplitInfo ได้อย่างชัดเจน และข้ามไปยังส่วนถัดไป:

    split_infos = [
        tfds.core.SplitInfo(
            name='train',
            shard_lengths=[1024, ...],  # Num of examples in shard0, shard1,...
            num_bytes=0,  # Total size of your dataset (if unknown, set to 0)
        ),
        tfds.core.SplitInfo(name='test', ...),
    ]
    
  • หากคุณไม่ทราบข้อมูลนี้ คุณสามารถคำนวณโดยใช้สคริปต์ compute_split_info.py (หรือในสคริปต์ของคุณเองด้วย tfds.folder_dataset.compute_split_info ) มันจะเปิดตัวบีมไปป์ไลน์ซึ่งจะอ่านชาร์ดทั้งหมดในไดเร็กทอรีที่กำหนดและคำนวณข้อมูล

เพิ่มไฟล์ข้อมูลเมตา

ในการเพิ่มไฟล์ข้อมูลเมตาที่เหมาะสมโดยอัตโนมัติในชุดข้อมูลของคุณ ให้ใช้ tfds.folder_dataset.write_metadata :

tfds.folder_dataset.write_metadata(
    data_dir='/path/to/my/dataset/1.0.0/',
    features=features,
    # Pass the `out_dir` argument of compute_split_info (see section above)
    # You can also explicitly pass a list of `tfds.core.SplitInfo`.
    split_infos='/path/to/my/dataset/1.0.0/',
    # Pass a custom file name template or use None for the default TFDS
    # file name template.
    filename_template='{SPLIT}-{SHARD_X_OF_Y}.{FILEFORMAT}',

    # Optionally, additional DatasetInfo metadata can be provided
    # See:
    # https://www.tensorflow.org/datasets/api_docs/python/tfds/core/DatasetInfo
    description="""Multi-line description."""
    homepage='http://my-project.org',
    supervised_keys=('image', 'label'),
    citation="""BibTex citation.""",
)

เมื่อฟังก์ชันถูกเรียกใช้ครั้งเดียวในไดเร็กทอรีชุดข้อมูลของคุณ จะมีการเพิ่มไฟล์ข้อมูลเมตา ( dataset_info.json ,...) และชุดข้อมูลของคุณพร้อมที่จะโหลดด้วย TFDS (ดูหัวข้อถัดไป)

โหลดชุดข้อมูลด้วย TFDS

โดยตรงจากโฟลเดอร์

เมื่อสร้างข้อมูลเมตาแล้ว สามารถโหลดชุดข้อมูลได้โดยใช้ tfds.builder_from_directory ซึ่งส่งคืน tfds.core.DatasetBuilder ด้วย TFDS API มาตรฐาน (เช่น tfds.builder ):

builder = tfds.builder_from_directory('~/path/to/my_dataset/3.0.0/')

# Metadata are available as usual
builder.info.splits['train'].num_examples

# Construct the tf.data.Dataset pipeline
ds = builder.as_dataset(split='train[75%:]')
for ex in ds:
  ...

โดยตรงจากหลาย ๆ โฟลเดอร์

นอกจากนี้ยังสามารถโหลดข้อมูลจากหลาย ๆ โฟลเดอร์ได้อีกด้วย สิ่งนี้สามารถเกิดขึ้นได้ ตัวอย่างเช่น ในการเรียนรู้การเสริมกำลัง เมื่อตัวแทนหลายรายสร้างชุดข้อมูลแยกกัน และคุณต้องการโหลดทั้งหมดเข้าด้วยกัน กรณีการใช้งานอื่นๆ คือเมื่อมีการสร้างชุดข้อมูลใหม่เป็นประจำ เช่น ชุดข้อมูลใหม่ต่อวัน และคุณต้องการโหลดข้อมูลจากช่วงวันที่

ในการโหลดข้อมูลจากหลายโฟลเดอร์ ให้ใช้ tfds.builder_from_directories ซึ่งส่งคืน tfds.core.DatasetBuilder ด้วย TFDS API มาตรฐาน (เช่น tfds.builder ):

builder = tfds.builder_from_directories(builder_dirs=[
    '~/path/my_dataset/agent1/1.0.0/',
    '~/path/my_dataset/agent2/1.0.0/',
    '~/path/my_dataset/agent3/1.0.0/',
])

# Metadata are available as usual
builder.info.splits['train'].num_examples

# Construct the tf.data.Dataset pipeline
ds = builder.as_dataset(split='train[75%:]')
for ex in ds:
  ...

โครงสร้างโฟลเดอร์ (ไม่บังคับ)

เพื่อให้เข้ากันได้กับ TFDS มากขึ้น คุณสามารถจัดระเบียบข้อมูลของคุณเป็น <data_dir>/<dataset_name>[/<dataset_config>]/<dataset_version> ตัวอย่างเช่น:

data_dir/
    dataset0/
        1.0.0/
        1.0.1/
    dataset1/
        config0/
            2.0.0/
        config1/
            2.0.0/

สิ่งนี้จะทำให้ชุดข้อมูลของคุณเข้ากันได้กับ tfds.load / tfds.builder API เพียงแค่ให้ data_dir/ :

ds0 = tfds.load('dataset0', data_dir='data_dir/')
ds1 = tfds.load('dataset1/config0', data_dir='data_dir/')