Ada beberapa cara untuk menulis ke stderr:
# Note: this first one does not work in Python 3
print >> sys.stderr, "spam"
sys.stderr.write("spam\n")
os.write(2, b"spam\n")
from __future__ import print_function
print("spam", file=sys.stderr)
Itu tampaknya bertentangan dengan zen dari Python # 13 † , jadi apa bedanya di sini dan apakah ada kelebihan atau kekurangan untuk satu cara atau yang lain? Jalan mana yang harus digunakan?
† Seharusnya ada satu - dan lebih disukai hanya satu - cara yang jelas untuk melakukannya.
Jawaban:
Saya menemukan ini menjadi satu-satunya yang pendek + fleksibel + portabel + dapat dibaca:
Fungsi
eprint
ini dapat digunakan dengan cara yang sama sepertiprint
fungsi standar :sumber
print
di seluruh program Anda. Hanya dalam modul yang berisi definisieprint()
. Masukkan ke dalam file kecil dengan sendirinya, imporeprint
dari itu ke file Anda yang lain, dan Anda dapat terus menggunakan pernyataanprint
selama yang Anda inginkan.Adalah pilihan saya, hanya lebih mudah dibaca dan mengatakan dengan tepat apa yang ingin Anda lakukan dan portable di seluruh versi.
Sunting: menjadi 'pythonic' adalah pemikiran ketiga untuk saya tentang keterbacaan dan kinerja ... dengan dua hal ini dalam pikiran, dengan python 80% dari kode Anda akan pythonic. daftar pemahaman menjadi 'hal besar' yang tidak sering digunakan (keterbacaan).
sumber
print
pernyataan ini adalah mencetak nilai-nilai non-string dengan mudah, tanpa harus mengubahnya terlebih dahulu. Jika Anda memerlukan pernyataan cetak, oleh karena itu saya akan merekomendasikan menggunakan opsi ke-3 untuk menjadi python 3 siapsys.stderr.write()
tidak sepertiprint
. Itu tidak menambahkan baris baru.os.linesep
. Ini yang sedangstderr
kita bicarakan. Tidak ingin konsol mengacaukan baris baru yang salah.print >> sys.stderr
hilang dalam Python3. http://docs.python.org/3.0/whatsnew/3.0.html mengatakan:Bagi banyak dari kita, rasanya agak tidak wajar untuk memindahkan tujuan ke akhir perintah. Alternatifnya
terlihat lebih berorientasi objek, dan secara elegan beralih dari generik ke spesifik. Tetapi perhatikan bahwa
write
itu bukan pengganti 1: 1 untukprint
.sumber
print('spam', file=sys.stderr)
. Jika Anda melakukannya berulang-ulang, Anda dapat membuat kode fungsi 'eprint' seperti pada jawaban paling populer, tetapi dalam hal ini, saya akan bertanya, apa yang salah dengan logging? stackoverflow.com/a/41304513/1450294with sys.stderr as dest:
sebelum panggilan indentasi keprint("ERROR", file=dest)
Belum ada yang disebutkan
logging
, tetapi pencatatan dibuat khusus untuk mengkomunikasikan pesan kesalahan. Konfigurasi dasar akan mengatur penulisan stream handler ke stderr.Skrip ini:
memiliki hasil berikut ketika dijalankan di baris perintah:
dan bar.txt akan berisi 'hello world' yang dicetak di stdout.
sumber
Untuk Python 2 pilihan saya adalah:
print >> sys.stderr, 'spam'
Karena Anda cukup mencetak daftar / dicts dll tanpa mengubahnya menjadi string.print >> sys.stderr, {'spam': 'spam'}
dari pada:sys.stderr.write(str({'spam': 'spam'}))
sumber
"{0}".format({'spam': 'spam'})
, bukan? Saya akan mengatakan Anda harus menghindari konversi secara eksplisit ke string. Sunting: Saya tidak sengaja tata bahasaSaya melakukan yang berikut ini dengan menggunakan Python 3:
Jadi sekarang saya dapat menambahkan argumen kata kunci, misalnya, untuk menghindari carriage return:
sumber
Saya akan mengatakan bahwa pendekatan pertama Anda:
adalah "Satu ... cara yang jelas untuk melakukannya" Yang lain tidak memenuhi aturan # 1 ("Cantik lebih baik daripada yang jelek.")
sumber
>>
artinya secara sintaksis? Saya mengerti bahwa ini adalah upaya untuk menyalin bash>
, jadi apakah itu beberapa sintaksis shoehorned untuk melakukan hal itu?std::cout << "spam";
Ini akan meniru fungsi cetak standar tetapi menghasilkan pada stderr
sumber
print
tidak termasuk flush.Dalam Python 3, kita cukup menggunakan print ():
hampir keluar dari kotak:
atau:
Ini mudah dan tidak perlu memasukkan apa pun selain itu
sys.stderr
.sumber
EDIT Di belakang-penglihatan, saya pikir potensi kebingungan dengan mengubah sys.stderr dan tidak melihat perilaku diperbarui membuat jawaban ini tidak sebagus hanya menggunakan fungsi sederhana seperti yang orang lain tunjukkan.
Menggunakan sebagian hanya menghemat 1 baris kode. Potensi kebingungan tidak layak disimpan 1 baris kode.
asli
Untuk membuatnya lebih mudah, inilah versi yang menggunakan 'parsial', yang merupakan bantuan besar dalam fungsi pembungkus.
Anda kemudian menggunakannya seperti itu
Anda dapat memeriksa apakah itu mencetak ke stderr dan tidak stdout dengan melakukan hal berikut (kode over-riding dari http://coreygoldberg.blogspot.com.au/2009/05/python-redirect-or-turn-off-stdout-and .html ):
Kelemahan dari ini adalah sebagian memberikan nilai sys.stderr ke fungsi yang dibungkus pada saat penciptaan. Yang berarti, jika Anda mengarahkan ulang stderr nanti tidak akan memengaruhi fungsi ini. Jika Anda berencana untuk mengarahkan ulang stderr, maka gunakan metode ** kwargs yang disebutkan oleh aaguirre di halaman ini.
sumber
Hal yang sama berlaku untuk stdout:
Seperti yang dinyatakan dalam jawaban lain, cetak menawarkan antarmuka yang cantik yang seringkali lebih nyaman (misalnya untuk mencetak informasi debug), sementara menulis lebih cepat dan juga bisa lebih nyaman ketika Anda harus memformat output dengan cara tertentu. Saya akan mempertimbangkan rawatan:
Anda nanti dapat memutuskan untuk beralih antara stdout / stderr dan file biasa.
print () sintaks telah berubah di Python 3, jadi jika Anda perlu mendukung kedua versi, tulis () mungkin lebih baik.
sumber
from __future__ import print_function
adalah cara yang lebih baik untuk mendukung Python 2.6+ dan Python 3.Saya bekerja di python 3.4.3. Saya memotong sedikit pengetikan yang menunjukkan bagaimana saya sampai di sini:
Apa itu bekerja? Coba redirect stderr ke file dan lihat apa yang terjadi:
Nah, selain dari fakta bahwa sedikit pengantar yang diberikan python kepada Anda telah disedot ke dalam stderr (ke mana lagi ia akan pergi?), Ia bekerja.
sumber
Jika Anda melakukan tes sederhana:
Anda akan menemukan bahwa sys.stderr.write () secara konsisten 1,81 kali lebih cepat!
sumber
Jika Anda ingin keluar dari program karena kesalahan fatal, gunakan:
dan
import sys
di header.sumber
Perbedaan antara fungsi tulis cetak dan stderr: stderr : stderr (standard error) adalah pipa yang dibangun ke dalam setiap sistem UNIX / Linux, ketika program Anda crash dan mencetak informasi debugging (seperti traceback dengan Python), ia pergi ke stderr pipa.
print : print adalah pembungkus yang memformat input (input adalah ruang antara argumen dan baris baru di akhir) dan kemudian memanggil fungsi tulis dari objek yang diberikan, objek yang diberikan secara default adalah sys.stdout, tapi kita bisa lewat file yaitu kita dapat mencetak input dalam file juga.
Python2: Jika kita menggunakan python2 maka
http://python3porting.com/noconv.html
https://docs.python.org/2/library/logging.html#logger-objects
sumber