GNU/Linux >> Belajar Linux >  >> Linux

Apakah ada cara untuk menemukan waktu berjalan dari perintah yang terakhir dieksekusi di shell?

Saya tidak tahu, bagaimana di bash, tapi di zsh Anda bisa mendefinisikan preexec dan precmd fungsi sehingga mereka menyimpan waktu saat ini ke variabel $STARTTIME (preexec) dan $ENDTIME (precmd) sehingga Anda dapat menemukan perkiraan waktu berjalan. Atau Anda dapat menentukan accept-line berfungsi sehingga akan menambahkan time sebelum setiap perintah.

PEMBARUAN :Ini adalah kode, yang akan menyimpan waktu yang telah berlalu di $_elapsed larik:

preexec () {
   (( $#_elapsed > 1000 )) && set -A _elapsed $_elapsed[-1000,-1]
   typeset -ig _start=SECONDS
}
precmd() { set -A _elapsed $_elapsed $(( SECONDS-_start )) }

Kemudian jika Anda menjalankan sleep 10s :

% set -A _elapsed # Clear the times
% sleep 10s
% sleep 2s ; echo $_elapsed[-1]
10
% echo $_elapsed
0 10 0

Tidak perlu dalam empat variabel. Tidak ada masalah dengan nama atau penundaan tambahan. Perhatikan bahwa $_elapsed array dapat tumbuh sangat besar, jadi Anda perlu menghapus item pertama (ini dilakukan dengan potongan kode berikut:(( $#_elapsed > 1000 )) && set -A _elapsed $_elapsed[-1000,-1] ).

PEMBARUAN2 :Menemukan skrip untuk mendukung gaya zsh precmd dan preexec di bash. Mungkin Anda perlu menghapus typeset -ig (Saya dulu hanya memaksa $_start menjadi bilangan bulat) dan ganti set -A var ... dengan var=( ... ) untuk membuat ini berfungsi. Dan saya tidak tahu cara mengiris array dan mendapatkan panjangnya di bash.

Skrip:http://www.twistedmatrix.com/users/glyph/preexec.bash.txt

PEMBARUAN3 :Menemukan satu masalah:jika Anda menekan kembali dengan baris kosong preexec tidak berjalan, sedangkan precmd berjalan, maka Anda akan mendapatkan nilai yang tidak berarti di $_elapsed Himpunan. Untuk memperbaikinya, ganti precmd fungsi dengan kode berikut:

precmd () {
   (( _start >= 0 )) && set -A _elapsed $_elapsed $(( SECONDS-_start ))
   _start=-1 
}

Dunia mungkin sedikit bergerak sejak orang lain menjawab pertanyaan ini.

zsh memiliki beberapa fitur bawaan untuk menghitung waktu yang dibutuhkan perintah.

Jika Anda mengaktifkan opsi inc_append_history_time dengan

setopt inc_append_history_time

Kemudian waktu yang diperlukan untuk menjalankan setiap perintah disimpan dalam riwayat Anda dan kemudian dapat dilihat dengan history -D .


Struktur jawaban ini:

  1. Tidak ada cara siap pakai untuk mengatur waktu perintah yang telah dijalankan
  2. Ada beberapa cara untuk menyimpulkan perkiraan durasi waktu perintah berjalan.
  3. Bukti konsep ditampilkan (dimulai dengan hipotesis bahwa hal itu tidak dapat dilakukan dan diakhiri dengan kesimpulan bahwa hipotesis itu salah).
  4. Ada peretasan yang dapat Anda lakukan sebelumnya yang akan mencatat waktu berlalu dari setiap perintah yang Anda jalankan
  5. Kesimpulan

Jawaban diberi label menurut bagian-bagiannya sesuai dengan garis besar di atas:

Bagian 1 - jawaban singkatnya adalah "tidak"

Tidak maaf. Anda harus menggunakan time .

Bagian 2 - mungkin Anda bisa menyimpulkan hasilnya

Dalam beberapa kasus jika suatu program menulis file keluaran atau informasi dalam file log, Anda mungkin dapat menyimpulkan waktu berjalan, tetapi itu akan menjadi khusus program dan hanya perkiraan. Jika Anda mengatur HISTTIMEFORMAT di Bash, Anda dapat melihat entri di file riwayat untuk mengetahui kapan program dimulai. Namun waktu berakhir tidak dicatat, jadi Anda hanya dapat menyimpulkan durasi jika program lain dimulai segera setelah program yang Anda minati selesai.

Bagian 3 - hipotesis dipalsukan

Hipotesis :Waktu idle akan dihitung dalam waktu yang telah berlalu

Berikut adalah contoh untuk mengilustrasikan poin saya. Ini berdasarkan saran dari ZyX , tetapi akan serupa menggunakan metode lain.

Di zsh :

% precmd() { prevstart=start; start=$SECONDS; }
% preexec() { prevend=$end; end=$SECONDS; }
% echo "T: $SECONDS ps: $prevstart pe: $prevend s: $start e: $end"
T: 1491 ps: 1456 pe: 1458 s: 1459 e: 1491

Sekarang kita tunggu... katakanlah selama 15 detik, lalu:

% echo "T: $SECONDS"; sleep 10
T: 1506

Sekarang kita tunggu... katakanlah selama 20 detik, lalu:

% echo "T: $SECONDS ps: $prevstart pe: $prevend s: $start e: $end"
T: 1536 ps: 1492 pe: 1506 s: 1516 e: 1536

Seperti yang Anda lihat, saya salah . Waktu mulai (1516) dikurangi sebelumnya waktu berakhir (1506) adalah durasi perintah (sleep 10 ).

Hipotesis dipalsukan - itu adalah mungkin untuk mendapatkan waktu berlalu yang benar tanpa menyertakan waktu idle

Bagian 4 - retasan untuk merekam waktu berlalu setiap perintah

Berikut adalah Bash yang setara dengan fungsi di ZyX's jawaban (mereka membutuhkan skrip yang ditautkan ke sana):

preexec () {
   (( ${#_elapsed[@]} > 1000 )) && _elapsed=(${_elapsed[@]: -1000})
   _start=$SECONDS
}

precmd () {
   (( _start >= 0 )) && _elapsed+=($(( SECONDS-_start )))
   _start=-1 
}

Setelah memasang preexec.bash (dari skrip tertaut) dan membuat dua fungsi di atas, contoh proses akan terlihat seperti ini:

$ _elapsed=() # Clear the times
$ sleep 10s
$ sleep 2s ; echo ${_elapsed[@]: -1}
10
$ echo ${_elapsed[@]}
0 10 2

Bagian 5 - kesimpulan

Gunakan time .


Linux
  1. Jadwalkan tugas dengan Linux pada perintah

  2. Alias ​​baris perintah di Linux Shell

  3. Inti Dari Perintah Eksternal `cd`?

  1. Menyesuaikan Bash Shell:Tebal/warnai Perintah?

  2. Cara Terbaik Untuk Membatalkan Semua Pekerjaan Slurm Dari Keluaran Perintah Shell?

  3. CentOS / RHEL :Cara mendapatkan tanggal dan waktu perintah yang dieksekusi di output perintah history

  1. Dari mana saya dapat menemukan kode sumber perintah cp?

  2. Apakah ada cara untuk mengubah id volume file .iso dari baris perintah?

  3. Apakah ada cara cepat untuk mendapatkan file terakhir dalam TAR besar?