Permintaan Django - id vs pk

203

Saat menulis pertanyaan Django, seseorang dapat menggunakan kedua id / pk sebagai parameter kueri.

Object.objects.get(id=1)
Object.objects.get(pk=1)

Saya tahu bahwa pk adalah singkatan dari Primary Key dan hanya jalan pintas, menurut dokumentasi Django. Namun tidak jelas kapan seseorang harus menggunakan id atau pk.

Seni
sumber
Berikut adalah dokumentasi masing-masing: untukid dan untukpk
Lutz Prechelt
Ingin tahu apakah ada sesuatu yang lebih dari itu docs.djangoproject.com/en/1.11/topics/db/queries/…
Rajan Chauhan
Periksa versi Diperbarui di sini docs.djangoproject.com/en/2.2/topics/db/models/…
Tessaracter

Jawaban:

224

Itu tidak masalah. pklebih independen dari bidang kunci utama yang sebenarnya yaitu Anda tidak perlu peduli apakah bidang kunci utama disebut idatau object_idatau apa pun.

Ini juga memberikan lebih banyak konsistensi jika Anda memiliki model dengan bidang kunci utama yang berbeda.

Felix Kling
sumber
34
Ya. Cukup gunakan pk. Selalu.
cethegeek
47
idjuga merupakan fungsi bawaan di Python, saya lebih suka menggunakan pk karena itu.
Thierry Lam
5
Ya, pklebih disukai. Lihat dokumentasi fungsiid bawaan di pustaka standar Python. (Ini sama dengan Python 2. )
Lutz Prechelt
26

Dalam proyek Django di mana saya tahu bahwa pkselalu kembali idsaya lebih suka menggunakan idketika tidak berbenturan dengan id()fungsi (di mana-mana kecuali nama variabel). Alasan untuk ini adalah itu pkadalah properti yang 7 kali lebih lambat daripada idkarena butuh waktu mencari pknama atribut di meta.

%timeit obj.id
46 ns ± 0.187 ns per loop (mean ± std. dev. of 7 runs, 10000000 loops each)
%timeit obj.pk
347 ns ± 11.3 ns per loop (mean ± std. dev. of 7 runs, 1000000 loops each)

Berikut adalah kode Django yang relevan:

def _get_pk_val(self, meta=None):
    meta = meta or self._meta
    return getattr(self, meta.pk.attname)

def _set_pk_val(self, value):
    return setattr(self, self._meta.pk.attname, value)

pk = property(_get_pk_val, _set_pk_val)

Ini benar-benar kasus yang jarang terjadi ketika saya perlu menggunakan variabel bernama pk. Saya lebih suka menggunakan sesuatu yang lebih verbose, seperti user_iddaripada pk.

Mengikuti konvensi yang sama lebih disukai di seluruh proyek. Dalam kasus Anda idadalah nama parameter, bukan properti, jadi hampir tidak ada perbedaan dalam timing. Nama parameter tidak berbenturan dengan nama id()fungsi bawaan, jadi aman untuk digunakan di idsini.

Singkatnya, terserah Anda untuk memilih apakah akan menggunakan nama bidang idatau pkpintasan. Jika Anda tidak mengembangkan perpustakaan untuk Django dan menggunakan bidang kunci utama otomatis untuk semua model, aman digunakan di idmana saja, yang terkadang lebih cepat. Dari sisi lain, jika Anda ingin akses universal ke bidang kunci utama (mungkin khusus), gunakan di pkmana-mana. Sepertiga mikrodetik bukan apa-apa untuk web.

utapyngo
sumber