Tampaknya ada dua cara yang berbeda untuk mengkonversi string ke byte, seperti yang terlihat dalam jawaban https://stackoverflow.com/questions/5471158/typeerror-str-does-not-support-the-buffer-interface
Yang mana metode ini akan lebih baik atau lebih Pythonic? Atau itu hanya masalah preferensi pribadi?
b = bytes(mystring, 'utf-8')
b = mystring.encode('utf-8')
Jika anda melihat docs untuk byte
, itu poin anda ke bytearray
:
bytearray([sumber[, encoding [kesalahan]]])
Return array dari byte. Yang bytearray jenis ini bisa berubah urutan bilangan bulat dalam rentang 0 <= x < 256. Ini memiliki sebagian besar metode yang biasa bisa berubah urutan, yang dijelaskan dalam Urutan bisa Berubah Jenis, serta sebagian besar metode yang byte jenis memiliki, melihat Byte dan Byte Array Metode.
opsional sumber parameter yang dapat digunakan untuk menginisialisasi array dalam beberapa cara yang berbeda:
Jika itu adalah string, anda juga harus memberikan pengkodean (dan opsional, kesalahan) parameter; bytearray() kemudian mengkonversi string ke byte menggunakan str.encode().
Jika itu adalah integer, array akan memiliki ukuran yang dan akan diinisialisasi dengan null byte.
Jika itu adalah sebuah objek sesuai dengan penyangga antarmuka, hanya-baca penyangga dari objek yang akan digunakan untuk menginisialisasi byte array.
Jika itu adalah sebuah iterable, itu harus menjadi iterable bilangan bulat dalam rentang 0 <= x < 256, yang digunakan sebagai isi awal dari array.
Tanpa argumen, sebuah array dari ukuran 0 dibuat.
Jadi byte
dapat melakukan lebih dari hanya mengkodekan string. It's Pythonic bahwa hal itu akan memungkinkan anda untuk memanggil konstruktor dengan jenis sumber parameter yang masuk akal.
Untuk encoding string, saya berpikir bahwa some_string.encode(encoding)
lebih Pythonic dari menggunakan konstruktor, karena itu adalah yang paling mandiri mendokumentasikan -- "mengambil string ini dan encode dengan encoding" jelas dari byte(some_string, encoding)
-- tidak ada secara eksplisit kerja ketika anda menggunakan konstruktor.
Edit: aku memeriksa Python sumber. Jika anda melewati sebuah string unicode untuk byte
menggunakan CPython, itu panggilan PyUnicode_AsEncodedString, yang merupakan implementasi dari encode
; jadi anda're hanya untuk melewatkan tingkat tipuan jika anda menelepon encode
diri sendiri.
Juga, melihat Serdalis' komentar -- unicode_string.encode(encoding)
juga lebih Pythonic karena kebalikannya adalah byte_string.decode(encoding)
dan simetri bagus.
It's lebih mudah daripada berpikir:
my_str = "hello world"
my_str_as_bytes = str.encode(my_str)
type(my_str_as_bytes) # ensure it is byte representation
my_decoded_str = my_str_as_bytes.decode()
type(my_decoded_str) # ensure it is string representation
Yang benar-benar cara terbaik adalah tidak lebih dari 2, tapi yang ke-3. Parameter pertama untuk encode
default 'utf-8'
sejak Python 3.0. Dengan demikian cara terbaik adalah
b = mystring.encode()
Ini juga akan lebih cepat, karena default argumen hasil tidak dalam string "utf-8"
dalam kode C, tapi NULL
yang banyak lebih cepat untuk memeriksa!
Berikut ini ada beberapa timing:
In [1]: %timeit -r 10 'abc'.encode('utf-8')
The slowest run took 38.07 times longer than the fastest.
This could mean that an intermediate result is being cached.
10000000 loops, best of 10: 183 ns per loop
In [2]: %timeit -r 10 'abc'.encode()
The slowest run took 27.34 times longer than the fastest.
This could mean that an intermediate result is being cached.
10000000 loops, best of 10: 137 ns per loop
Meskipun peringatan kali itu sangat stabil setelah berulang kali berjalan - penyimpangan itu hanya ~2 persen.
Menggunakan encode()
tanpa argumen ini tidak Python 2 kompatibel, seperti dalam Python 2 standar pengkodean karakter ASCII.
>>> 'äöä'.encode()
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
UnicodeDecodeError: 'ascii' codec can't decode byte 0xc3 in position 0: ordinal not in range(128)