Untuk apa tipe buffer Python?

138

Ada bufferjenis python, tapi saya tidak tahu bagaimana cara menggunakannya.

Dalam dokumen Python , deskripsinya adalah:

buffer(object[, offset[, size]])

Argumen objek haruslah objek yang mendukung antarmuka panggilan buffer (seperti string, array, dan buffer). Objek buffer baru akan dibuat yang mereferensikan argumen objek. Objek buffer akan menjadi potongan dari awal objek (atau dari offset yang ditentukan). Potongan akan meluas ke ujung objek (atau akan memiliki panjang yang diberikan oleh argumen ukuran).

satoru
sumber

Jawaban:

147

Contoh penggunaan:

>>> s = 'Hello world'
>>> t = buffer(s, 6, 5)
>>> t
<read-only buffer for 0x10064a4b0, size 5, offset 6 at 0x100634ab0>
>>> print t
world

Buffer dalam hal ini adalah sub-string, dimulai dari posisi 6 dengan panjang 5, dan tidak membutuhkan ruang penyimpanan ekstra - ini mereferensikan sepotong string.

Ini tidak terlalu berguna untuk string pendek seperti ini, tetapi mungkin diperlukan saat menggunakan data dalam jumlah besar. Contoh ini menggunakan bisa berubah bytearray:

>>> s = bytearray(1000000)   # a million zeroed bytes
>>> t = buffer(s, 1)         # slice cuts off the first byte
>>> s[1] = 5                 # set the second element in s
>>> t[0]                     # which is now also the first element in t!
'\x05'

Ini bisa sangat membantu jika Anda ingin memiliki lebih dari satu tampilan pada data dan tidak ingin (atau tidak bisa) menyimpan banyak salinan dalam memori.

Perhatikan bahwa buffertelah diganti dengan yang lebih baik bernama memoryviewdi Python 3, meskipun Anda dapat menggunakan baik di Python 2.7.

Perhatikan juga bahwa Anda tidak dapat mengimplementasikan antarmuka buffer untuk objek Anda sendiri tanpa mempelajari C API, yaitu Anda tidak dapat melakukannya dengan Python murni.

Scott Griffiths
sumber
Terima kasih atas penjelasan Anda. Tapi saya masih belum begitu mengerti apa perbedaan antara buffering dan simple slicing. Penggunaan s[6:11]juga tidak memakan ruang penyimpanan ekstra, apakah saya salah?
satoru
10
Secara umum sepotong akan membutuhkan penyimpanan ekstra, jadi ya s[6:11]akan menjadi salinan. Jika Anda mengatur t = s[6:11]dan kemudian del s, itu membebaskan memori yang diambil oleh s, membuktikan bahwa tdisalin. (Untuk melihat ini, Anda membutuhkan yang lebih besar sdan melacak penggunaan memori Python). Namun, jauh lebih efisien hanya membuat salinan jika tidak banyak data yang terlibat.
Scott Griffiths
1
Terima kasih banyak :) BTW, dapatkah Anda memberi tahu saya alat apa yang dapat saya gunakan untuk melacak penggunaan memori Python?
satoru
Untuk penggunaan memori, lihat stackoverflow.com/questions/110259 sebagai contoh. Terkadang paling mudah hanya untuk menonton penggunaan Python di Task Manager / Activity Monitor / top.
Scott Griffiths
13
Untuk Python noobs seperti saya: buffer adalah memoryview dengan Python 3
Dirk Bester
28

Saya pikir buffer misalnya berguna saat menghubungkan python ke perpustakaan asli. (Guido van Rossum menjelaskan bufferdi pos milis ini ).

Misalnya, numpy tampaknya menggunakan buffer untuk penyimpanan data yang efisien:

import numpy
a = numpy.ndarray(1000000)

itu a.dataadalah:

<read-write buffer for 0x1d7b410, size 8000000, offset 0 at 0x1e353b0>
Andre Holzner
sumber