Este es un proyecto cancelado que no recibe actualizaciones. No obstante, puedes acceder a su archivo como referencia.

Versión Cero

¿Importa programar bien?

Sergio Montoro

Existen dos tipos de programadores especialmente peligrosos para un proyecto de software. Conócelos en este artículo.

por Sergio Montoro Ten, 20 junio 05

Hace un par de meses pusimos en marcha un website con un gestor de contenidos por detrás. Como el website tenía que estar online para ayer, escogimos uno de los populares gestores escritos en PHP. Al poco de tenerlo operativo nos dimos cuenta de que el gestor en cuestión lanzaba una media de 15 consultas contra la base de datos al servir cada página. Por suerte, nos habíamos anticipado a la situación encargando una cantidad desproporcionadamente grande de hardware para el tráfico estimado (a fin de cuentas el hardware es muy barato como solución de fuerza bruta). El cliente ni se ha enterado y anda feliz con su sitio web dinámico que le funciona tan ricamente.

Un par de años atrás, en cambio, no fuimos tan afortunados. Cometimos el error de encargar a un programador inexperto la traducción de unas páginas. El especialista en cuestión cogió todos los literales en castellano y los puso en una columna en base de datos y luego creó otra columna con los literales en inglés y se hizo una función Java llamada traducirLiteral(“pepe�) que se conectaba contra la base de datos, buscaba el literal el castellano con una consulta SQL y devolvía la cadena de texto en inglés. Para una página típica esto eran como 70 conexiones a base de datos por página. Como había un pool de conexiones y la tabla de literales era lo bastante pequeña para que la base de datos la cacheara en RAM, incluso esta implementación por fuerza bruta le hubiera salido bien; de no ser porque en vez de usar el driver JDBC apropiado, usó un puente JDBC-ODBC con un bug que le hacía perder 30 bytes de memoria en cada desconexión, lo cual, a la postre, acababa tumbando irremediablemente el servidor.

De las experiencias anteriores me surgió una pregunta profunda: ¿hasta qué punto importa programar bien? La experiencia me dice que para aplicaciones de andar por casa (que son la mayoría) el programador medio se las puede apañar razonablemente bien con un gestor de contenidos de calidad mediocre. Existen, empero, dos especimenes de terroristas del compilador especialmente peligrosos: el codificador descerebrado y el hombre abstracto.

El rasgo fundamental que caracteriza al codificador juntalineas es que no piensa. Escribe código como esos generadores verborreicos de poesía o notas de prensa que producen textos sintácticamente válidos pero sin ningún sentido.
El codificador juntalineas no puede escribir más de 100 líneas de código sin perderse. Su ámbito de alcance en el diseño abarca los que le cabe en la pantalla, 100 líneas más o menos. A partir de ahí se pierde y es incapaz de recordar lo que estaba haciendo.
El codificador juntalineas carece de ninguna consideración por el uso de recursos físicos de la máquina, lo mismo te carga en RAM una tabla hash de 1 millón de elementos que te manda 10 megas de datos en un post de HTTP.
Las pantallas del codificador juntalineas son un rompecabezas. Nunca se sabe dónde hay que pinchar, ni en qué orden.
No hay dos fragmentos de código del programador descerebrado que sean iguales, ni siquiera parecidos porque como no tiene memoria, no se acuerda de la nomenclatura que empleó ayer y reinventa una nueva cada mañana.

El hombre abstracto es el antagonista puro del codificador juntalineas. Se le reconoce porque sus programas tienen tantas clases de objetos como instancias y, además, las dos terceras partes de las clases son interfaces abstractos que no hacen realmente nada.
El hombre abstracto jamás empieza un programa con el compilador. Siempre tiene una herramienta de diseño en la que emplea horas y horas modelando antes de escribir ni una sola línea de código.
Si el codificador juntalineas su siente en su salsa con la chapuza diaria, el hombre abstracto detesta las reuniones con cliente porque cada nuevo requisito arruina la belleza del diseño y obliga a una refactorización de código. Uno debe armarse de paciencia para hacer ingeniería inversa del código del hombre abstracto. Es posible recorrer 8 ó 10 clases anidadas buscado donde está la funcionalidad que buscas, sólo para llegar después de una hora a un comentario que dice “pendiente de implementar�. El hombre abstracto a menudo es un subproducto típico de la formación académica realizada por maestros que nunca tuvieron experiencia real en un proyecto de uno o dos millones de líneas de código, y llenan de pájaros la cabeza de los estudiantes con la forma ortodoxa de hacer las cosas.
Puede ser gente que tenga algo visceral contra los depuradores o contra los modernos sistemas expertos que revisan el código y hacen sugerencias según lo escribes.
Si las pantallas del codificador juntalineas eran un invento para usuarios masoquistas, los programas del hombre abstracto directamente no tienen interfaz gráfico porque el sujeto no tuvo tiempo de implementar algo tan banal. El hombre abstracto no programa para solucionar problemas, escribe código para un concurso de pureza estilística.

Comentarios
1 Jose Ramón
20 junio 2005, 10:53

No sé en cual de los dos perfiles encaja más, pero para mi, son también peligrosos los que programan sin conocer realmente lo que hace por debajo su código.
Por tanto, escribe lineas, que aparentemente funcionan, pero nunca se da cuenta de por qué genera bugs, ni por qué salen efectos colaterales no deseados, ni como influye en el resto de la aplicación.
Podría no ser ninguno de los dos perfiles, o quizás sea una cualidad de ambos.
2 alidhaey
20 junio 2005, 12:31

Ambos casos son ejemplos de programadores que no saben realmente lo que debajo de su código. Uno escribe codigo chorizo y el otro está todo el tiempo creando envolturas.
3 Marcelo Ruiz
20 junio 2005, 15:34

Excelente artículo!!! Particularmente a mí me ha tocado trabajar con los dos tipos de programadores, y es un verdadero dolor de cabeza. Creo que le temo más al programador abstracto!!
4 Sergio Montoro Ten
20 junio 2005, 16:55

Coincido con alidhaey en que uno de los rasgos principales que diferencian un programador bueno de uno malo es la conciencia de los efectos secundarios que tendrá un determinado algoritmo: consumo de CPU, tráfico de red, cambios sibilinos en otros subsistemas, etc.
5 elmaska
20 junio 2005, 16:59

¿Que si es necesario programar bien?. Pues claro, como todo en esta vida. ¿O caso no es necesario comer bien, dormir bien, ser un buen profesional, o una buena persona?. Quizá, como dice Sergio, hay 2 tipos de programadores, pero también hay mas de 2. Por ejemplo, a mi se me ocurren los siguientes:
* El programador paranóico: aquél quien es incapaz de “soportar” un código que no haya hecho él – sin entrar a valorar la “pureza” de lo que él hace habitualmente -.
* El programador sistemista: El que lo soluciona todo basándose en el hardware.
* El programador “integrador”: El que antes de plantearse la necesidad o no desarrollar algo, utiliza lo primero que encuentra (si en en PHP y GPL – o similar – mejor).

Y así hasta un numero de elementos taxonómicos importante.

Por cierto, eso de que al darse cuenta de que el sw. es malo como queda oculto por el rendimiento de hw. el cliente está feliz y nosotros nos desentendemos. ¿No es necesario ser un buen profesional?.
El día que el cliente se de cuenta (y esperemos que no sea pronto) del pufo que le han colado ¿qué dirá?.
6 Raúl
20 junio 2005, 18:50

elmaska:
El día que el cliente se de cuenta (y esperemos que no sea pronto) del pufo que le han colado ¿qué dirá?.

Por la forma en que Sergio lo ha contado entiendo que el rendimiento de hw es tan superior que enmascara completamente la poca eficiencia del sw por lo que, a no ser que la carga del sistema crezca hasta niveles altísimos, el cliente no se verá afectado.

“Bueno. Rápido. Barato. Elige dos”. Parece que el cliente no escogió la primera ;)
7 ernesto
21 junio 2005, 04:11

Yo estoy a favor del programador abstracto, pero no por seres humanos que haya visto y con los que yo haya conversado; sino por obras de algunos que crearon productos completos, supergrandes, de millones de líneas y que, sin embargo, tienen una armonía perfecta entre su diseño y su implementación… por ejemplo, el JDK de Java o el Microsoft.NET Framework. ¿No creen ustedes que no han sido programadores abstractos los que han desarrollado semejantes marcos de aplicaciones? El asunto falla en que los programadores abstractos, a los que vemos cada día, que se sientan en el cubículo junto al nuestro, llevan sobre sus hombros la enseñanza mediocre de docentes mediocres, la poca experiencia y la falta de criterio común… cubrir con hardware deficiencias del software me parece un error que lo comete alguien que no sabe lo que funciona por debajo (igual que el juntalíneas)
8 nico
21 junio 2005, 06:50

Me parece que un programador abstracto de por sí no es peligroso. Peligroso es un programador abstracto sin límites.

Yo me considero un programador abstracto cuando la situación lo amerita, o sea, al principio de un proyecto, cuando se está definiendo la arquitectura. Una vez superada esa instancia, trato de ser el programador más práctico y eficiente del mundo.

Todo depende de la situación, y de la capacidad de liderazgo del líder de proyecto (valga la redundancia).

Prefiero intentar hacer las mejores encapsulaciones, árboles de clases, y código independiente, que responda a todas (o casi) las probabilidades de la mejor manera; que hacer todo lo más rápido posible (sin dejar de hacerlo bien), y llegado el caso de que haga falta algo especial, utilizar un trigger de BBDD, o una función que resuelve el caso especial, o romper las propias reglas definidas al principio porque este caso en particular lo justifica.
9 Raúl
21 junio 2005, 09:48

ernesto: Yo estoy a favor del programador abstracto…

Yo también admiro el diseño de algunos desarrollos pero, seamos sinceros, ¿trabajamos a diario en proyectos como el JDK o el .NET Framework? Creo que debemos valorar cada proyecto antes de comenzar su diseño, y dedicarle el tiempo que merece, ni más ni menos.

ernesto: cubrir con hardware deficiencias del software me parece un error que lo comete alguien que no sabe lo que funciona por debajo

Yo no creo que sea un error en todos los casos. Nuestra labor es resolver problemas ajustándonos a unos parámetros. En el caso que menciona Sergio parece que el software funciona correctamente, pero realiza demasiadas consultas a la base de datos.

Parece que Sergio evaluó dos opciones que consiguen el rendimiento que necesita su cliente:
a) Dedicar más tiempo a optimizar un software que posiblemente no volvamos a utilizar. Esto retrasa el proyecto y/o aumenta el coste de desarrollo: el precio aumenta en X.
b) Utilizar un hardware más potente: el precio aumenta en Y.

Si X > Y Sergio ha solucionado el problema de su cliente con un menor coste.
10 Raúl
21 junio 2005, 09:51

Ups, tras releer mi último comentario creo que puede malinterpretarse: sólo aclarar que nunca he trabajado con Sergio ;)
11 Sergio Montoro Ten
21 junio 2005, 10:54

Por especificar un poco más: un programa es, en mi opinión, demasiado abstracto cuando el ratio de clases abstractas e interfaces vs. clases finales es superior a 1:1.
Si para cada clase final tienes una clase abstracta, eso significa en la practica que puedes cambiar la implementación de todos tus métodos sin tocar los interfaces.

Las colecciones de java.util tienen más o menos un ratio 1:1.
Hay 4 interfaces: Collection, List, Set y SortedSet; 3 clases abstractas: AbstractCollection, AbstractList y AbstractSet; y 6 implementaciones: ArrayList, LinkedList, Vector, HashSet, LinkedHashSet y TreeSet.

Esto es una librería de propósito general. Para un programa de misión específica normalmente no compensa crear tantas subclases.

Aunque también existen contraejemplos, los interfaces de Sun para la especificación de portlets JSR-168 son un caso en el cual la librería es enteramente abstracta porque su propósito es justamente que cada programador implemente su propio código pero adiriéndose a unos interfaces determinados.

El comentario de Raúl da en la diana del concepto de que pensar cuesta tiempo, y el tiempo puede ser un recurso más valioso que el dinero según qué casos.
12 Juanjo Navarro
21 junio 2005, 11:05

Bueno, esto es un off-topic, pero con el ejemplo de java.util faltaría toda la parte de Map como interface y HashMap, TreeMap, etc, como implementaciones.

En general, por cada interface existen 3 o 4 implementaciones (unas centradas en velocidad de acceso, otras en velocidad de inserción, etc).

Por otro lado, es cierto que a veces una implementación rápida que resuelva el problema es mejor que una óptima pero que tarda el triple en ser implementada. Desde hace mucho se sabe que uno de los pecados de nuestra profesión es la optimización temprana: Optimizar un algoritmo para que tarde la mitad de tiempo en ejecutarse cuando dicho algoritmo solo ocupa el 0,05% del tiempo de ejecución.
13 Nacho
21 junio 2005, 16:51

Gran artículo, efectivamente, pero (creo que) en vez de servirnos para pensar que tal o cual persona encaja en un estereotipo debe ayudarnos a que nosotros no caigamos en ellos… Yo tengo que admitir que a veces sí me veo reflejado, y hay que mejorar.
14 martin
22 junio 2005, 00:07

A mi también me ha gustado el artículo. Quizas le he encontrado la pega que señalaba antes elmaska, y que es que hay muchas especies diferentes de terroristas del software, y no necesariamente los dos que ha mencionado Sergio son los más peligrosos.

¿Hasta que punto importa programar bien? No debe ser muy importante, si después de cada proyecto miramos para atrás y nos preguntamos diantres, pero como se me ocurrió implementar aquella funcionalidad de ese otro modo, que verguenza, si lo pudiese hacer de nuevo ahora cambiaría muchas cosas… :)

No, ahora en serio. Yo creo que siempre depende de lo que consideres como programar bien: ¿rendimiento?, ¿cantidad de bugs?, ¿consumo de hardware?, ¿tiempo de proceso?, ... ¿todo?,... Quizás, todo, ¿verdad?. Pero conseguir ese todo en la realidad de la empresa es algo muy difícil.

Entonces, quizás pueda ser que lo realmente importante sea primeramente no cometer chapuzas que nos puedan hacer perder el cliente, y a partir de ahí ya podríamos seguir. Además, otra regla de oro, básica, es satisfacer al cliente. Al cliente si le das esa funcionalidad que su viejo programa, de hace diez años, no tenía, pues estará tan contento aunque tu aplicación no sea la mejor del mundo, aunque hayas reutilizado otra herramienta, aunque consuma algo más de memoria de lo que debiera, etc. etc. La mayor parte de las veces, por cuestiones de tiempo, habrá que balancear todas esas medidas ideales. Quizás habrá que sacrificar un poco la arquitectura en pos de conseguir una solución rápidamente, o quizás habrá que centrarse en el rendimiento y descuidar la arquitectura, etc. etc.

Sergio expone esto en el artículo cuando habla de que hacía falta una solución que estuviese online para ayer. Ahí claramente tienes que buscar ante todo tiempo de respuesta, por encima de cualquier gusto sobre plataformas, arquitecturas, etc. En otros casos podría pasar lo contrario, quizás el cliente quisiera una solución de enorme rendimiento, seguridad y capacidades de personalización sobre la que basar sus futuros desarrollos internos, y entonces a lo mejor habría que descartar todas los paquetes prediseñados, y comenzar a crear un sistema propio ajustado a su negocio.

Resumiendo, que para mi, programar bien por supuesto que es muy importante, pero teniendo siempre en mente el ser muy pragmático.
15 elmaska
24 junio 2005, 14:07

Segun Raúl la solución de optar por cubrir las deficiencias sw. por la capacidad del hw. es perfectamente válida por motivos de eficacia (hacer las cosas correctamente); cosa por otro lado que nada tiene que ver con la eficiencia (hacer lo correcto).

Lo que es más discutible es plantear esa solución en un contexto como el articulo que nos ocupa. Vamos a ver, si yo escribiese un artículo acerca de la satisfacción del cliente como fin último no habría discusión alguna. El asunto es que el articulo va sobre ”¿Importa programar bien?”. Si se habla de “programar bien” (que por cierto como ya dije en el articulo al final no queda claro) se habla de programar bien (como quiera que se haga eso).

Además Raúl, no nos engañemos. Cuando un cliente contrata unos servicios espera (y esperamos todos) que se haya hecho el mejor esfuerzo por solucionar su problema, no la solución de compromiso. ¿Qué pasará si se decide ampliar la funcionalidad del sistema?. ¿Qué pasara cuando la carga del sistema aumente?. La única solución es: Profesionalidad.

No vale hacer crítica de salón y luego en el mundo real tirar por la calle de enmedio.

P.D.: “Enmascarar”: Cubrir con una máscara. Utensilios que por cierto suele ser utilizados por aquellos que quieren ocultar algo o quieren ocultarse de alguien. ¿No suena un poco negativo?. Yo no me sentiría cómodo diciendo que en mi trabajo “enmascaro” las cosas.
16 Raúl
24 junio 2005, 19:31

Además Raúl, no nos engañemos. Cuando un cliente contrata unos servicios espera (y esperamos todos) que se haya hecho el mejor esfuerzo por solucionar su problema, no la solución de compromiso.

Yo no me engaño: claro que un cliente quiere el mayor esfuerzo, pero en ocasiones no puede/quiere asumir el coste que conllevaría ese esfuerzo, o impone restricciones de tiempo muy estrictas (como en el caso que menciona Sergio).

En otras palabras, no siempre podemos dedicar los recursos necesarios para proporcionar la “solución ideal”. En esos casos tenemos que ofrecer opciones (ojo, advirtiendo de las limitaciones que conllevan!) que, sin ser ideales, solucionen lo mejor posible las necesidades del cliente.

¿Qué pasará si se decide ampliar la funcionalidad del sistema?. ¿Qué pasara cuando la carga del sistema aumente?. La única solución es: Profesionalidad.
Supongo que no estás afirmando que Sergio no es profesional ;) Personalmente no veo falta de profesionalidad si el cliente es consciente de las limitaciones. Volvemos a lo de antes: claro que preferiría que desarrolláramos un producto mejor, pero quizá no quiere asumir el coste (económico o temporal) que eso conlleva.

No vale hacer crítica de salón y luego en el mundo real tirar por la calle de enmedio.
Esto no sé a qué se refiere :-(

Enmascarar(...)¿No suena un poco negativo?
Joer, sí que hilas fino :-) Cambiaré el término: ¿qué tal “compensar”?
17 Alberto Molpeceres
30 junio 2005, 19:35

Tengo que reconocer que no he leído todos los comentarios (perdón por semejante falta de educación), por lo que a lo mejor soy repetitivo, pero volviendo al tema del artículo (importa programar bien?), no sé, a mi me parece que el gran problema de esta profesión está en la falsedad, más aún en lo malo o bueno que sean los programadores (que normalmente somos muy malos).

No me negareis que en este país y en esta profesión se ha mentido y se ha metido la pata tanto, a todos los niveles, que sinceramente, lo que menos me importa es si el programador es malo o muy malo.

Seguramente cada uno obtiene lo que paga (ya se ha dicho, aunque yo lo resumo: escoge entre bueno y barato, porque CASI nunca van juntos), y si alguién paga por mortadela (en producto, en empleados, etc.), que tenga claro que no le van a dar jamón de bellota. Pero eso no quita que si seguimos todos simulando ser o tener lo que ni somos ni tenemos, seguiremos viviendo una profesión de la que mejor sería desertar si supieramos cantar para ir a OT.

Simplemente mi opinión, tan buena y mala como cualquier otra.
18 J
3 agosto 2005, 21:00

Yo entiendo que ambas concepciones de “programador” estan directamente relacionadas con que hace la persona antes de implementar. El programador “juntalineas” no analiza nada. Se lanza a golpear el teclado hasta crear un codigo espagetti. Ese código posiblemente funcione, pero será extremadamente costoso de mantener. De este tipo de gente hay mucha; y me atrevo a decir que corresponde a personas sin experiència y/o que han caido en proyectos poco serios, y con fases de especificación y diseño deficientes o inexistentes.

El segundo arquetipo corresponde a gente que analiza el problema que le ocupa antes de implementar, pero por falta de experiencia y/o conocimientos su análisis es incompleto o, peor aún, erróneo.

De estos hay menos. Puestos a elegir prefiero al hombre abstracto, porque creo que el hombre abstracto de hoy puede ser el analista infalible de mañana.
El programador espagetti no tiene ningún futuro.

Es una visión del tema. Hay otras.

Saludos,
Jose Luis
Acerca - Contacto - Información legal y técnica - Condiciones de uso - Noticias sobre el mundo del Desarrollo de Software.