en: Programacion
Estos pequeños consejos para optimizar el código de tu aplicación no son los únicos y probablemente los habrá mejores pero sin duda te pueden servir de gran ayuda si estas buscando optimizar partes de código de una aplicación, algunas de ellas son unicamente aplicables a un lenguaje en concreto pero con un poco de ingenio las podrás extrapolar a cualquiere lenguaje.
Aclarar que la optimización de código puede realizarse durante la generación o como paso adicional a esta y en último caso (menos recomendable) a posteriori.
Las optimizaciones de código en realidad proporcionan mejoras, pero obviamente no aseguran el éxito de una aplicación.
Clasificación de optimizaciones:
1. Dependientes de la máquina.
* Asignación de registros.
* Instrucciones especiales (“idioms”).
* Reordenación del código.
2. Independientes de la máquina.
* Ejecución en tiempo de compilación.
* Eliminación de redundancias.
* Cambio de orden.
* Reducción de frecuencia de ejecución (invariancias).
* Reducción de fuerza.
Tras esta breve introducción pasemos a ver cuales son las más técnicas más destacadas:
Si tienes código innecesario elimínalo, parece obvio pero en muchas ocasiones esos pequeños trozos de código se mantienen en todas las versiones de la aplicación, si tienes que reescribir una función pero no estas del todo seguro y por lo tanto no quieres perder la versión original, haz una copia de seguridad y de ese modo no se vera realentizada la ejecución de la aplicación.
Es probablemente una de los errores que puede consumir más CPU, por supuesto sé más cuidadoso con aquellos bucles que tengan mas iteraciones (Iteración significa repetir un proceso varias veces), con lo de sacar código no se trata de modificar la función final del bucle sino de optimizar al máximo su rendimiento, con esto queremos decir no incluir la declaración de una variable, no incluir comentarios, etc …
Para aquellos que no sepais ¿Qué es pasar un valor por referencia? es mejor explicarlo con un ejemplo:
function valores_por_referencia (&$var)
{
$var++;
}$a=5;
valores_por_referencia ($a);
// $a será 6 aqui
Cómo se puede deducir en el ejemplo al pasar un objeto por referencia damos la posibilidad a la función de cambiar el valor de la variable pasada, por lo tanto si pasamos los objetos por referencia ahorraremos a la máquina de copiar una y otra vez el valor de un objeto.
Manipular datos de los discos duros o de las memorias flash es mucho más lento que manipular datos almacenados en memoria por eso si vas a manejar archivos ten en cuenta este punto.
Un buen número de utiles consejos más específicos para Php los puedes encontrar aquí.
1 – Inicializa las variables antes de utilizarlas
2 – Dedica tiempo a estudiar PHP, está en un continuo proceso de crecimiento y sus características van cambiando con el tiempo.
3 – Incrementar una variable en un método es lo mas rápido, del mismo modo que hacerlo en una función.
4 – Incrementar una variable global es dos veces mas lento que una variable local.
5 – Incrementar la propiedad de un objeto (ej. $this->prop++) es 3 veces más lento que incrementar una variable local.
6 – Incrementar una variable indefinida es 9 ó 10 veces más lento que una ya pre-declarada.
7 – El hecho de declarar una variable global a pesar de que no la utilices en ninguna función realentiza tu script, PHP tiene que chequear si la variable existe.
8 – La llamada a una función con un parametro toma aproximadamente el mismo tiempo que de 7 a 8 operaciones con variables locales, y esa misma llamada a un método supondrían unas 15 operaciones.
Por último veamos algunos de los consejos más comunes de optimización (PHP) que publicamos hace ya algún tiempo.
| Código lento (No recomendado) | Código rápìdo (Recomendado) | Explicación |
| $i++; | ++$i; | Ninguna razón |
| $i += 1; | ++$i; | Ninguna razón |
| rand($min,$max); | mt_rand($min,$max); | mt_rand es matemáticamente más veloz |
| $i = 0; while($array[$i]){ ++$i; } |
$i = 0; $count = count($array); while($i < $count){ ++$i; } |
Probar si un array existe es más lento que probar que una variable es menor que otra |
| print ‘algo’; | echo ‘algo’; | echo no devuelve nada por el contrario print si lo hace |
| ob_start(); echo ‘algo’; ob_end_flush(); |
ob_start(); print ‘algo’; ob_end_flush(); |
echo no devuelve nada, print si lo hace y por lo tanto haciendo el echo se debe de evaluar dos veces |
| echo ‘algo (HTML, con etiquetas php)’; | algo (HTML, con etiquetas php) | Php es más lento que la salida directa en HTML |
| include(‘output/contain_no_php’); | readfile(‘output/contain_no_php’); | readfile devuelve directamente la salida de un fichero por el contrario include debe de evaluarlo por dos veces |
| echo “$variable cadena “; | echo $variable.’cadena’; | Las comillas simples no evaluan el contenido sin embargo las dobles comillas si lo hacen por lo que realentiza la ejecución del script |
| UNA_CONSTANTE; | $una_variable; | Ninguna razón |
| constant(‘UNA_CONSTANTE’); | UNA_CONSTANTE; | Ninguna razón |
| pi(); | M_PI; | Php crea una constante más rápido que el tiempo que tarda en calcular una función matemática, aplicar a todas aquellas constantes matemáticas existentes en Php |
|
if($numero<0){
$numero *= -1; } |
abs($numero); | Siempre utilizar una función existente en Php antes de crearla por nosotros mismos |
| pow($x , $exp) + pow($x , $exp – 1); $a*$b+$a*$c+$a*$d; |
($x + 1) * pow($x , $exp – 1); $a*($b+$c+$d); |
Las operaciones en formato expandido son habitualmente más lentas |
|
if($a == $b)
|
if($a === $b) |
La triple = no necesita convertir los tipos de datos |
| pow($x, 0.5); | sqrt($x); | Ninguna razón |
| 1/2; |
0.5; |
Php realiza la división entre 1 y 2 mientras por el contrario el segundo caso es directamente el resultado y no necesita ser procesado |
| if($a == 30); | if(30 == $a); | El segundo caso nos devolverá un error en caso de que hayamos cometido un error tipográfico del tipo ‘=’ en vez de ‘==’ , por lo tanto es mejor esta opción ya que podremos encontrar el error fácilmente |
Generar passwords accesibles con Php
Codigo Fuente del generador de passwords en PHP
Ejemplo de ejecución del script
PHP y MySql una estrecha relación
5 cosas que no sabías hacer con PHP
Generar documentos OpenOffice con PHP
Nueva versión de Notepad++
Hola Mundo!
Identificar las consultas más lentas de MySql
Crea sencillas gráficas con MySql
Programar un script PHP para saber quién está en línea
Consejos para optimizar PHP
Editando en Opera páginas web en tiempo real
6 Respuestas a Técnicas de optimización de código
Albo
18 de Mayo de 2007 a las 3:40 pm
En PHP5 todas las asignaciones o paso de variables de objetos se hace por referencias
“Cuando se asigna una instancia de un objeto previamente creado a una nueva variable, la nueva variable accesará la misma instancia que la del objeto a la que fue asignada. Este comportamiento es el mismo cuando se pasan instancias a una función. Una nueva instancia de un objeto previamente creado puede ser hecho clonandolo.”
(Extraido en la documentacion oficial http://php.net/language.oop5.basic)
Edu
18 de Mayo de 2007 a las 5:26 pm
Nada, felicitarte por el artículo. Hay un par de trucos que desconocía y me serán de utilidad.
Gracias y sigue así
Anónimo
4 de Noviembre de 2007 a las 11:54 pm
Albo, creo que te equivocas. Eso es para objetos. Para variables debes anteponer el símbolo ámpersan al declarar la interfaz para que la variable sea pasada por referencia (Capítulo 21: explicando las referencias).
Por cierto, que el paso por referencia aquí aconsejado, aunque eficiente, es peligroso porque abre la puerta a modificaciones de esa variable desde dentro de una función/método; algo peligrosísimo porque te puedes encontrar con que una variable cambia de valor sin motivo aparente durante la ejecución del código (sin motivo aparente porque no te acuerdas de qué función/método era la que la modificaba). No me parece un buen consejo salvo en casos de necesidad extrema de rendimiento. No recuerdo donde leí que el paso de valores por referencia tiende a extinguirse por los problemas que causan.
En cuanto a la recomendación de include/readfile, es un poco chorra si realmente entiendo el significado de las expresiones aquí usadas. Porque en el ejemplo se “incluye” un fichero llamado “contain_no_php”. Es decir, que ese ejemplo se aplica a la lectura de ficheros que no tienen código PHP. Si ése es el caso, la recomendación es chorra porque es una tontería hacer una “inclusion” sobre un fichero que no tiene código PHP. Total, no hay nada que evaluar en ese fichero y, por tanto, nadie usaría un include().
Respecto a los comentarios en los bucles puedo hablar con conocimiento de causa al decir que NO ES CIERTO. He hecho pruebas en las que he hecho iterar millones de veces un bucle sin y con comentarios (y cuando digo “con comentarios” digo meter comentarios con un peso 100 veces superior al código iterable), y no ha habido ninguna diferencia apreciable. Si mal no recuerdo PHP superó ese problema hace tiempo, ya que cuando ejecuta un fragmento de código emplea un enfoque parecido al de Java con el JIT, por lo que, una vez limpiados los comentarios en la primera iteración, no tiene que volver a limpiarlos en las siguientes.
Por el contrario, los comentarios son muy necesarios para comprender el funcionamiento de algunos bucles. Sencillamente no le veo beneficio por ninguna parte.
Y respecto al uso de ++$variable frente a $variable++, puedo confirmar que hay una mejora; una mejora de 1% suponiendo que el código no haga otra cosa que repetir la misma orden millones de veces…
Y el que no me crea que haga sus experimentos.
Katherine
24 de Enero de 2009 a las 1:45 pm
Excelente aporte pero sirve tambien para el posicionamiento web .
angel
13 de Noviembre de 2009 a las 12:39 pm
FOR v_conta IN 1..v_numtok LOOP
select RegresaToken(FRASE,v_conta) into v_token from dual;
select count(*) into v_cuenta from TABLADIC where ESPANOL=v_token;
IF (v_cuenta>0) then
v_esp:=v_esp+1;
END IF;
select count(*) into v_cuenta from TABLADIC where INGLES=v_token;
IF (v_cuenta>0) then
v_eng:=v_eng+1;
END IF;
select count(*) into v_cuenta from TABLADIC where FRANCES=v_token;
IF (v_cuenta>0) then
v_france:=v_france+1;
END IF;
select count(*) into v_cuenta from TABLADIC where ZAPOTECO=v_token;
IF (v_cuenta>0) then
v_zapot:=v_zapot+1;
END IF;
select count(*) into v_cuenta from TABLADIC where CHINANTECO=v_token;
IF (v_cuenta>0) then
v_china:=v_china+1;
END IF;
END LOOP;
necesito optimizar este codigo ayuda
20+ Consejos para optimizar tus programas PHP | Dipler
11 de Febrero de 2010 a las 11:56 pm
[...] Emezeta, tufuncion, Google AKPC_IDS += "1240,"; Etiqueta(s): Optimización Categoría(s): Manuales, [...]