Apa cara tercepat untuk mengambil baris terakhir dari sebuah tabel?

11

Saya punya tabel PostgreSQL Prices,, dengan kolom:

  • price (Desimal)
  • product_id (Int)

Ada juga created_atdan updated_atkolom.

Harga diperbarui secara berkala dan saya menjaga harga lama di atas meja. Untuk produk tertentu, harga terakhir dalam tabel adalah harga saat ini.

Apa cara paling efisien untuk mendapatkan harga terakhir untuk produk tertentu:

  • Indeks product_iddan permintaan untuk catatan terakhir
  • Tambahkan kolom ketiga active(Boolean) untuk menandai harga terbaru dan buat indeks komposit ( product_iddan active)
  • Atau sesuatu yang lain?
Mike81
sumber
4
Menggunakan indeks parsial dengan kondisi where activemungkin akan membantu lebih banyak untuk mengambil produk terbaru.
a_horse_with_no_name

Jawaban:

11

Anda akan memerlukan indeks pada product_id terlepas dari solusinya.

Asalkan Anda memiliki indeks pada kolom updated_at, dan yang Anda butuhkan hanyalah mengambil "produk tertentu" seperti yang Anda nyatakan, maka saya akan lakukan:

select *
from Prices
where product_id = ?
order by updated_at desc 
limit 1

Tetapi jika saya tidak mendapatkan hasil yang saya inginkan atau jika saya perlu mendapatkan harga saat ini untuk banyak produk, maka saya akan mencoba opsi menambahkan kolom aktif, dan mengaturnya ke N untuk semua harga selain yang baru ketika melakukan pembaruan harga dan kemudian saya akan membuat indeks parsial di mana aktif seperti yang disarankan oleh a_horse_with_no_name. Saya akan pergi ke sana hanya jika saya perlu karena menambah lapisan kompleksitas memperbarui baris harga sebelumnya untuk tidak aktif, dll.

ETL
sumber
1
Permintaan ini membutuhkan indeks pada (product_id, updated_at)- atau di (product_id, updated_at DESC)- agar efisien. Bukan hanya di (updated_at).
ypercubeᵀᴹ
5

Tanpa pengetahuan tentang sisa basis data Anda, Anda dapat membeli sedikit bentuk tidak normal untuk mempercepat pengambilan harga produk (dengan asumsi ada satu harga untuk setiap item).

Cukup buat kolom baru bernama last_pricetipe pricedi producttabel Anda dan buat pemicu AFTER INSERT ON EACH ROWdi pricetabel Anda . Setiap kali harga baru dibuat, itu memperbarui produk terkait dengan harga terbaru. Dengan cara ini, setiap kali Anda mengambil produk, Anda juga mengambil harga terakhirnya.

Sejak versi 9.3, PostgreSQL mendukung pandangan terwujud. Ini adalah cara yang bagus untuk mendenormalisasi data, menjaga bentuk normal untuk penulisan dan tampilan denormalized untuk membaca. Pembaruan tampilan dapat dipicu oleh mekanisme LISTEN / NOTIFY Postgres.

greg
sumber