Saya menyimpan program berikut di new.c
int main()
{
a;
return 0;
}
Ini mengembalikan pesan kesalahan. Saya ingin mengirim pesan ini ke file. Jadi saya menggunakan perintah berikut
gcc new.c > temp.txt
Tapi saya masih mendapatkan output di terminal. Saya menggunakan Ubuntu 13.04. Bagaimana saya bisa membuatnya bekerja?
Jawaban:
Ketika Anda mengkompilasi program dengan
gcc
, ada berbagai jenis output: kestdout
danstderr
. Biasanya,>
akan mengarahkanstdout
aliran ke file (misalnya, hasil dariprintf("hello world\n");
dikirim kestdout
). Namun,stderr
terus dikirim ke layar, karena itu dianggap "sesuatu yang luar biasa yang perlu Anda ketahui".Ada cara untuk mengarahkan stderr ke file - Anda melakukan ini dengan perintah berikut (tidak sangat intuitif):
di mana
&>
"bash steno" untuk "redirect everything". Seperti yang ditunjukkan oleh @CharlesDuffy, formulir yang sesuai dengan POSIX adalahIni berarti "kompilasi 'new.c' dan kirim
stdout
kemyFile
. Dan kirimstderr
(2) ke tempat yang sama denganstdout
(&1
=" tempat yang sama dengan stdout ").Anda akan menemukan detail lebih lanjut tentang pengalihan yang berbeda di http://tldp.org/HOWTO/Bash-Prog-Intro-HOWTO-3.html dan http://mywiki.wooledge.org/BashFAQ/055
Omong-omong, jika Anda ingin mengirim sesuatu dari dalam program Anda khusus untuk
stderr
, Anda dapat melakukannya dengan berikut iniJika Anda memasukkannya ke dalam program, jalankan program dan kirim output "normal" ke file, ini masih akan muncul di konsol. Jadi, jika Anda mengkompilasi di atas ke dalam executable
urgent
, ketikkandi konsol, output Anda akan muncul di layar.
sumber
>myFile 2>&1
) dan juga ekstensi bash (&>
).Karena
>
hanya mengarahkan ulang stdout, dan kesalahan ditulisstderr
, Anda perlu menggunakan salah satu dari berikut ini sebagai gantinya:...atau...
&>
adalah ekstensi BASH yang mengarahkan baikstdout
danstderr
ke file; sebaliknya, pendekatan termudah adalah dengan stdout redirect pertama (>temp.txt
), dan kemudian membuat stderr (FD 2) salinan file handle yang sudah diarahkan pada stdout (FD 1), seperti:2>&1
.sumber
Seperti yang dikatakan orang lain, linux menyediakan dua aliran keluaran yang berbeda:
stdout , atau "output standar" adalah tempat semua output biasa berjalan.
Anda dapat referensi menggunakan deskriptor file
1
.stderr , atau "standard error" adalah aliran terpisah untuk informasi out-of-band.
Anda dapat referensi menggunakan deskriptor file
2
.Mengapa dua aliran output berbeda? Pertimbangkan pipa perintah imajiner:
Sekarang bayangkan
decrypt
perintah gagal dan menghasilkan pesan kesalahan. Jika mengirim pesanstdout
itu, itu akan mengirim ke pipa, dan kecuali jika ada kata "rahasia" Anda tidak akan pernah melihatnya. Jadi, Anda akan berakhir dengan file output kosong, tanpa tahu apa yang salah.Namun, karena pipa hanya menangkap
stdout
,decrypt
perintah dapat mengirim kesalahannya kestderr
, di mana mereka akan ditampilkan di konsol.Anda dapat mengarahkan
stdout
danstderr
, baik bersama-sama atau secara mandiri:Anda dapat mengarahkan kesalahan ke
stdout
dan memprosesnya seolah-olah itu adalah output normal:Anda juga dapat menggunakan "singkatan" notasi untuk mengarahkan kedua stdout dan stderr ke file yang sama:
Dan, akhirnya,
>
operator akan terlebih dahulu memotong file outputnya sebelum menulis ke sana. Sebaliknya, jika Anda ingin menambahkan data ke file yang ada, gunakan>>
operator:sumber
$FOO
) adalah sumber bug yang umum, dan menunjukkannya dalam contoh tidak terlalu bagus. (2) Penggunaan nama variabel semua-huruf besar adalah alasan utama untuk konflik namespace antara variabel lingkungan dan bawaan (huruf besar dengan konvensi) dan variabel lokal (huruf kecil dengan konvensi). (3) Mendorong orang untuk berulang kali menggunakan>>
(yang membuka kembali file setiap kali digunakan dalam perintah) daripada membuka file sekali dan membiarkan deskriptor file terbuka untuk digunakan oleh beberapa perintah menghasilkan kode yang tidak efisien.exec 4>secrets; echo "this is a secret" >&4; echo "this is another secret" >&4
exec
karena kesederhanaan, meskipun dalam praktiknya itu umumnya strategi yang lebih baik.command₁
>
output_file
;
command₂
>>
the_same_output_file
(
command₁
;
command₂
) >
output_file
{
command₁
;
command₂
; } >
output_file
{
;
}