Hub documentation

Lance

Hugging Face's logo
Join the Hugging Face community

and get access to the augmented documentation experience

to get started

Lance

Lance adalah format tabel lakehouse multimodal terbuka untuk AI. Anda dapat menggunakan jalur Hugging Face (hf://) untuk mengakses dataset Lance di Hub. Hal ini memungkinkan Anda memindai dan mencari dataset besar di Hugging Face Hub tanpa perlu menyalin seluruh dataset secara lokal.

Memulai

Untuk memulai, instal pylance dan pyarrow menggunakan pip:

pip install pylance pyarrow

Mengapa Lance?

  • Dioptimalkan untuk beban kerja ML/AI: Lance adalah format kolom modern yang dirancang untuk akses acak yang cepat tanpa mengorbankan kinerja pemindaian, sehingga berguna untuk pencarian, analitik, pelatihan, rekayasa fitur, dan banyak kasus penggunaan lainnya.
  • Aset multimodal disimpan sebagai byte, atau objek biner (“blobs as files”) di Lance bersama dengan embedding dan data skalar tradisional — ini memudahkan Anda untuk mengatur, membagikan, dan mendistribusikan dataset besar Anda melalui Hub.
  • Indexing adalah fitur utama (native pada format itu sendiri): Lance dilengkapi dengan indeks vektor dan FTS yang cepat, on-disk, dan scalable yang berada tepat berdampingan dengan dataset di Hub, sehingga Anda dapat membagikan tidak hanya data Anda tetapi juga embeddings dan indeks Anda tanpa pengguna Anda perlu menghitung ulang.
  • Skema fleksibel dan evolusi data memungkinkan Anda menambahkan fitur/kolom baru secara bertahap (tag moderasi, embedding, dll.) tanpa perlu menulis ulang seluruh tabel.

Simpan semua data Anda di satu tempat

Di Lance, aset data multimodal Anda (gambar, audio, video) disimpan sebagai byte mentah berdampingan dengan metadata skalar dan embedding Anda. Hal ini memudahkan pemindaian dan penyaringan dataset Anda di satu tempat tanpa perlu merangkai beberapa sistem penyimpanan.

Stream dari Hub dengan datasets

Gunakan load_dataset(..., streaming=True) untuk memindai dan mengiterasi data tanpa mengunduhnya secara lokal.

from datasets import load_dataset

# Return as a Hugging Face dataset
ds = load_dataset(
    "lance-format/laion-1m",
    split="train",
    streaming=True
)
# Take first three rows
for row in ds.take(3):
    print(row["caption"])

Streaming sangat berguna untuk mengambil sampel metadata guna memahami data yang Anda miliki. Untuk pencarian vektor atau bekerja dengan blob biner besar, Anda dapat menggunakan API dataset Lance, yang dijelaskan di bawah ini.

Streaming cepat untuk mengambil sampel metadata skalar sederhana, tetapi tidak secepat itu untuk embedding atau aset multimodal besar. Untuk bekerja dengan dataset besar, disarankan untuk memindai metadata, mengidentifikasi subset yang Anda butuhkan, dan mengunduh bagian tersebut dari dataset secara lokal untuk menghindari batas laju Hub: hf download lance-format/laion-1m --repo-type dataset --local-dir ./laion

Stream dari Hub dengan lance.dataset

Anda juga dapat memindai dataset Lance yang disimpan di Hugging Face Hub menggunakan penentu jalur hf://. Ini memindai dataset jarak jauh tanpa mengharuskan Anda mengunduhnya secara lokal. Dengan menggunakan API dataset Lance, sangat mudah untuk mengatur batas, filter, dan proyeksi agar hanya mengambil data yang Anda butuhkan.

import lance

# Return as a Lance dataset
ds = lance.dataset("hf://datasets/lance-format/laion-1m/data/train.lance")

scanner = ds.scanner(
    columns=["caption", "url", "similarity"],
    limit=5
)

rows = scanner.to_table().to_pylist()
for row in rows:
    print(row)

Bekerja dengan aset biner

Contoh di bawah ini menunjukkan bagaimana gambar diambil dari dataset Lance sebagai byte JPEG mentah di kolom image, dan digunakan di hilir. Gunakan ds.take untuk mengambil byte dan menuliskannya ke disk agar Anda dapat menggunakannya di tempat lain.

import lance
from pathlib import Path

ds = lance.dataset("hf://datasets/lance-format/laion-1m/data/train.lance")

dir_name = "laion_samples"
Path(dir_name).mkdir(exist_ok=True)

rows = ds.take([0, 1], columns=["image", "caption"]).to_pylist()
for idx, row in enumerate(rows):
    with open(f"{dir_name}/{idx}.jpg", "wb") as f:
        f.write(row["image"])
        print(f"Wrote image with caption: {row['caption']}")

Tulis subset ke dataset Lance baru

Bekerja dengan dataset besar? Mudah untuk menjalankan pemindaian terfilter guna memilih subset baris dari Hub dan materialisasikannya menjadi dataset Lance lokal.

import lance

ds = lance.dataset("hf://datasets/lance-format/laion-1m/data/train.lance")
scanner = ds.scanner(
    columns=["image", "caption", "width", "height"],
    filter="width >= 200 AND height >= 100",
    limit=10,
)
subset = scanner.to_table()

lance.write_dataset(subset, "./laion_subset")

Buat indeks

Jika dataset Anda belum memiliki indeks yang terkait, Anda dapat membuatnya setelah mengunduhnya secara lokal.

# ds is a local Lance dataset
ds.create_index(
    "img_emb",
    index_type="IVF_PQ",
    num_partitions=256,
    num_sub_vectors=96,
    replace=True,
)

Lihat dokumentasi Lance tentang pembuatan indeks vektor untuk contoh yang lebih detail. Setelah Anda membuat indeks vektor, Anda dapat menjalankan pencarian kemiripan pada data melalui embeddings.

Pencarian vektor

Karena indeks adalah warga kelas satu di Lance, Anda dapat menyimpan tidak hanya data Anda tetapi juga embedding dan indeks Anda secara bersama-sama dan melakukan kueri langsung di Hub. Cukup gunakan metode describe_indices() untuk mendaftar informasi indeks untuk dataset. Jika sebuah indeks tidak ada di dataset, Anda dapat menggunakan lance.write_dataset() untuk menulis versi lokal dari dataset dan menggunakan LanceDataset.create_index untuk membuat indeks sesuai kebutuhan Anda.

Contoh di bawah ini menunjukkan dataset yang sudah memiliki indeks vektor pada field img_emb:

import lance

ds = lance.dataset("hf://datasets/lance-format/laion-1m/data/train.lance")

print(ds.list_indices())

# Returns
# [
#   IndexDescription(
#       name=img_emb_idx,
#       type_url=/lance.table.VectorIndexDetails,
#       num_rows_indexed=1209588,
#       fields=[15],
#       field_names=["img_emb"],
#       num_segments=1
#.   )
# ]

Anda dapat menjalankan kueri pencarian vektor langsung pada dataset jarak jauh tanpa mengunduhnya (atau, jika Anda lebih memilih, unduh dataset secara lokal dan buat indeks baru). Contoh di bawah ini menunjukkan cara menjalankan pencarian tetangga terdekat pada indeks vektor menggunakan embedding gambar sebagai vektor kueri.

import lance
import pyarrow as pa

ds = lance.dataset("hf://datasets/lance-format/laion-1m/data/train.lance")

emb_field = ds.schema.field("img_emb")
ref = ds.take([0], columns=["img_emb"]).to_pylist()[0]["img_emb"]
query = pa.array([ref], type=emb_field.type)

neighbors = ds.scanner(
    nearest={
        "column": emb_field.name,
        "q": query[0],
        "k": 6,
        "nprobes": 16,
        "refine_factor": 30,
    },
    columns=["caption", "url", "similarity"],
).to_table().to_pylist()

Menetapkan nilai k atau nprobes yang besar, atau mengirim batch kueri dalam jumlah besar sekaligus, dapat mencapai batas laju Hub. Untuk penggunaan intensif, unduh dataset (atau subset-nya) secara lokal dan arahkan Lance ke jalur lokal untuk menghindari pembatasan.

Evolusi dataset

Salah satu fitur paling kuat dari Lance adalah evolusi data yang fleksibel dan tanpa biaya, yang berarti Anda dapat dengan mudah menambahkan kolom turunan tanpa menulis ulang tabel asli. Untuk tabel yang sangat besar dengan banyak blob berukuran besar, penghematan I/O dapat cukup signifikan. Fitur ini sangat relevan jika Anda sedang bereksperimen dengan data untuk tugas rekayasa ML/AI dan sering kali menemukan diri Anda menambahkan fitur baru, embedding, atau metadata turunan.

Contoh di bawah ini menunjukkan cara menambahkan kolom moderation_label turunan yang menandai gambar sebagai NSFW berdasarkan kolom skor yang sudah ada. Ketika Anda melakukan perubahan ini, backfilling kolom baru hanya menulis data kolom baru, tanpa menyentuh blob gambar asli atau data di kolom lain. Anda juga dapat memilih untuk hanya menambahkan skema kolom baru tanpa melakukan backfill data apa pun.

import lance
import pyarrow as pa

# Assumes you ran the export to Lance example above to store a local subset of the data
local_ds = lance.dataset("./laion_subset")

# schema only (data to be added later)
local_ds.add_columns(pa.field("moderation_label", pa.string()))

# with data backfill
local_ds.add_columns(
    {
        "moderation_label": "case WHEN \"NSFW\" > 0.5 THEN 'review' ELSE 'ok' END"
    }
)

Lihat dokumentasi Lance tentang evolusi data untuk mempelajari cara mengubah dan menghapus kolom dalam dataset Lance.

Bekerja dengan blob video

Tabel Lance juga mendukung blob video inline berukuran besar. Dataset OpenVid-1M (dari makalah ini) berisi video berkualitas tinggi yang ekspresif beserta caption-nya. Data video disimpan pada kolom video_blob dari dataset Lance berikut di Hub.

import lance

lance_ds = lance.dataset("hf://datasets/lance-format/Openvid-1M/data/train.lance")
blob_file = lance_ds.take_blobs("video_blob", ids=[0])[0]
video_bytes = blob_file.read()

Berbeda dengan format data lainnya, objek biner multimodal berukuran besar (blob) merupakan warga kelas satu di Lance. API blob menyediakan API tingkat tinggi untuk menyimpan dan mengambil blob besar dalam dataset Lance. Contoh berikut menunjukkan cara menelusuri metadata secara efisien tanpa memuat blob video yang lebih berat, lalu mengambil blob video yang relevan sesuai permintaan.

import lance

ds = lance.dataset("hf://datasets/lance-format/Openvid-1M/data/train.lance")

# 1. Browse metadata without loading video blobs.
metadata = ds.scanner(
    columns=["caption", "aesthetic_score"],
    filter="aesthetic_score >= 4.5",
    limit=2,
).to_table().to_pylist()

# 2. Fetch a single video blob by row index.
selected_index = 0
blob_file = ds.take_blobs("video_blob", ids=[selected_index])[0]
with open("video_0.mp4", "wb") as f:
    f.write(blob_file.read())

Siapkan data untuk pelatihan

Pelatihan adalah area lain di mana kinerja akses acak dan pemindaian cepat Lance dapat berguna. Anda dapat menggunakan dataset Lance sebagai mekanisme penyimpanan untuk data pelatihan Anda, mengacaknya, dan memuatnya ke dalam batch sebagai bagian dari pipeline pelatihan Anda.

API blob di Lance kompatibel dengan torchcodec, sehingga Anda dapat dengan mudah mendekode blob video menjadi tensor torch:

from torchcodec.decoders import VideoDecoder
decoder = VideoDecoder(blob_file)
tensor = decoder[0]  # uint8 tensor of shape [C, H, W]

Lihat dokumentasi torchcodec untuk fungsi-fungsi lain dalam mengurai video secara efisien.

Selain itu, Anda juga dapat melihat dokumentasi Lance untuk contoh lebih lanjut tentang memuat data gambar ke torchvision untuk melatih model gambar Anda sendiri.

Jelajahi lebih banyak dataset Lance

Lance adalah format terbuka dengan dukungan native untuk blob multimodal di samping data tabular tradisional Anda. Dengan integrasi Hugging Face Hub, Anda dapat dengan mudah bekerja dengan gambar, audio, video, teks, embeddings, dan metadata skalar semuanya di satu tempat.

Jelajahi lebih banyak dataset Lance di Hugging Face Hub, dan bagikan dataset Lance Anda sendiri dengan orang lain di komunitas! Anda dapat mengunjungi lance.org untuk lebih banyak potongan kode dan contoh.

Update on GitHub