Je ne sais pas comment c'est en bash, mais en zsh vous pouvez définir preexec
et precmd
fonctions pour qu'elles enregistrent l'heure actuelle dans les variables $STARTTIME
(preexec) et $ENDTIME
(precmd) afin que vous puissiez trouver le temps d'exécution approximatif. Ou vous pouvez définir un accept-line
fonction pour qu'elle préfixe time
avant chaque commande.
MISE À JOUR :C'est le code qui stockera les temps écoulés dans le $_elapsed
tableau :
preexec () {
(( $#_elapsed > 1000 )) && set -A _elapsed $_elapsed[-1000,-1]
typeset -ig _start=SECONDS
}
precmd() { set -A _elapsed $_elapsed $(( SECONDS-_start )) }
Ensuite, si vous exécutez sleep 10s
:
% set -A _elapsed # Clear the times
% sleep 10s
% sleep 2s ; echo $_elapsed[-1]
10
% echo $_elapsed
0 10 0
Pas besoin de quatre variables. Pas de problèmes avec les noms ou des retards supplémentaires. Notez simplement que $_elapsed
array peut devenir très gros, vous devez donc supprimer les premiers éléments (cela se fait avec le morceau de code suivant :(( $#_elapsed > 1000 )) && set -A _elapsed $_elapsed[-1000,-1]
).
MISE À JOUR2 :Trouvé le script pour prendre en charge les precmd et preexec de style zsh dans bash. Peut-être devrez-vous supprimer typeset -ig
(J'avais juste l'habitude de forcer $_start
être entier) et remplacer set -A var ...
avec var=( ... )
afin que cela fonctionne. Et je ne sais pas comment découper des tableaux et obtenir leur longueur en bash.
Script :http://www.twistedmatrix.com/users/glyph/preexec.bash.txt
MISE À JOUR3 :Trouvé un problème :si vous appuyez sur retour avec une ligne vide, preexec ne s'exécute pas, alors que precmd le fait, vous obtiendrez donc des valeurs sans signification dans $_elapsed
déployer. Pour résoudre ce problème, remplacez le precmd
fonction avec le code suivant :
precmd () {
(( _start >= 0 )) && set -A _elapsed $_elapsed $(( SECONDS-_start ))
_start=-1
}
Le monde a peut-être un peu évolué depuis que d'autres personnes ont répondu à ces questions.
zsh
a des fonctionnalités intégrées pour chronométrer le temps que prennent les commandes.
Si vous activez l'option inc_append_history_time avec
setopt inc_append_history_time
Ensuite, le temps nécessaire pour exécuter chaque commande est enregistré dans votre historique et peut ensuite être visualisé avec history -D
.
La structure de cette réponse :
- Il n'y a pas de méthode toute faite pour chronométrer une commande qui a déjà été exécutée
- Il existe des moyens de déduire une estimation approximative de la durée d'exécution d'une commande.
- Une preuve de concept est présentée (commençant par l'hypothèse que cela ne peut pas être fait et se terminant par la conclusion que l'hypothèse était fausse).
- Il existe des hacks que vous pouvez mettre en place à l'avance pour enregistrer le temps écoulé de chaque commande que vous exécutez
- Conclusion
La réponse étiquetée par ses parties selon le schéma ci-dessus :
Partie 1 - la réponse courte est "non"
Non désolé. Vous devez utiliser time
.
Partie 2 - peut-être pouvez-vous en déduire un résultat
Dans certains cas, si un programme écrit des fichiers de sortie ou des informations dans des fichiers journaux, vous pourrez peut-être en déduire le temps d'exécution, mais ce serait spécifique au programme et seulement une estimation. Si HISTTIMEFORMAT est défini dans Bash, vous pouvez consulter les entrées du fichier d'historique pour avoir une idée du démarrage d'un programme. Mais l'heure de fin n'est pas enregistrée, vous ne pouvez donc en déduire une durée que si un autre programme a été démarré immédiatement après la fin de celui qui vous intéresse.
Partie 3 - une hypothèse est infirmée
Hypothèse :Le temps d'inactivité sera compté dans le temps écoulé
Voici un exemple pour illustrer mon propos. Il est basé sur la suggestion de ZyX , mais serait similaire avec d'autres méthodes.
En 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
Maintenant on attend... disons 15 secondes, puis :
% echo "T: $SECONDS"; sleep 10
T: 1506
Maintenant on attend... disons 20 secondes, puis :
% echo "T: $SECONDS ps: $prevstart pe: $prevend s: $start e: $end"
T: 1536 ps: 1492 pe: 1506 s: 1516 e: 1536
Comme vous pouvez le voir, j'avais tort . L'heure de début (1516) moins la précédente heure de fin (1506) est la durée de la commande (sleep 10
).
Hypothèse falsifiée - c'est c'est possible d'obtenir le temps écoulé correct sans inclure le temps d'inactivité
Partie 4 - un hack pour enregistrer le temps écoulé de chaque commande
Voici les équivalents Bash des fonctions de ZyX réponse (ils nécessitent le script lié à celui-ci):
preexec () {
(( ${#_elapsed[@]} > 1000 )) && _elapsed=(${_elapsed[@]: -1000})
_start=$SECONDS
}
precmd () {
(( _start >= 0 )) && _elapsed+=($(( SECONDS-_start )))
_start=-1
}
Après avoir installé preexec.bash
(à partir du script lié) et en créant les deux fonctions ci-dessus, l'exemple d'exécution ressemblerait à ceci :
$ _elapsed=() # Clear the times
$ sleep 10s
$ sleep 2s ; echo ${_elapsed[@]: -1}
10
$ echo ${_elapsed[@]}
0 10 2
Partie 5 -conclusion
Utilisez time
.