Obtenir le temps d’exécution du programme dans le shell

Je veux exécuter quelque chose dans un shell Linux sous différentes conditions et être capable de générer le temps d’exécution de chaque exécution.

Je sais que je pourrais écrire un script perl ou python qui le ferait, mais y a-t-il un moyen de le faire dans le shell? (qui se trouve être bash)

Utilisez le mot time clé de time intégré:

 $ temps d'aide

 time: time [-p] PIPELINE
     Exécutez PIPELINE et imprimez un résumé du temps réel en temps réel,
     et le temps CPU du système passé à exécuter PIPELINE quand il se termine.
     Le statut de retour est le statut de retour de PIPELINE.  L'option `-p '
     imprime le résumé de synchronisation dans un format légèrement différent.  Cela utilise
     la valeur de la variable TIMEFORMAT comme format de sortie.

Exemple:

 $ time sleep 2 
 vrai 0m2.009s
 utilisateur 0m0.000s
 sys 0m0.004s

Vous pouvez obtenir des informations beaucoup plus détaillées que le temps intégré bash (mentionné par Robert Gamble) en utilisant le temps (1) . Normalement, il s’agit de /usr/bin/time .

Remarque de l’éditeur: pour vous assurer que vous appelez l’ time utilitaire externe plutôt que le mot clé time de votre shell, appelez-le sous la forme /usr/bin/time .
time est un utilitaire POSIX , mais la seule option requirejse pour la prise en charge est -p .
Des plates-formes spécifiques implémentent des extensions non standard spécifiques: -v fonctionne avec l’utilitaire de time GNU , comme démontré ci-dessous (la question est balisée linux ); l’implémentation BSD / macOS utilise -l pour produire une sortie similaire – voir man 1 time .

Exemple de sortie verbeuse:

$ /usr/bin/time -v sleep 1 Command being timed: "sleep 1" User time (seconds): 0.00 System time (seconds): 0.00 Percent of CPU this job got: 1% Elapsed (wall clock) time (h:mm:ss or m:ss): 0:01.05 Average shared text size (kbytes): 0 Average unshared data size (kbytes): 0 Average stack size (kbytes): 0 Average total size (kbytes): 0 Maximum resident set size (kbytes): 0 Average resident set size (kbytes): 0 Major (requiring I/O) page faults: 0 Minor (reclaiming a frame) page faults: 210 Voluntary context switches: 2 Involuntary context switches: 1 Swaps: 0 File system inputs: 0 File system outputs: 0 Socket messages sent: 0 Socket messages received: 0 Signals delivered: 0 Page size (bytes): 4096 Exit status: 0
$ /usr/bin/time -v sleep 1 Command being timed: "sleep 1" User time (seconds): 0.00 System time (seconds): 0.00 Percent of CPU this job got: 1% Elapsed (wall clock) time (h:mm:ss or m:ss): 0:01.05 Average shared text size (kbytes): 0 Average unshared data size (kbytes): 0 Average stack size (kbytes): 0 Average total size (kbytes): 0 Maximum resident set size (kbytes): 0 Average resident set size (kbytes): 0 Major (requiring I/O) page faults: 0 Minor (reclaiming a frame) page faults: 210 Voluntary context switches: 2 Involuntary context switches: 1 Swaps: 0 File system inputs: 0 File system outputs: 0 Socket messages sent: 0 Socket messages received: 0 Signals delivered: 0 Page size (bytes): 4096 Exit status: 0 
 #!/bin/bash START=$(date +%s) # do something # start your script work here ls -R /etc > /tmp/x rm -f /tmp/x # your logic ends here END=$(date +%s) DIFF=$(( $END - $START )) echo "It took $DIFF seconds" 

Pour une mesure delta ligne par ligne, essayez gnomon .

Un utilitaire de ligne de commande, un peu comme les moreutils, pour append les informations d’horodatage à la sortie standard d’une autre commande. Utile pour les processus de longue durée où vous souhaitez un historique de ce qui prend tant de temps.

Vous pouvez également utiliser les --high et / ou --medium pour spécifier un seuil de longueur en secondes, sur lequel gnomon mettra en évidence l’horodatage en rouge ou en jaune. Et vous pouvez faire quelques autres choses aussi.

Exemple

Si vous voulez plus de précision, utilisez %N avec date (et utilisez bc pour le diff, car $(()) ne gère que les entiers).

Voici comment faire:

 start=$(date +%s.%N) # do some stuff here dur=$(echo "$(date +%s.%N) - $start" | bc) printf "Execution time: %.6f seconds" $dur 

Exemple:

 start=$(date +%s.%N); \ sleep 0.1s; \ dur=$(echo "$(date +%s.%N) - $start" | bc); \ printf "Execution time: %.6f seconds\n" $dur 

Résultat:

 Execution time: 0.104623 seconds 

Si vous avez l’intention d’utiliser les temps plus tard pour calculer, apprenez à utiliser l’option -f de /usr/bin/time pour générer du code qui permet de gagner du temps. Voici un code que j’ai utilisé récemment pour obtenir et sortinger les temps d’exécution d’une classe entière de programmes pour étudiants:

 fmt="run { date = '$(date)', user = '$who', test = '$test', host = '$(hostname)', times = { user = %U, system = %S, elapsed = %e } }" /usr/bin/time -f "$fmt" -o $timefile command args... 

J’ai ensuite concaténé tous les fichiers $timefile et $timefile la sortie dans un interpréteur Lua . Vous pouvez faire la même chose avec Python ou bash ou quelle que soit votre syntaxe préférée. J’aime cette technique.

Si vous avez seulement besoin de précision à la seconde, vous pouvez utiliser la variable intégrée $SECONDS , qui compte le nombre de secondes pendant lesquelles le shell a été exécuté.

 while true; do start=$SECONDS some_long_running_command duration=$(( SECONDS - start )) echo "This run took $duration seconds" if some_condition; then break; fi done 

Vous pouvez utiliser le time et le sousshell () :

 time ( for (( i=1; i<10000; i++ )); do echo 1 >/dev/null done ) 

Ou dans le même shell {} :

 time { for (( i=1; i<10000; i++ )); do echo 1 >/dev/null done } 

Le chemin est

 $ > g++ -lpthread perform.c -o per $ > time ./per 

la sortie est >>

 real 0m0.014s user 0m0.010s sys 0m0.002s