(Este artículo aparece en la revista IEEE Computer, marzo de 1998)
Resumen
Los lenguajes de scripting como Perl y Tcl representan un estilo de programación muy diferente al de los lenguajes de programación de sistemas como C o JavaTM. Los lenguajes de scripting están diseñados para "unir" aplicaciones; utilizan enfoques sin tipos para lograr un nivel más alto de programación y un desarrollo de aplicaciones más rápido que los lenguajes de programación de sistemas. Los aumentos en la velocidad de las computadoras y los cambios en la mezcla de aplicaciones están haciendo que los lenguajes de scripting sean cada vez más importantes para las aplicaciones del futuro.
Palabras clave: marcos de componentes, programación orientada a objetos, scripting, tipado fuerte, programación de sistemas.
Los lenguajes de scripting están diseñados para tareas diferentes a las de los lenguajes de programación de sistemas, y esto lleva a diferencias fundamentales en los lenguajes. Los lenguajes de programación de sistemas fueron diseñados para construir estructuras de datos y algoritmos desde cero, comenzando desde los elementos más primitivos de la computadora, como las palabras de memoria. En contraste, los lenguajes de scripting están diseñados para unir: asumen la existencia de un conjunto de componentes poderosos y están destinados principalmente a conectar componentes entre sí. Los lenguajes de programación de sistemas son fuertemente tipados para ayudar a manejar la complejidad, mientras que los lenguajes de scripting son sin tipos para simplificar las conexiones entre componentes y proporcionar un desarrollo rápido de aplicaciones.
Los lenguajes de scripting y los lenguajes de programación de sistemas son complementarios, y la mayoría de las plataformas informáticas importantes desde la década de 1960 han proporcionado ambos tipos de lenguajes. Los lenguajes se utilizan típicamente juntos en marcos de componentes, donde los componentes se crean con lenguajes de programación de sistemas y se unen con lenguajes de scripting. Sin embargo, varias tendencias recientes, como máquinas más rápidas, mejores lenguajes de scripting, la creciente importancia de las interfaces gráficas de usuario y las arquitecturas de componentes, y el crecimiento de Internet, han aumentado enormemente la aplicabilidad de los lenguajes de scripting. Estas tendencias continuarán durante la próxima década, con más y más aplicaciones nuevas escritas completamente en lenguajes de scripting y lenguajes de programación de sistemas utilizados principalmente para crear componentes.
A finales de la década de 1950 comenzaron a aparecer lenguajes de nivel superior como Lisp, Fortran y Algol. En estos lenguajes, las instrucciones ya no corresponden exactamente a las instrucciones de máquina; un compilador traduce cada instrucción en el programa fuente en una secuencia de instrucciones binarias. Con el tiempo, una serie de lenguajes de programación de sistemas evolucionaron a partir de Algol, incluyendo lenguajes como PL/1, Pascal, C, C++ y Java. Los lenguajes de programación de sistemas son menos eficientes que los lenguajes ensambladores, pero permiten que las aplicaciones se desarrollen mucho más rápidamente. Como resultado, casi han reemplazado por completo a los lenguajes ensambladores para el desarrollo de aplicaciones grandes.
Los lenguajes de programación de sistemas difieren de los lenguajes ensambladores en dos formas: son de nivel superior y están fuertemente tipados. El término "nivel superior" significa que muchos detalles se manejan automáticamente para que los programadores puedan escribir menos código para hacer el mismo trabajo. Por ejemplo:
while e if para estructuras de control; el compilador genera todas las instrucciones detalladas para implementar las estructuras de control.
La segunda diferencia entre el lenguaje ensamblador y los lenguajes de programación de sistemas es el tipado. Utilizo el término "tipado" para referirme al grado en que el significado de la información se especifica antes de su uso. En un lenguaje fuertemente tipado, el programador declara cómo se utilizará cada pieza de información y el lenguaje impide que la información se use de cualquier otra manera. En un lenguaje débilmente tipado no hay restricciones a priori sobre cómo se puede usar la información: el significado de la información se determina únicamente por la forma en que se usa, no por ninguna promesa inicial.1
Las computadoras modernas son fundamentalmente sin tipos: cualquier palabra en memoria puede contener cualquier tipo de valor, como un entero, un número de punto flotante, un puntero o una instrucción. El significado de un valor se determina por cómo se usa: si el contador de programa apunta a una palabra de memoria, entonces se trata como una instrucción; si una palabra es referenciada por una instrucción de suma de enteros, entonces se trata como un entero; y así sucesivamente. La misma palabra puede usarse de diferentes maneras en diferentes momentos.
En resumen, los lenguajes de programación de sistemas están diseñados para manejar las mismas tareas que los lenguajes ensambladores, es decir, crear aplicaciones desde cero. Los lenguajes de programación de sistemas son de nivel superior y mucho más fuertemente tipados que los lenguajes ensambladores. Esto permite que las aplicaciones se creen más rápidamente y se gestionen más fácilmente con solo una ligera pérdida de rendimiento. Vea Figura 1 para una comparación gráfica del lenguaje ensamblador y varios lenguajes de programación de sistemas.

3 Lenguajes de scripting
Los lenguajes de scripting como Perl[9], Python[4], Rexx[6], Tcl[8], Visual Basic y los shells de Unix representan un estilo de programación muy diferente al de los lenguajes de programación de sistemas. Los lenguajes de scripting asumen que ya existe una colección de componentes útiles escritos en otros lenguajes. Los lenguajes de scripting no están destinados a escribir aplicaciones desde cero; están destinados principalmente a conectar componentes. Por ejemplo, Tcl y Visual Basic se pueden usar para organizar colecciones de controles de interfaz de usuario en la pantalla, y los scripts de shell de Unix se utilizan para ensamblar programas de filtro en tuberías. Los lenguajes de scripting se utilizan a menudo para extender las características de los componentes, pero rara vez se utilizan para algoritmos complejos y estructuras de datos; características como estas suelen ser proporcionadas por los componentes. Los lenguajes de scripting a veces se denominan lenguajes de pegamento o lenguajes de integración de sistemas.
Para simplificar la tarea de conectar componentes, los lenguajes de scripting tienden a ser sin tipos: todas las cosas se ven y se comportan de la misma manera para que sean intercambiables. Por ejemplo, en Tcl o Visual Basic, una variable puede contener una cadena en un momento y un entero al siguiente. El código y los datos a menudo son intercambiables, de modo que un programa puede escribir otro programa y luego ejecutarlo sobre la marcha. Los lenguajes de scripting a menudo están orientados a cadenas, ya que esto proporciona una representación uniforme para muchas cosas diferentes.
select | grep scripting | wc
El programa select lee el texto que está actualmente seleccionado en la pantalla y lo imprime en su salida; el programa grep lee su entrada e imprime en su salida las líneas que contienen "scripting"; el programa wc cuenta el número de líneas en su entrada. Cada uno de estos programas puede usarse en numerosas otras situaciones para realizar diferentes tareas.button .b -text Hello! -font {Times 16} -command {puts hello}
Este comando crea un nuevo control de botón que muestra una cadena de texto en una fuente Times de 16 puntos e imprime un mensaje corto cuando el usuario hace clic en el control. Mezcla seis tipos diferentes de cosas en una sola instrucción: un nombre de comando (button), un control de botón (.b), nombres de propiedades (-text, -font y -command), cadenas simples (Hello! y hello), un nombre de fuente (Times 16) que incluye un nombre de tipo de letra (Times) y un tamaño en puntos (16), y un script Tcl (puts hello). Tcl representa todas estas cosas de manera uniforme con cadenas. En este ejemplo, las propiedades pueden especificarse en cualquier orden y las propiedades no especificadas reciben valores predeterminados; más de 20 propiedades quedaron sin especificar en el ejemplo.
CFont *fontPtr = new CFont();
Gran parte de este código es una consecuencia del tipado fuerte. Para establecer la fuente de un botón, debe invocarse su método
fontPtr->CreateFont(16, 0, 0,0,700, 0, 0, 0, ANSI_CHARSET,
OUT_DEFAULT_PRECIS,CLIP_DEFAULT_PRECIS, DEFAULT_QUALITY,
DEFAULT_PITCH|FF_DONTCARE, "Times New Roman");
buttonPtr->SetFont(fontPtr);
SetFont, pero este método debe recibir un puntero a un objeto CFont. Esto a su vez requiere que se declare e inicialice un nuevo objeto. Para inicializar el objeto CFont debe invocarse su método CreateFont, pero CreateFont tiene una interfaz rígida que requiere que se especifiquen 14 argumentos diferentes. En Tcl, las características esenciales de la fuente (tipo de letra Times, tamaño 16 puntos) pueden usarse inmediatamente sin declaraciones ni conversiones. Además, Tcl permite que el comportamiento del botón se incluya directamente en el comando que crea el botón, mientras que C++ y Java requieren que se coloque en un método declarado por separado.xyz. La diferencia es que los lenguajes de scripting realizan su verificación de errores en el último momento posible, cuando se usa un valor. El tipado fuerte permite que los errores se detecten en tiempo de compilación, por lo que se evita el costo de las verificaciones en tiempo de ejecución. Sin embargo, el precio a pagar por esta eficiencia son las restricciones sobre cómo se puede usar la información: esto resulta en más código y programas menos flexibles.
Debido a las características descritas anteriormente, los lenguajes de scripting permiten un desarrollo muy rápido para aplicaciones que están orientadas a la unión. Tabla 1 proporciona apoyo anecdótico para esta afirmación. Describe varias aplicaciones que se implementaron en un lenguaje de programación de sistemas y luego se reimplementaron en un lenguaje de scripting, o viceversa.

En resumen, los lenguajes de scripting están diseñados para unir aplicaciones. Proporcionan un nivel más alto de programación que los lenguajes ensambladores o de programación de sistemas, un tipado mucho más débil que los lenguajes de programación de sistemas y un entorno de desarrollo interpretado. Los lenguajes de scripting sacrifican la velocidad de ejecución para mejorar la velocidad de desarrollo.
4 Herramientas diferentes para tareas diferentes
Un lenguaje de scripting no es un reemplazo para un lenguaje de programación de sistemas o viceversa. Cada uno está adaptado a un conjunto diferente de tareas. Para unir e integrar sistemas, las aplicaciones pueden desarrollarse 5-10x más rápido con un lenguaje de scripting; los lenguajes de programación de sistemas requerirán grandes cantidades de código repetitivo y de conversión para conectar las piezas, mientras que esto puede hacerse directamente con un lenguaje de scripting. Para algoritmos complejos y estructuras de datos, el tipado fuerte de un lenguaje de programación de sistemas hace que los programas sean más fáciles de gestionar. Donde la velocidad de ejecución es clave, un lenguaje de programación de sistemas puede ejecutarse 10-20x más rápido que un lenguaje de scripting porque realiza menos verificaciones en tiempo de ejecución.
sh y csh para scripting. En el mundo de las PC de la década de 1990, se usaban C y C++ para la programación de sistemas y Visual Basic para scripting. En el mundo de Internet que se está formando ahora, se usa Java para la programación de sistemas y lenguajes como JavaScript, Perl y Tcl para scripting.El scripting y la programación de sistemas son simbióticos. Usados juntos, producen entornos de programación de poder excepcional: los lenguajes de programación de sistemas se utilizan para crear componentes emocionantes que luego pueden ensamblarse utilizando lenguajes de scripting. Por ejemplo, gran parte de la atracción de Visual Basic es que los programadores de sistemas pueden escribir componentes ActiveX en C y programadores menos sofisticados pueden luego usar los componentes en aplicaciones de Visual Basic. En Unix es fácil escribir scripts de shell que invoquen aplicaciones escritas en C. Una de las razones de la popularidad de Tcl es la capacidad de extender el lenguaje escribiendo código C que implemente nuevos comandos.
Las interfaces gráficas de usuario (GUIs) comenzaron a aparecer a principios de la década de 1980 y se generalizaron a finales de la década; las GUIs ahora representan la mitad o más del esfuerzo total en muchos proyectos de programación. Las GUIs son aplicaciones fundamentalmente de unión: el objetivo no es crear nueva funcionalidad, sino hacer conexiones entre una colección de controles gráficos y las funciones internas de la aplicación. No estoy al tanto de ningún entorno de desarrollo rápido para GUIs basado en un lenguaje de programación de sistemas. Ya sea que el entorno sea Windows, Macintosh Toolbox o Unix Motif, los kits de herramientas GUI basados en lenguajes como C o C++ han demostrado ser difíciles de aprender, torpes de usar e inflexibles en los resultados que producen. Algunos de estos sistemas tienen herramientas gráficas muy agradables para diseñar diseños de pantalla que ocultan el lenguaje subyacente, pero las cosas se vuelven difíciles tan pronto como el diseñador tiene que escribir código, por ejemplo, para proporcionar los comportamientos para los elementos de la interfaz. Todos los mejores entornos de desarrollo rápido de GUI están basados en lenguajes de scripting: Visual Basic, HyperCard y Tcl/Tk. Por lo tanto, los lenguajes de scripting han aumentado en popularidad a medida que ha aumentado la importancia de las GUIs.
El crecimiento de Internet también ha popularizado los lenguajes de scripting. Internet no es más que una herramienta de unión. No crea nuevos cálculos o datos; simplemente hace que una gran cantidad de cosas existentes sean fácilmente accesibles. El lenguaje ideal para la mayoría de las tareas de programación de Internet es uno que haga posible que todos los componentes conectados trabajen juntos, es decir, un lenguaje de scripting. Por ejemplo, Perl se ha vuelto popular para escribir scripts CGI y JavaScript es popular para scripting en páginas web.
El tercer ejemplo de aplicaciones orientadas al scripting son los marcos de componentes como ActiveX, OpenDoc y JavaBeans. Aunque los lenguajes de programación de sistemas funcionan bien para crear componentes, la tarea de ensamblar componentes en aplicaciones es más adecuada para el scripting. Sin un buen lenguaje de scripting para manipular los componentes, gran parte del poder de un marco de componentes se pierde. Esto puede explicar en parte por qué los marcos de componentes han tenido más éxito en las PC (donde Visual Basic proporciona una herramienta de scripting conveniente) que en otras plataformas como Unix/CORBA donde el scripting no está incluido en el marco de componentes.
Otra razón para la creciente popularidad de los lenguajes de scripting son las mejoras en la tecnología de scripting. Los lenguajes de scripting modernos como Tcl y Perl son muy diferentes de los primeros lenguajes de scripting como JCL. Por ejemplo, JCL ni siquiera proporcionaba iteración básica y los primeros shells de Unix no admitían procedimientos. La tecnología de scripting todavía es relativamente inmadura incluso hoy en día. Por ejemplo, Visual Basic no es realmente un lenguaje de scripting; fue implementado originalmente como un lenguaje de programación de sistemas simple, luego modificado para hacerlo más adecuado para scripting. Los futuros lenguajes de scripting serán aún mejores que los disponibles hoy en día.
La tecnología de scripting también se ha beneficiado de la velocidad cada vez mayor del hardware de las computadoras. Solía ser que la única manera de obtener un rendimiento aceptable en una aplicación de cualquier complejidad era usar un lenguaje de programación de sistemas. En algunos casos, incluso los lenguajes de programación de sistemas no eran lo suficientemente eficientes, por lo que las aplicaciones tenían que escribirse en ensamblador. Sin embargo, las máquinas de hoy son 100-500 veces más rápidas que las máquinas de 1980 y continúan duplicando su rendimiento cada 18 meses. Hoy en día, muchas aplicaciones pueden implementarse en un lenguaje interpretado y aún tener un rendimiento excelente; por ejemplo, un script Tcl puede manipular colecciones con varios miles de objetos y aún proporcionar una buena respuesta interactiva. A medida que las computadoras se vuelven más rápidas, el scripting se volverá atractivo para aplicaciones cada vez más grandes.
Una razón final para el uso creciente de los lenguajes de scripting es un cambio en la comunidad de programadores. Hace veinte años, la mayoría de los programadores eran programadores sofisticados que trabajaban en proyectos grandes. Los programadores de esa época esperaban pasar varios meses para dominar un lenguaje y su entorno de programación, y los lenguajes de programación de sistemas estaban diseñados para tales programadores. Sin embargo, desde la llegada de la computadora personal, más y más programadores ocasionales se han unido a la comunidad de programadores. Para estas personas, la programación no es su función principal de trabajo; es una herramienta que usan ocasionalmente para ayudar con su trabajo principal. Ejemplos de programación ocasional son consultas simples de bases de datos o macros para una hoja de cálculo. Los programadores ocasionales no están dispuestos a pasar meses aprendiendo un lenguaje de programación de sistemas, pero a menudo pueden aprender lo suficiente sobre un lenguaje de scripting en unas pocas horas para escribir programas útiles. Los lenguajes de scripting son más fáciles de aprender porque tienen una sintaxis más simple que los lenguajes de programación de sistemas y porque omiten características complejas como objetos e hilos. Por ejemplo, compare Visual Basic con Visual C++; pocos programadores ocasionales intentarían usar Visual C++, pero muchos han podido construir aplicaciones útiles con Visual Basic.
Incluso hoy en día, el número de aplicaciones escritas en lenguajes de scripting es mucho mayor que el número de aplicaciones escritas en lenguajes de programación de sistemas. En los sistemas Unix hay muchos más scripts de shell que programas en C, y bajo Windows hay muchos más programadores y aplicaciones de Visual Basic que de C o C++. Por supuesto, la mayoría de las aplicaciones más grandes y más utilizadas están escritas en lenguajes de programación de sistemas, por lo que una comparación basada en el total de líneas de código o el número de copias instaladas puede seguir favoreciendo a los lenguajes de programación de sistemas. No obstante, los lenguajes de scripting ya son una fuerza importante en el desarrollo de aplicaciones y su cuota de mercado aumentará en el futuro.
¿Cuánto beneficio ha proporcionado realmente la programación orientada a objetos? Desafortunadamente, no he visto suficientes datos cuantitativos para responder a esta pregunta de manera definitiva. En mi opinión, los objetos proporcionan solo un beneficio modesto: tal vez una mejora del 20-30% en la productividad, pero ciertamente no un factor de dos, y mucho menos un factor de 10. C++ ahora parece ser odiado tanto como amado, y algunos expertos en lenguajes están comenzando a hablar en contra de la programación orientada a objetos [2]. El resto de esta sección explica por qué los objetos no mejoran la productividad de manera dramática como lo hace el scripting, y argumenta que los beneficios de la programación orientada a objetos pueden lograrse en lenguajes de scripting.
La razón por la que la programación orientada a objetos no proporciona una gran mejora en la productividad es que no eleva el nivel de programación ni fomenta la reutilización. En un lenguaje orientado a objetos como C++, los programadores todavía trabajan con unidades básicas pequeñas que deben describirse y manipularse en gran detalle. En principio, podrían desarrollarse paquetes de librerías poderosos, y si estas librerías se usaran extensamente, podrían elevar el nivel de programación. Sin embargo, no han surgido muchas de estas librerías. El tipado fuerte de la mayoría de los lenguajes orientados a objetos fomenta paquetes estrechamente definidos que son difíciles de reutilizar. Cada paquete requiere objetos de un tipo específico; si dos paquetes deben trabajar juntos, debe escribirse código de conversión para traducir entre los tipos requeridos por los paquetes.
goto. Como resultado, los sistemas orientados a objetos a menudo sufren de complejidad y falta de reutilización.7 Otros lenguajes
Este artículo no está destinado a ser una caracterización completa de todos los lenguajes de programación. Hay muchos otros atributos de los lenguajes de programación además de la fuerza del tipado y el nivel de programación, y hay muchos lenguajes interesantes que no pueden caracterizarse limpiamente como un lenguaje de programación de sistemas o un lenguaje de scripting. Por ejemplo, la familia de lenguajes Lisp se encuentra en algún lugar entre el scripting y la programación de sistemas, con algunos de los atributos de cada uno. Lisp fue pionero en conceptos como la interpretación y el tipado dinámico que ahora son comunes en los lenguajes de scripting, así como la gestión automática de almacenamiento y los entornos de desarrollo integrados, que ahora se utilizan tanto en lenguajes de scripting como de programación de sistemas.8 Conclusión
Los lenguajes de scripting representan un conjunto diferente de compensaciones que los lenguajes de programación de sistemas. Renuncian a la velocidad de ejecución y la fuerza del tipado en comparación con los lenguajes de programación de sistemas, pero proporcionan una productividad de programador significativamente mayor y una reutilización de software. Esta compensación tiene más sentido a medida que las computadoras se vuelven más rápidas y baratas en comparación con los programadores. Los lenguajes de programación de sistemas son adecuados para construir componentes donde la complejidad está en las estructuras de datos y algoritmos, mientras que los lenguajes de scripting son adecuados para unir aplicaciones donde la complejidad está en las conexiones. Las tareas de unión se están volviendo cada vez más prevalentes, por lo que el scripting se convertirá en un paradigma de programación aún más importante en el próximo siglo de lo que es hoy.
[2] S. Johnson, Objecting To Objects, Invited Talk, USENIX Technical Conference, San Francisco, CA, enero de 1994.
[3] C. Jones, "Programming Languages Table, Release 8.2", marzo de 1996, http://www.spr.com/library/0langtbl.htm.
[4] M. Lutz, Programming Python, O'Reilly, ISBN 1-56592-197-6, 1996.
[5] Netscape Inc., "JavaScript in Navigator 3.0", http://home.netscape.com/eng/mozilla/3.0/handbook/javascript/atlas.html#taint_dg.
[6] R. O'Hara y D. Gomberg, Modern Programming Using REXX, Prentice Hall, ISBN 0-13-597329-5, 1988.
[7] J. Ousterhout, Additional Information for Scripting White Paper, http://www.ajubasolutions.com/people/john.ousterhout/scriptextra.html.
[8] J. Ousterhout, Tcl and the Tk Toolkit, Addison-Wesley, ISBN 0-201-63337-X, 1994.
[9] L. Wall, T. Christiansen, y R. Schwartz, Programming Perl, Segunda Edición, O'Reilly and Associates, ISBN 1-56592-149-6, 1996.
Sun y Java son marcas comerciales o marcas registradas de Sun Microsystems, Inc. en los Estados Unidos y otros países.
Tcl DeveloperXChange
Última actualización: 8 de agosto de 2000
Copiado de aquí. También vea scripting.pdf.