Me preguntaba si hay pautas generales para optimizar los scripts de Bash.
Por ejemplo, es más conveniente escribir bucles que líneas de comandos, pero ¿también es más rápido procesar para el sistema? Ejemplo:
for i in a b c; do echo $i; done echo a echo b echo c
A veces las personas presentan diferentes soluciones para el mismo problema. Por ejemplo,
sed
,cut
,awk
, yecho
son todos capaces de despojar a los dígitos de una cadena. Me preguntaba si puede decir que cuanto menos código de dígitos tenga, más rápido será si usa:el mismo comando, por ejemplo
STRING=abc.def echo ${STRING} | sed 's/.def//g' echo ${STRING} | sed '$s/....$//'
diferentes comandos, por ejemplo
STRING=abc.def echo ${STRING} | cut -d . -f 1 echo ${STRING} | sed 's/.def//g'
shell-script
Vincent
fuente
fuente
Respuestas:
Los shells no reorganizan el código que reciben, solo se interpreta una línea tras otra (nada más tiene sentido en un intérprete de comandos). Gran parte del tiempo dedicado por el shell se destina al análisis léxico / análisis / lanzamiento de los programas llamados.
Para operaciones simples (como las que combinan cadenas en los ejemplos al final de la pregunta), me sorprendería si el momento de cargar los programas no abruma las diferencias de velocidad minúsculas.
La moraleja de la historia es que si realmente necesita más velocidad, es mejor usar un lenguaje (semi) compilado como Perl o Python, que es más rápido para comenzar, en el que puede escribir muchas de las operaciones mencionadas directamente y no tiene que llamar a programas externos, y tiene la opción de invocar programas externos o llamar a módulos C (o lo que sea) optimizados para hacer gran parte del trabajo. Esa es la razón por la cual en Fedora el "azúcar de administración del sistema" (esencialmente las GUI) están escritas en Python: puede agregar una buena GUI sin demasiado esfuerzo, lo suficientemente rápido para tales aplicaciones, tener acceso directo a las llamadas del sistema. Si eso no es suficiente velocidad, toma C ++ o C.
Pero no vaya allí, a menos que pueda demostrar que la ganancia de rendimiento vale la pérdida de flexibilidad y tiempo de desarrollo. Los scripts de Shell no son demasiado malos para leer, pero me estremezco cuando recuerdo algunos scripts utilizados para instalar Ultrix que una vez intenté descifrar. Me di por vencido, se había aplicado demasiada "optimización de script de shell".
fuente
La primera regla de optimización es: no optimizar . Prueba primero. Si las pruebas muestran que su programa es demasiado lento, busque posibles optimizaciones.
La única forma de estar seguro es comparar su caso de uso. Existen algunas reglas generales, pero solo se aplican a volúmenes de datos típicos en aplicaciones típicas.
Algunas reglas generales que pueden o no ser ciertas en cualquier circunstancia particular:
echo $foo
es más lento queecho "$foo"
, porque sin comillas dobles, se divide$foo
en palabras e interpreta cada palabra como un patrón comodín de nombre de archivo. Más importante aún, rara vez se desea ese comportamiento de división y engrosamiento. Por lo tanto, recuerde siempre poner comillas dobles alrededor de sustituciones variables y sustituciones de comandos:"$foo"
,"$(foo)"
.cut
ohead
pueden ser emuladas consed
, perosed
serán más lentas eawk
incluso más lentas. El procesamiento de cadenas de shell es lento, pero para cadenas cortas supera en gran medida la llamada a un programa externo.Es raro que el rendimiento sea una preocupación en los scripts de shell. La lista anterior es puramente indicativa; está perfectamente bien usar métodos "lentos" en la mayoría de los casos, ya que la diferencia es a menudo una fracción de un porcentaje.
Por lo general, el objetivo de un script de shell es hacer algo rápido. Tienes que ganar mucho con la optimización para justificar pasar más minutos escribiendo el guión.
fuente
python
yruby
definitivamente son más lentos para comenzar, al menos en mi sistema,perl
es tan rápido comobash
oksh
. GNU awk es significativamente más lento que GNU sed especialmente en entornos locales utf-8, pero no es cierto para todos los awks y todos los seds. ksh93> dash> pdksh> zsh> bash no siempre es tan claro como eso. Algunos proyectiles son mejores en algunas cosas que otros, y el ganador no siempre es el mismo.Errores robados del script de shell común por Pádraig Brady.
fuente
for i in *; do wc -l "$i">/dev/null; done
hacerlo mejorfor i in *; do wc -l "$i"; done>/dev/null
.time
cmdwc -l
, comprueba que he actualizado en publicar tu salida