Unidad III Programación modular

 

 
 
 

 

 

3.1 Declaración de funciones  

3.2 Biblioteca de funciones

3.3 Entrada y salida

3.4 Archivo

3.5 Cadenas

3.6 Programación de Interfaces

3.6.1 Programación de puertos de la computadora

3.6.2 Escribiendo datos al puerto paralelo

3.6.3 Elaboración de interfaces

3.6.4 Control de interfaces a través de computadora

 3.7 Aplicación en la industria

 
 
 
 
 
 

Introducción

L

a programación modular es un paradigma de programación que consiste en dividir un programa en módulos o subprogramas con el fin de hacerlo más legible y manejable.

Se presenta históricamente como una evolución de la programación estructurada para solucionar problemas de programación más grandes y complejos de lo que ésta puede resolver.

Al aplicar la programación modular, un problema complejo debe ser dividido en varios subproblemas más simples, y estos a su vez en otros subproblemas más simples. Esto debe hacerse hasta obtener sus problemas lo suficientemente simples como para poder ser resueltos fácilmente con algún lenguaje de programación. Ésta técnica se llama refinamiento sucesivo, divide y vencerás ó análisis descendente (Top-Down).

Un módulo es cada una de las partes de un programa que resuelve uno de los su problemas en que se divide el problema complejo original. Cada uno de estos módulos tiene una tarea bien definida y algunos necesitan de otros para poder operar. En caso de que un módulo necesite de otro, puede comunicarse con éste mediante una interfaz de comunicación que también debe estar bien definida.

Uno de los problemas habituales del programador ocurre cuando los programas alcanzan un tamaño considerable en cuanto a línea de código. El problema se puede volver tan complejo que fuera inabordable. Para mitigar este problema apareció la programación modular.

En ella el programa se divide en módulos de tamaño manejable. Cada módulo realiza una función muy concreta y se pueden programar de forma independiente. Se basa en concentrar los esfuerzos en resolver problemas sencillos y una vez resueltos, el conjunto de esos problemas soluciona el problema original. En definitiva la programación modular implementa el paradigma divide y vencerás, tan importante en la programación. El programa se descompone en módulos. Los módulos se puede entender que son pequeños programas. Reciben datos y a partir de ellos realizan un cálculo o una determinada tarea. Una vez el módulo es probado y validado se puede utilizar las veces que haga falta en el programa sin necesidad de tener que volver a programar. En C los módulos se llaman funciones.

Si bien un módulo puede entenderse como una parte de un programa en cualquiera de sus formas y variados contextos, en la práctica se los suele tomar como sinónimos de procedimientos y funciones. Pero no necesaria ni estrictamente un módulo es una función o un procedimiento, ya que el mismo puede contener muchos de ellos, no debe confundirse el término "modulo" (en el sentido de programación modular) con términos como "función" o "procedimiento", propios del lenguaje que lo soporte.

Uno de los problemas habituales del programador ocurre cuando los programas alcanzan un tamaño considerable en cuanto a línea de código. El problema se puede volver tan complejo que fuera inabordable. Para mitigar este problema apareció la programación modular.

En ella el programa se divide en módulos de tamaño manejable. Cada módulo realiza una función muy concreta y se pueden programar de forma independiente. Se basa en concentrar los esfuerzos en resolver problemas sencillos y una vez resueltos, el conjunto de esos problemas soluciona el problema original. En definitiva la programación modular implementa el paradigma divide y vencerás, tan importante en la programación. El programa se descompone en módulos. Los módulos se puede entender que son pequeños programas. Reciben datos y a partir de ellos realizan un cálculo o una determinada tarea. Una vez el módulo es probado y validado se puede utilizar las veces que haga falta en el programa sin necesidad de tener que volver a programar. En C los módulos se llaman funciones.

Cada programa contiene un módulo denominado programa principal que controla todo lo que sucede; se transfiere el control a submodulos (posteriormente se denominarán subprogramas), de modo que ellos puedan ejecutar sus funciones; sin embargo, cada submodulo devuelve el control al módulo principal cuando se haya completado su tarea. Si la tarea asignada a cada submodulo es demasiado compleja, este deberá romperse en otros módulos más pequeños. El proceso sucesivo de subdivisión de módulos continua hasta que cada módulo tenga solamente una tarea específica que ejecutar. Esta tarea puede ser entrada, salida, manipulación de datos, control de otros módulos o alguna combinación de estos. Un módulo puede transferir temporalmente (bifurcación) el control a otro modulo; sin embargo, cada módulo debe devolver el control al módulo del cual se recibe originalmente el control.

Algunos lineamientos para la programación modular son:

1.  Mantener cada módulo de un tamaño manejable (de manera ideal incluyendo sólo una función).

2.  Prestar atención particular en las interfaces criticas (esto es, a los datos y a las variables de control que pasan entre los módulos).

3. Minimizar el número de módulos que el usuario necesite modificar cuando haga cambios.

4. Mantener las relaciones jerárquicas establecidas en las etapas de descenso.

 

Ejemplo:

Se desea diseñar un algoritmo que realice las siguientes tareas:

-Impresión de cabeceras de un informe,

-Lectura de datos,

-Ejecutar cálculos,

-Imprimir líneas detalladas de información,

-Imprimir totales.

Este programa se puede descomponer en módulos, de modo que exista un módulo principal o de control y diferentes submodulos.

Módulo principal:

·         Llamada a submódulo (impresión de cabeceras)

·         Llamada a submodulo (proceso de datos)

·         Llamada a submodulo (impresión de totales)

 

3.1 Declaración de funciones

 

L

os prototipos de las funciones que se utilizan en un programa se incluyen generalmente en la cabecera del programa y presentan la siguiente sintaxis:

En el prototipo de una función no se especifican las sentencias que forman parte de la misma, sino sus características. Por ejemplo:

En este caso se declara la función cubo que recibe como parámetro una variable de tipo entero (numero) y devuelve un valor del mismo tipo. En ningún momento estamos especificando qué se va a hacer con el variable número, sólo declaramos las características de la función cubo.

Cabe señalar que el nombre de los parámetros es opcional y se utiliza para mejorar la comprensión del código fuente. De esta manera, el prototipo de la función cubo podría expresarse de la siguiente manera:

Los prototipos de las funciones son utilizados por el compilador para verificar que se accede a la función de la manera adecuada con respecto al número y tipo de parámetros, y al tipo de valor de retorno de la misma. Veamos algunos ejemplos de prototipos de funciones:

Las funciones de biblioteca se declaran en lo que se conocen como ficheros de cabecera o ficheros .h (del inglés hederse, cabeceras). Cuando deseamos utilizar alguna de las funciones de biblioteca, debemos especificar el fichero .h en que se encuentra declarada la función, al inicio de nuestro programa. Por ejemplo, si deseamos utilizar la función pronto en nuestro programa, debemos incluir el fichero stdio.h que contiene el prototipo de esta función.

En el ejemplo adjunto podremos ver la declaración de una función ( prototipo ). Al no recibir ni retornar ningún valor, está declarada como void en ambos lados. También vemos que existe una variable global llamada  num. Esta variable es reconocible en todas las funciones del programa. Ya en la función  main encontramos una variable local llamada num. Al ser una variable local, ésta tendrá preferencia sobre la global. Por tanto la función escribirá los números 10 y 5. /* Declaración de funciones. */

           #include <stdio.h>

void funcion(void); /* prototipo */

int num=5; /* variable global */

main() /* Escribe dos números */

{

 int num=10; /* variable local */

 printf("%d\n",num);

 función(); /* llamada */

}

void funcion(void)

{

 printf("%d\n",num);

Por valor: cualquier cambio que se realice dentro de la función en el argumento enviado, NO afectará al valor original de las variables utilizadas en la llamada. Es como si trabajáramos con una  copia, no con el  original. No es posible enviar por valor  arrays, deberemos hacerlo por referencia.

Por referencia: lo que hacemos es enviar a la función la dirección de memoria donde se encuentra la variable o dato. Cualquier modificación SI afectará a las variables utilizadas en la llamada. Trabajamos directamente con el original. /* Paso por valor. */

Para enviar un valor por referencia se utiliza el símbolo  & ( ampersand ) delante de la variable enviada. Esto le indica al compilador que la función que se ejecutará tendrá que obtener la dirección de memoria en que se encuentra la variable.

Vamos a fijarnos en los ejemplos. En el ejemplo anterior podrás comprobar que antes y después de la llamada, las variables mantienen su valor. Solamente se modifica en la función intercambio (paso por valor ).

En el siguiente ejemplo podrás ver como las variables intercambian su valor tras la llamada de la función (paso por referencia).

Las variables con un  * son conocidas como  punteros, el único dato en 'C' que puede almacenar una dirección de memoria.

 

E

3.2 Biblioteca de funciones

 

l lenguaje C, C++ contiene numerosas funciones, cuando se emplean funciones de esta biblioteca estandar, se incrementa la transportabilidad de los programas.

Las funciones estandar se dividen en grupos, todas las funciones que pertenecen al mismo grupo estan declaradas en el archivo de cabecera (aquel que dice xxx.h), la letra "h" significa header en inglés y es lo que se llama cabecera.

C ofrece un conjunto de funciones estándar que dan soporte a las operaciones que se utilizan con más frecuencia. Estas funciones están agrupadas en bibliotecas. Para utilizar cualquiera de las funciones que forman parte de las bibliotecas estándar de C, sólo hace falta realizar una llamada a dicha función.

En ciencias de la computación, una biblioteca (del inglés library) es un conjunto de subprogramas utilizados para desarrollar software. Las bibliotecas contienen código y datos, que proporcionan servicios a programas independientes, es decir, pasan a formar parte de éstos. Esto permite que el código y los datos se compartan y puedan modificarse de forma modular. Algunos programas ejecutables pueden ser a la vez programas independientes y bibliotecas, pero la mayoría de éstas no son ejecutables. Ejecutables y bibliotecas hacen referencias (llamadas enlaces) entre sí a través de un proceso conocido como enlace, que por lo general es realizado por un software denominado enlazador.

Ejemplo de librería estándar. math

Math es el nombre de una librería que incorpora funciones matemáticas. Para poder utilizar dichas funciones hay que añadir la instrucción #include <math.h> al principio del código de nuestro archivo. Cada directiva include se coloca en una línea separada y no requiere punto y coma al ser una indicación al compilador y no una instrucción de verdad .Esta librería contiene las siguientes funciones (se indican los prototipos y uso);

Prototipo

Descripción

Int abs(int n)

Devuelve el valor absoluto del número entero indicado.

Int cell(double n)

Redondea el numero decimal n obteniendo el menor entero mayor o igual que n es decir cell(2.3)  devuelve el 3 y cell(2.7) y devuelve 3.

double cos(double n)

Obtiene el coseno de n(n se expresa en radianes).

double exp(double n)

Obtiene en.

double fabs(double n)

Obtiene el valor absoluto de n( siendo n un número double)

Int floor(double n)

Redondea el número decimal n obteniendo el mayor entero menor o igual que n. es decir floor(2.3) devuelve 2 y de floor(2.7) también devuelve 2.

 

Identificación y organización de archivos

En los sistemas informáticos modernos, los archivos siempre tienen nombres. Los archivos se ubican en directorios. El nombre de un archivo debe ser único en ese directorio. En otras palabras, no puede haber dos archivos con el mismo nombre en el mismo directorio.

El nombre de un archivo y la ruta al directorio del archivo lo identifica de manera unívoca entre todos los demás archivos del sistema informático -no puede haber dos archivos con el mismo nombre y ruta-. El aspecto del nombre depende del tipo de sistema informático que se use. Las primeras computadoras sólo permitían unas pocas letras o dígitos en el nombre de un archivo, pero las computadoras modernas permiten nombres largos que contengan casi cualquier combinación de letras unicode y dígitos unicode, haciendo más fácil entender el propósito de un archivo de un vistazo. Algunos sistemas informáticos permiten nombres de archivo que contengan espacios; otros no. La distinción entre mayúsculas y minúsculas en los nombres de archivo está determinada por el sistema de archivos. Los sistemas de archivos Unix distinguen normalmente entre mayúsculas y minúsculas, y permiten a las aplicaciones a nivel de usuario crear archivos cuyos nombres difieran solamente en si los caracteres están en mayúsculas o minúsculas. Microsoft Windows reconoce varios sistemas de archivos, cada uno con diferentes políticas en cuanto a la distinción entre mayúsculas y minúsculas. El popular antiguo sistema de archivos FAT puede tener varios archivos cuyos nombres difieran únicamente en las mayúsculas y minúsculas si el usuario utiliza un editor de discos para editar los nombres de archivo en las entradas de directorio. Las aplicaciones de usuario, sin embargo, normalmente no permitirán al usuario crear varios archivos con el mismo nombre pero con diferentes letras en mayúsculas y minúsculas.

 

3.3  Entrada y salida

Las funciones que forman parte de la biblioteca estándar de C, funciones estándar o predefinidas, están divididas en grupos. Todas las funciones que pertenecen a un mismo grupo se definen en el mismo fichero de cabecera. Los nombres de los ficheros cabeceras de C se muestran en la siguiente tabla:

Cuando deseamos utilizar cualquiera de las funciones estándar de C, primero debemos utilizar la directiva de precompilación #include para incluir los ficheros cabecera en nuestro programa. Por otra parte, antes de utilizar una función, primero debemos conocer las características de dicha función, es decir, el número y tipo de datos de sus argumentos y el tipo de valor que devuelve. Esta información es proporcionada por los prototipos de función.

Los grupos de funciones estándar más comunes son:

- entrada/salida estándar

- matemáticas

- de conversión

- diagnóstico

- de manipulación de memoria

- control de proceso

- ordenación

- directorios

- fecha y hora

- búsqueda

- manipulación de cadenas

- gráficos

- etcétera

Podemos incluir tantos ficheros de cabecera como nos haga falta, incluyendo los ficheros de cabecera que hemos creado y donde hemos definido nuestras funciones. En el resto de este apartado veremos algunas de las funciones de la entrada/salida estándar más utilizadas.

En C no existe ninguna palabra clave para realizar la entrada y salida de datos (E/S). Se realizan a través de funciones de biblioteca (concretamente, la biblioteca stdio.h, ver capítulo 13).

Las funciones principales que realizan la entrada y salida sin formato son:getchar(): Lee un carácter del teclado. Espera hasta que se pulsa una tecla y entonces devuelve su valor.

putchar(): Imprime un carácter en la pantalla en la posición actual del cursor.

gets(): Lee una cadena de caracteres introducida por el teclado y la sitúa en una dirección apuntada por su argumento de tipo puntero a carácter.

puts(): Escribe su argumento de tipo cadena en la pantalla seguida de un carácter de salto de línea.

El siguiente fragmento de código lee un carácter del teclado y lo muestra por pantalla. A continuación lee una cadena (de 10 caracteres incluido el carácter nulo) y también la muestra por pantalla:

#include <stdio.h>

main()

{

charcadena[10];

int i;

i=getchar();

putchar(i);

gets(cadena);

puts(cadena);

}

Las funciones principales que realizan la entrada y salida con formato, es decir, se pueden leer y escribir en distintas formas controladas, son:

printf(): Escribe datos en la consola con el formato especificado.

scanf(): Función de entrada por consola con el formato especificado.

Sus prototipos son los siguientes:

intprintf (" caracteres de transmisión y escape", lista de argumentos);

intscanf (" caracteres de transmisión y escape", lista de argumentos);

En la función printf() (con scanf() no), entre las comillas se pueden poner rótulos literales mezclados con los caracteres de transmisión.

Los caracteres de transmisión son precedidos de un % para distinguirlos de los normales:

Caracteres de transmisión Argumento que transmite

%c Int: un carácter simple

%NsChar *: una cadena de caracteres

%Nd %Ni Int: un número decimal

%o Int: octal sin signo

%x %X Int: hexadecimal sin signo

%NuInt: decimal sin signo

%N.DfFloat o double con D decimales, en notación fija

%N.De %N.DE Float o double con D decimales, en notación científica

%N.Dg %N.DG Float o double en notación científica si el exponente es menor de diez a la menos cuatro, o fija en caso contrario.

%p Void *: escribe el número que corresponde al puntero

%% Escribe un signo de %

Donde aparecen las letras N.D o no se pone nada o serán en realidad dos números que dicen que la transmisión total del valor al menos ocupará N posiciones (si el número necesita más de N las tomará, si usa menos las dejara en blancos, a menos que se quiera rellenar con ceros, entonces se pone 0N) y que la parte decimal tendrá como máximo las D posiciones después de un punto.

Normalmente el número se ajusta por la derecha para el campo de N posiciones que le hemos dicho que utilice; si deseamos el ajuste por la izquierda, se añade un signo menos precediendo al valor N (-N).

Una l precediendo a N (p.e. %l5d) significa que transmitiremos un longint : si, por el contrario, es una h significa que transmitiremos un short int.

Existe otro tipo de carácter especial, los caracteres de escape, que tienen un significado especial. Los caracteres de escape son los siguientes:

\n Nueva línea

\t Tabulador

\b Espacio atrás

\r Retorno de carro

\f Comienzo de página

\a Pitido sonoro

\¿ Comilla simple

\" Comilla doble

\\ Barra invertida

\xdd Código ASCII en notación hexadecimal (cada d representa un dígito)

\ddd Código ASCII en notación octal (cada d representa un dígito)

La lista de argumentos estará separada por comas. Debe existir una correspondencia biyectiva entre los caracteres de transmisión (aquellos que comienzan con un %) y la lista de argumentos a transmitir.

Cabe destacar una diferencia en la lista de argumentos entre las funciones printf() y  scanf(). En estáultima función (scanf()), la lista de argumentos va precedida por el operador de dirección(&), puesto que scanf() requiere que los argumentos sean las direcciones de las variables, en lugar de ellas mismas.

(&), puesto que scanf() requiere que los argumentos sean las  direcciones de las variables, en lugar de ellas mismas.

3.4 Archivo

En C un archivo puede ser cualquier cosa, desde un archivo de disco a un terminal o una impresora. Se asocia una secuencia con un archivo específico realizando una operación de apertura, una vez que está abierto, la información puede ser intercambiada entre éste y el programa. El puntero a un archivo es el hilo que unifica el sistema de E/S con buffer. Un puntero a un archivo es un puntero a una información que define varias cosas sobre él, incluyendo el nombre, el estado y la posición actual del archivo. En esencia, el puntero a un archivo identifica un archivo en disco específico y utiliza la secuencia asociada para dirigir el funcionamiento de las funciones de E/S con buffer. Para obtener una variable de tipo puntero a archivo se debe utilizar una sentencia como la siguiente:FILE *punt;

La función fopen() abre una secuencia para que pueda ser utilizada y le asocia a un archivo. Su prototipo es: FILE *fopen(constchar *nombre_archivo, constchar *modo); Donde nombre_archivo es un puntero a una cadena de caracteres que representan un nombre válido del archivo y puede incluir una especificación de directorio. La cadena que apunta modo determina cómo se abre el archivo. Los modos son los siguientes:

r: Abre un archivo de texto para lectura.

w: Crea un archivo de texto par escritura

a: Abre un archivo de texto para añadir

r+: Abre un archivo de texto para lectura/escritura

w+: Crea un archivo de texto para lectura/escritura

a+: Añade o crea un archivo de texto para lectura/escritura

La función fclose() cierra una secuencia que fue abierta mediante una llamada a fopen(). Escribe toda la información que todavía se encuentre en el buffer del disco y realiza un cierre formal del archivo a nivel del sistema operativo. También libera el bloque de control de archivo asociado con la secuencia, dejándolo libre para su reutilización. A veces es necesario cerrar algún archivo para poder abrir otro, debido a la existencia de un límite del sistema operativo en cuanto al número de archivos abiertos. Su prototipo es: intfclose(FILE *fp);

La función putc() escribe caracteres en un archivo que haya sido abierto previamente para operaciones de escritura, utilizando la función fopen(). Su prototipo es: intputc(int car, FILE *pf);

La función getc() escribe caracteres en un archivo que haya sido abierto, en modo lectura, mediante fopen(). Su prototipo es: intgetc(FILE *pf);La función fputs() escribe la cadena en la secuencia especificada. Su prototipo es: fputs() escribe la cadena en la secuencia especificada. Su prototipo es:  intfputs(constchar *cad, FILE *pf);La función fgets() lee una cadena de la secuencia especificada hasta que se lee un carácter de salto de línea o hasta que se han leído longitud-1 caracteres.

La función rewind() inicia el indicador de posición al principio del archivo indicado por su argumento. Su prototipo es: rewind() inicia el indicador de posición al principio del archivo indicado por su argumento. Su prototipo es: voidrewind(FILE *pf);

Existen otras muchas funciones en la biblioteca estándar de C (ver capítulo 13) como pueden serremove(): Borra el archivo especificado.

fflush(): Vacía el contenido de una secuencia de salida.

fread(): Lee tipos de datos que ocupan más de un byte. Permiten la lectura de bloques de cualquier tipo de datos.

fwrite(): Escribe tipos de datos que ocupan más de un byte. Permiten la escritura de bloques de cualquier tipo de datos.

fprintf(): Hace las funciones de printf() sobre un fichero.

fscanf(): Hace las funciones de scanf() sobre un fichero.

feof(): Detecta el final de un fichero.

ferror(): Detecta un error en la lectura/escritura de un fichero.

fclose() cierra una secuencia que fue abierta mediante una llamada a fopen().

putc() escribe caracteres en un archivo que haya sido abierto previamente para operaciones de escritura, utilizando la función fopen().

La función getc() escribe caracteres en un archivo que haya sido abierto, en modo lectura, mediante fopen(). Su prototipo es:

La función fputs() escribe la cadena en la secuencia especificada. Su prototipo es: intfputs(constchar *cad, FILE *pf);

La función fgets() lee una cadena de la secuencia especificada hasta que se lee un carácter de salto de línea o hasta que se han leído longitud-1 caracteres. Su prototipo es: fgets() lee una cadena de la secuencia especificada hasta que se lee un carácter de salto de línea o hasta que se han leído longitud-1 caracteres. Su prototipo es:intfgets(char *cad, FILE *pf); 
 

3.5 Cadenas

 

Manejo de cadenas <string.h>

Recordando la presentación de arreglos hecha (capítulo 5) en donde las cadenas están definidas como un arreglo de caracteres o un apuntador a una porción de memoria conteniendo caracteres ASCII. Una cadena en C es una secuencia de cero o más caracteres seguidas por un caracter NULL o \0:

 

Es importante preservar el caracter de terminación NULL, ya que con éste es como C define y maneja las longitudes de las cadenas. Todas las funciones de la biblioteca estándar de C lo requieren para una operación satisfactoria.

En general, aparte de algunas funciones restringidas en longitud (strncat(), strncmp() y strncpy()), al menos que se creen cadenas a mano, no se deberán encontrar problemas. Se deberán usar las funciones para manejo de cadenas y no tratar de manipular las cadenas en forma manual desmantelando y ensamblando cadenas.

 

Todas las funciones para manejo de cadenas tienen su prototipo en:

#include<string.h>

Las funciones más comunes son descritas a continuación:

  • char *strcpy(constchar *dest, constchar *orig) -- Copia la cadena de caracteres apuntada por orig (incluyendo el carácter terminador '\0') al vector apuntado por dest. Las cadenas no deben solaparse, y la de destino, debe ser suficientemente grande como para alojar la copia.
  • intstrcmp(constchar *s1, constchar *s2) -- Compara las dos cadenas de caracteres s1 y s2. Devuelve un entero menor, igual o mayor que cero si se encuentra que s1 es, respectivamente, menor que, igual a, o mayor que s2.
  • char *strerror(interrnum) -- Devuelve un mensaje de error que corresponde a un número de error.
  • intstrlen(constchar *s) -- Calcula la longitud de la cadena de caracteres.
  • char *strncat(char *s1, const char *s2, size_t n) -- Agregancaracteres de s2 a s1.
  • intstrncmp(constchar *s1, char *s2, size_t n) -- Compara los primeros n caracteres de dos cadenas.
  • char *strncpy(constchar *s1, constchar *s2, size_t n) -- Copia los primeros n caracteres de s2 a s1.
  • strcasecmp(constchar *s1, constchar *s2) -- versión que ignora si son mayúsculas o minúsculas de strcmp().
  • strncasecmp(constchar *s1, constchar *s2, size_t n) -- versión insensible a mayúsculas o minúsculas de strncmp() que compara los primeros n caracteres de s1.

El uso de muchas funciones es directo, por ejemplo:

char *s1 = "Hola";
char *s2;
intlongitud;
 
longitud = strlen("Hola");  /* long = 4 */
(void) strcpy(s2,s1);

Observar que tanto strcat() y strcopy() regresan una copia de su primer argumento, el cual es el arreglo destino. Observar también que orden de los argumentos es arreglo destino seguido por arreglo fuente lo cual a veces es una situación para hacerlo incorrectamente.

La función strcmp() compara lexicográficamente las dos cadenas y regresa:

  • Menor que cero -- si s1 es léxicamente menor que s2;
  • Cero -- si s1 y s2 son léxicamente iguales;
  • Mayor que cero -- si s1 es léxicamente mayor que s2;

Las funciones de copiado strncat(), strncmp() y strncpy() son versiones más restringidas que sus contrapartes más generales. Realizan una tarea similar, pero solamente para los primerosn caracteres. Observar que el caracter de terminación NULL podría ser violado cuando se usa estas funciones, por ejemplo:

char *s1 = "Hola";
char *s2 = 2;
intlongitud = 2;
 
(void) strncpy(s2, s1, longitud); /* s2 = "Ho" */donde s2 no tiene el terminador NULL. 
 

Es importante preservar el caracter de terminación NULL, ya que con éste es como C define y maneja las longitudes de las cadenas. Todas las funciones de la biblioteca estándar de C lo requieren para una operación satisfactoria.

En general, aparte de algunas funciones restringidas en longitud (strncat(), strncmp() y strncpy()), al menos que se creen cadenas a mano, no se deberán encontrar problemas. Se deberán usar las funciones para manejo de cadenas y no tratar de manipular las cadenas en forma manual desmantelando y ensamblando cadenas.

 

Todas las funciones para manejo de cadenas tienen su prototipo en:

#include<string.h>

Las funciones más comunes son descritas a continuación:

  • char *strcpy(constchar *dest, constchar *orig) -- Copia la cadena de caracteres apuntada por orig (incluyendo el carácter terminador '\0') al vector apuntado por dest. Las cadenas no deben solaparse, y la de destino, debe ser suficientemente grande como para alojar la copia.
  • intstrcmp(constchar *s1, constchar *s2) -- Compara las dos cadenas de caracteres s1 y s2. Devuelve un entero menor, igual o mayor que cero si se encuentra que s1 es, respectivamente, menor que, igual a, o mayor que s2.
  • char *strerror(interrnum) -- Devuelve un mensaje de error que corresponde a un número de error.
  • intstrlen(constchar *s) -- Calcula la longitud de la cadena de caracteres.
  • char *strncat(char *s1, const char *s2, size_t n) -- Agregancaracteres de s2 a s1.
  • intstrncmp(constchar *s1, char *s2, size_t n) -- Compara los primeros n caracteres de dos cadenas.
  • char *strncpy(constchar *s1, constchar *s2, size_t n) -- Copia los primeros n caracteres de s2 a s1.
  • strcasecmp(constchar *s1, constchar *s2) -- versión que ignora si son mayúsculas o minúsculas de strcmp().
  • strncasecmp(constchar *s1, constchar *s2, size_t n) -- versión insensible a mayúsculas o minúsculas de strncmp() que compara los primeros n caracteres de s1.

El uso de muchas funciones es directo, por ejemplo:

char *s1 = "Hola";
char *s2;
intlongitud;
 
longitud = strlen("Hola");  /* long = 4 */
(void) strcpy(s2,s1);

Observar que tanto strcat() y strcopy() regresan una copia de su primer argumento, el cual es el arreglo destino. Observar también que orden de los argumentos es arreglo destino seguido por arreglo fuente lo cual a veces es una situación para hacerlo incorrectamente.

La función strcmp() compara lexicográficamente las dos cadenas y regresa:

  • Menor que cero -- si s1 es léxicamente menor que s2;
  • Cero -- si s1 y s2 son léxicamente iguales;
  • Mayor que cero -- si s1 es léxicamente mayor que s2;

Las funciones de copiado strncat(), strncmp() y strncpy() son versiones más restringidas que sus contrapartes más generales. Realizan una tarea similar, pero solamente para los primerosn caracteres. Observar que el caracter de terminación NULL podría ser violado cuando se usa estas funciones, por ejemplo:

char *s1 = "Hola";
char *s2 = 2;
intlongitud = 2;
 
(void) strncpy(s2, s1, longitud); /* s2 = "Ho" */donde s2 no tiene el terminador NULL. 

 

 

 3.6 programaion de interfaces

U

na interfaz de programación representa la capacidad de comunicación entre componentes de software. Se trata del conjunto de llamadas a ciertas bibliotecas que ofrecen acceso a ciertos servicios desde los procesos y representa un método para conseguir abstracción en la programación, generalmente (aunque no necesariamente) entre los niveles o capas inferiores y los superiores del software. Uno de los principales propósitos de una API consiste en proporcionar un conjunto de funciones de uso general, por ejemplo, para dibujar ventanas o iconos en la pantalla. De esta forma, los programadores se benefician de las ventajas de la API haciendo uso de su funcionalidad, evitándose el trabajo de programar todo desde el principio. Las APIs asimismo son abstractas: el software que proporciona una cierta API generalmente es llamado la implementación de esa API.

Los puertos de comunicación de la PC son de particular interés para el estudioso de la electrónica ya que le permiten utilizar una computadora personal para controlar todo tipo circuitos electrónicos utilizados, principalmente, en actividades de automatización de procesos, adquisición de datos, tareas repetitivas y otras actividades que demandan precisión. Éste artículo es el primero de una serie que analizará diversos usos para el puerto paralelo de la PC.


Existen dos métodos básicos para transmisión de datos en las computadoras modernas. En un esquema de transmisión de datos en serie un dispositivo envía datos a otro a razón de un bit a la vez a través de un cable. Por otro lado, en un esquema de transmisión de datos en paralelo un dispositivo envía datos a otro a una tasa de n número de bits a través de n número de cables a un tiempo. Sería fácil pensar que un sistema en paralelo es n veces más rápido que un sistema enserie, sin embargo esto no se cumple, básicamente el impedimento principal es el tipo de cable que se utiliza para interconectar los equipos.

Por ejemplo, se puede ver la tarea de escribir "Hola Mundo" sobre la pantalla en diferentes niveles de abstracción:

  1. Haciendo todo el trabajo desde el principio:
    1. Traza, sobre papel milimetrado, la forma de las letras (y espacio) "H,o, l, a,M,u, n, d, o".
    2. Crea una matriz de cuadrados negros y blancos que se asemeje a la sucesión de letras.
    3. Mediante instrucciones en ensamblador, escribe la información de la matriz en la memoria intermedia ("buffer") de pantalla.
    4. Mediante la instrucción adecuada, haz que la tarjeta gráfica realice el volcado de esa información sobre la pantalla.
  2. Por medio de un sistema operativo para hacer parte del trabajo:
    1. Carga una fuente tipográfica proporcionada por el sistema operativo.
    2. Haz que el sistema operativo borre la pantalla.
    3. Haz que el sistema operativo dibuje el texto "Hola Mundo" usando la fuente cargada.
  3. Usando una aplicación (que a su vez usa el sistema operativo) para realizar la mayor parte del trabajo:
    1. Escribe un documento HTML con las palabras "Hola Mundo" para que un navegador Web como Google Chrome, Mozilla, Firefox, Opera o Internet Explorer pueda representarlo en el monitor.

Como se puede ver, la primera opción requiere más pasos, cada uno de los cuales es mucho más complicado que los pasos de las opciones siguientes. Además, no resulta nada práctico usar el primer planteamiento para representar una gran cantidad de información, como un artículo enciclopédico sobre la pantalla, mientras que el segundo enfoque simplifica la tarea eliminando un paso y haciendo el resto más sencillos y la tercera forma simplemente requiere escribir "Hola Mundo". Sin embargo, las APIs de alto nivel generalmente pierden flexibilidad; por ejemplo, resulta mucho más difícil en un navegador web hacer girar texto alrededor de un punto con un contorno parpadeante que programarlo a bajo nivel. Al elegir usar una API se debe llegar a un cierto equilibrio entre su potencia, simplicidad y pérdida de flexibilidad.

 

3.6.1 Programación de puertos de la computadora

 

Un puerto en la computadora es por donde la información fluye hacia dentro o hacia fuera. Los dispositivos Hardware como la impresora o modem pueden ser llamados puertos, un puerto que manda información fuera de tu computadora puede ser el monitor o la impresora. Un puerto que recibe información seria el modem o un scanner.

El puerto paralelo del PC es un conjunto de dispositivos (conector, circuitos electrónicos, etc.) que permite la conexión de un equipo informático con el propósito de intercambiar información digital.

 

Desde el punto de vista del software, el puerto paralelo son tres registros de 8 bits cada uno, ocupando tres direcciones de I/O consecutivas de la arquitectura x86.

Desde el punto de vista hardware, el puerto es un conector hembra DB25 con doce salidas y cinco entradas, con 8 líneas de masa.

La función normal es transferir datos a una impresora a través de las 8 líneas de datos, usando las señales restantes como control de flujo.

Los puertos de comunicación de la PC son de particular interés para el estudioso de la electrónica ya que le permiten utilizar una computadora personal para controlar todo tipo circuitos electrónicos utilizados, principalmente, en actividades de automatización de procesos, adquisición de datos, tareas repetitivas y otras actividades que demandan precisión.

Existen dos métodos básicos para transmisión de datos en las computadoras modernas. En un esquema de transmisión de datos en serie un dispositivo envía datos a otro a razón de un bit a la vez a través de un cable. Por otro lado, en un esquema de transmisión de datos en paralelo un dispositivo envía datos a otro a una tasa den número de bits a través deun número de cables a un tiempo. Sería fácil pensar que un sistema en paralelo es n veces más rápido que un sistema en serie, sin embargo esto no se cumple, básicamente el impedimento principal es el tipo de cable que se utiliza para interconectar los equipos. Si bien un sistema de comunicación en paralelo puede utilizar cualquier número de cables para transmitir datos, la mayoría de los sistemas paralelos utilizan ocho líneas de datos para transmitir un byte a la vez, como en todo, existen excepciones, por ejemplo el estándar SCSI permite transferencia de datos en esquemas que van desde los ocho bits y hasta los treinta y dos bits en paralelo. En éste artículo nos concentraremos en transferencias de ocho bits ya que ésta es la configuración del puerto paralelo de una PC.

Un típico sistema de comunicación en paralelo puede ser de una   dirección (unidireccional) o de dos direcciones (bidireccional). El más simple mecanismo utilizado en un puerto paralelo de una PC es de tipo unidireccional y es el que analizaremos en primer lugar. Distinguimos dos elementos: la parte transmisora y la parte receptora.

La parte transmisora coloca la información en las líneas de datos e informa a la parte receptora que la información (los datos)  están disponibles; entonces la parte receptora lee la información en las líneas de datos e informa a la parte transmisora que ha tomado la información (los datos). Observe que ambas partes sincronizan su respectivo acceso a las líneas de datos, la parte receptora no leer á las líneas de datos hasta que la parte transmisora se lo indique en tanto que la parte transmisora no colocará nueva información en las líneas de datos hasta quela parte receptora remueva la información y le indique a la parte transmisora que ya ha tomado los datos, a ésta coordinación de operaciones se le llama acuerdo ó entendimiento. Bien, en estos ámbitos tecnológicos es recomendable utilizar ciertas palabras en inglés que nos permiten irónicamente un mejor entendimiento de los conceptos tratados. Repito: a la coordinación de operaciones entre la parte transmisora y la parte receptora se le llama handshaking, que en español es elacto con el cual dos partes manifiestan estar de acuerdo, es decir, se dan un apretón de manos.

 

Se dividen en 2 tipos:

 

a) Puertos físicos de la computadora: son conectores integrados en tarjetas de expansión ó en la tarjeta principal "Motherboard" de la computadora; diseñados con formas y características electrónicas especiales, utilizados para interconectar una gran gama de dispositivos externos con la computadora, es decir, los periféricos. Usualmente el conector hembra estará montado en la computadora y el conector macho estará integrado en los dispositivos ó cables. Varía la velocidad de transmisión de datos y la forma física del puerto acorde al estándar y al momento tecnológico.

 Anteriormente los puertos venían integrados exclusivamente en tarjetas de expansión denominadas tarjetas controladoras, posteriormente se integraron en la tarjeta principal "Motherboard" y tales controladoras perdieron competencia en el mercado, pero actualmente se siguen comercializando sobre todo para servidores.

b) Puertos lógicos de la computadora: son puntos de acceso entre equipos para el uso de servicios y flujo de datos entre ellos, ejemplos el puerto 21 correspondiente al servicio FTP (permite el intercambio de archivos) ó el puerto  515 que está asociado con el servicio de impresión.

C

on ocho bits podemos escribir en el puerto un total de 256 valores diferentes, cada uno de éstos representa un byte de información y cada byte puede representar una acción concreta que nosotros podemos definir de acuerdo a nuestras necesidades. En éste artículo el objetivo es entender cómo trabajar con el puerto paralelo, por lo tanto hagamos un programa que nos permita escribir un número cualquiera entre 0 y 255 de tal manera que sea posible visualizar el valoren formato binario. En primer lugar consulte la documentación de su compilador para verificar la correcta sintaxis de la función que nos sirve para escribir en el puerto, en el caso específico de Symantec C++, dicha función eoutp( ). Ésta función requiere dos parámetros, el primero de tipo unsignedint que especifica la dirección del puerto paralelo, y el segundo de tipo char que especifica el valor a escribir en las líneas de datos de puerto. Una típica llamada a la función outp( ) se parece a esto:

 

 

 

Se aprecia la facilidad de manejo de la función, aunque diferentes compiladores dan a sus respectivas funciones nombres diferentes, la mecánica es la misma, se requieren dos parámetros, la dirección del puerto y el valor a escribir en el puerto. Estudie el siguiente código:

 

/**********************************************************

*puerto2.c

*

*Escribe datos al puerto paralelo de la PC

*

**********************************************************/

#include <stdio.h>

#include <dos.h>

intpuerto(intdirecc);

intseleccion;

int main()

{
unsignedint __far *puntero_a_direccion;
int i, direccion[3]={0,0,0}, disponible[3]={0,0,0};

 

 

puntero_a_direccion = (unsignedint __far *)0x00000408;

printf("Seleccione el puerto:\n");
/* ¿Cuantos puertos existen?
*/
for (i=0; i<3; i++)

{
if (*puntero_a_direccion == 0)
printf("Puerto LPT%d...............no disponible\n", i+1);
else
{

disponible[i] = 1;
direccion[i] = *puntero_a_direccion;
printf("Puerto LPT%d...............%d\n", i+1, i+1);

}puntero_a_direccion++;
}printf("Salir del programa........0\n");
scanf("%d", &seleccion);
do

{

switch(seleccion)

{
case 0:/* Salir del programa */
printf("Adios!!!\n");
return 0;
break;

case 1:/* Puerto LPT1 */
if(disponible[0]==1)
puerto(direccion[0]);
else
{

printf("ERROR: PUERTO NO DISPONIBLE\n");

return 0;

}break;

case 2:/* Puerto LPT2 */
if(disponible[1]==1)
puerto(direccion[1]);
else
{

printf("ERROR: PUERTO NO DISPONIBLE\n");

return 0;

}break;

case 3:/* Puerto LPT3 */
if(disponible[2]==1)
puerto(direccion[2]);
else
{

printf("ERROR: PUERTO NO DISPONIBLE\n");

return 0;

}

 

 

break;

default:
printf("ERROR: OPCION INCORRECTA!\n");
break;

}if(seleccion!=0)

{
printf("Seleccione otra opcion\n");
scanf("%d", &seleccion);

}

}while(seleccion!=0);

return 0;

}intpuerto(intdirecc)

{

unsignedchar valor; /* Solo valores entre 0 y 255 */

printf("Ahora puede escribir cualquier valor\n");
printf("entre 1 y 255, 0 para terminar el programa\n");
do

{
printf("Valor al puerto?\n");
scanf("%d", &valor);
outp(direcc, valor);
printf("Se ha escrito %d al puerto\n", valor);

}while(valor!=0);

returnseleccion=0;

}

 

 

 

 

El programa determina el número de puertos paralelo instalados en la

Computadora y almacena sus respectivas direcciones en el arreglo llamado dirección, en caso de encontrarse una dirección válida además se establece en

1 el valor del arreglo llamado disponible[i] simplemente como una medida de seguridad adicional. Como resultado de estas acciones el programa despliega un menú basado en los puertos encontrados, en este punto Usted puede seleccionar, en caso de que disponga de más de un puerto, el puerto en donde está conectado el circuito mostrado en el diagrama de arriba.

 

Una vez seleccionado el puerto Usted puede escribir un valor cualquiera comprendido entre 0 y 255. Independientemente del puerto seleccionado toda la funcionalidad del programa está encapsulada en la función de tipo int llamada puerto( ) a la cual se le pasa un único parámetro que es la dirección del puerto seleccionado. La función está codificada de tal forma que al escribir un 0 el programa termina, de ésta manera al cerrar el programa las líneas de datos del puerto paralelo están todas en un nivel lógico bajo. Éste programa y el circuito asociado son útiles para entender de forma visual la forma de representar valores en formato binario, además establece las bases de trabajo para otros proyectos de control basados en computadora.

3.6.3 Elaboración de interfaces

 

El diseño de interfaz de usuario o ingeniería de la interfaz es el diseño de computadoras, aplicaciones, máquinas, dispositivos de comunicación móvil, aplicaciones de software, y sitios web enfocado en la experiencia de usuario y la interacción.

Normalmente es una actividad multidisciplinar que involucra a varias ramas del diseño y el conocimiento como el diseño gráfico, industrial, web, de software y la ergonomía; y está implicado en un amplio rango de proyectos, desde sistemas para computadoras, vehículos hasta aviones comerciales.

Su objetivo es que las aplicaciones o los objetos sean más atractivos y además, hacer que la interacción con el usuario sea lo más intuitiva posible, conocido como el diseño centrado en el usuario. En este sentido las disciplinas del diseño industrial y gráfico se encargan de que la actividad a desarrollar se comunique y aprenda lo más rápidamente, a través de recursos como la gráfica, los pictogramas, los estereotipos y la simbología, todo sin afectar el funcionamiento técnico eficiente.

Tipos de Interfaces

El interface es de dos tipos que ellos son:

Interface Paralelo

Un interface paralelo transfiere datos en la forma de uno o varios bytes en la paralela a o del dispositivo.

Asuma un ordenador 16 bites, direccionable por el byte, donde la entrada - salida controlada del programa es usada con asincrónico del ducto, y el cronometraje de transferencias de ducto es unos. El interface contiene memorias intermedias de datos separadas para insumo y producción y hay un registro de estado asociado con cada memoria intermedia. Para una operación de insumo, y la palabra de datos es transferida del dispositivo de producción a registros y puesta a 1. Cuando tan pronto como la señal lista es recibida, esto habilita las puertas de producción correspondiente al byte dirigido o palabra y colocación de sus contenido en las líneas de datos. También, la señal de producción aceptan también es puesto a 1. Este constituye la respuesta del interface a la petición leída emitida por la unidad central de proceso. Tan pronto como la señal lista se cae a 0, la señal aceptaré es borrada y todo el ducto es borrado. Note que cuando la memoria intermedia es dirigida, la bandera de estado de insumo es reinicializada a 0. Este es esencial a fin de garantizar que cada artículo de datos de insumo es leído por el ordenador sólo una vez. Una operación de producción procede del mismo modo, cuando la señal habilitaré es puesta a 1. El insumo de reloj a la memoria intermedia de producción es puesto. Este resulta en la carga de la memoria intermedia con los datos en las líneas de datos. Al mismo tiempo, es puesto a 1 indicar que el interface está listo a aceptar una nueva transferencia de producción.

Interface Consecutivo

Un interface consecutivo contiene el mismo recorrido de control y dirección que el interface paralelo, pero con una adición controla para transferir datos en serie entre registros y el dispositivo de entrada - salida. Aquí, un chip es usado, que es un barco de circuito integrado que contiene todo el recorrido lógico para la conversión paralela y consecutiva requerida. Los dos registros y las banderas de estado son incluidos en el chip.

3.6.4 Control de interfaces a través de computadora

 

En aplicaciones de control que requieren que el procesamiento de la información se realice en una computadora personal (PC) la velocidad de transferencia de datos desde y hacia la computadora puede ser un factor limitante. Para superar esta limitación se propone utilizar el bus USB como interface. En este articulo se muestra un ejemplo aplicado al control de un brazo robot y como el cambio a una interface USB permite mejorar la tasa de transferencia de datos entre la computadora y el sistema de control del brazo robot.

 

Instrumentación basada en PC es fácil de implementar el uso de herramientas y tarjetas de National Instruments - Prueba y Medida. La mayoría de los instrumentos se pueden comunicar con el PC en la interfaz GPIB .

Puede empezar por aprender a usar el puerto paralelo y puerto serie.
MIDI-puerto de juegos también tiene lo suficiente para ayudarle a comenzar, aprender interfaces informáticas en el hogar.
Intente un pequeño experimento fácil de
RS-232 del sensor de temperatura Powered. Esto puede empezar también.
Los pocos ejemplos de arriba muestran una instrumentación - Analizador Lógico 'Like' de interfaz y un circuito de control del relé de visualización. Son ejemplos he intentado por los estudiantes a probar y aprender.

 

Elaborar una interfaz:

Como consecuencia del uso masivo de internet y de la gran cantidad de documentación disponible para desarrolladores, es posible encontrar en la actualidad una gran variedad de productos de software. El problema está en que gran parte de esas aplicaciones no cumple con el objetivo principal para el cual debieron ser diseñadas, que es facilitar la vida de sus usuarios, razón por la que muchas veces son descartadas y reemplazadas por otras aplicaciones. En la mayor parte de los casos esto no se debe a errores de codificación, sino más bien a la forma en que las diferentes funcionalidades del software son presentadas a su público, lo que de ahora en adelante conoceremos como "interfaz de usuario". Este elemento, considerado una métrica de la calidad de un software, influye directamente en la percepción final del producto y en la resistencia del usuario a probar la aplicación. ¡Un software podrá ser muy bueno y poderoso, pero no será popular si su interfaz es deficiente! Por eso, basado en mi experiencia como desarrollador y en diversas lecturas sobre el tema, compartiré los elementos que considero más importantes al momento de desarrollar una buena interfaz de usuario.

3.7 Aplicación en la industria

La interfaz de usuario más popular consiste en la representación gráfica de  programas como iconos seleccionados a través del ratón que se ejecutan en ventanas desplegadas en la pantalla de la computadora. Los comandos y opciones de los programas pueden ser seleccionados a través de menús dispuestos en 2seccionesespecíficas de las ventanas. Esta interfaz, conocida comúnmente como WIMP (Windowsicons-mouse-pointer), ha sido sumamente exitosa por más de 20 años, un período sorprendentemente largo cuando se habla de TICs.

Canny (2006) considera que la longevidad de las interfaces WIMP se debe, entre

otros, a dos factores principales. En primer lugar, esta abstracción permitió que la

Computadora pudiera ser utilizada prácticamente por cualquier persona sin tener que ser experta en computación; se trata de una interfaz centrada en el usuario. En segundo lugar, ha resultado muy apropiada al considerar la computadora como una herramienta de trabajo para las funciones convencionales en la oficina, la escuela y el hogar.

 

Sin embargo, este modelo de Interacción Humano-Computadora (IHC) presenta

Severas limitaciones ante los nuevos escenarios que las TICs van englobando durante su acelerado proceso de transformación social. Un estudio reciente realizado por la División de Ciencias de la Computación de la Universidad de California en Berkeley consideró que la prioridad número uno en investigación y desarrollo debería concentrarse en IHC(Canny, 2006).

 

Algunos de estos escenarios son el objeto de estudio del presente

Documento, entre los que cabe destacar los siguientes:

 

Si bien las interfaces WIMP han permitido la adopción generalizada de las

Computadoras, la facilidad de uso sigue considerándose la principal barrera para el

Crecimiento y éxito de las TIC en las organizaciones (Canny, 2006).

 Hace tiempo que la computadora ha dejado de ser tan sólo herramienta de trabajo en la oficina y el hogar. Las consolas de videojuegos, los reproductores de DVD, los nuevos televisores, un número creciente de sistemas de control en el automóvil y el hogar, son tan sólo algunos ejemplos de equipos computacionales con los que el hombre contemporáneo interactúa todos los días. En estos dispositivos resulta crítica.

Diseño minimalista: entre más elementos existan en la pantalla, más confundido y temeroso se encontrará el usuario. Por eso es importante reducir al máximo el número de componentes visibles, siendo muchas veces recomendada la utilización de asistentes o "wizards", los cuales permiten dividir una gran pantalla de datos en una serie de pasos lógicos, ordenados y sencillos de seguir. El uso de asistentes, al estar compuestos por varias pantallas, permite además mejorar el orden y disposición de los componentes.

 

Distinción clara de los elementos: siempre que se incorpore un componente a la pantalla del usuario, el diseñador deberá preocuparse que este sea diferenciable del resto y de que su funcionalidad esté claramente expresada. Para ello, el mejor recurso es la utilización de imágenes, las cuales se recomienda sean únicas para cada componente o agrupación de los mismos, y semejantes a objetos de la vida real, de forma de hacer la aplicación más intuitiva.

 

Atención a las glosas o textos: cada vez que se necesite colocar un texto en pantalla, ya sea para reforzar el concepto de un componente o para entregar una instrucción o advertencia, este deberá ser cuidadosamente escrito, procurando utilizar siempre el mismo tamaño, color y fuente de letra, dejando fuera el uso de "negrita" , "cursiva" o cualquier otro elemento que sobrecargue la pantalla más de lo necesario. Aunque suene obvio, los textos deberán ser siempre lo más concisos y claros posibles, intentando idealmente localizarlos de acuerdo a la región geográfica donde vayan a ser utilizados.

 

 -  Minimizar el uso del teclado y de comandos especiales: no hay aplicación más confusa y difícil de usar que una pensada para "ingenieros". Muchos software caen en el error de incorporar comandos especiales para realizar acciones de programa, pensando que un usuario experto ganará tiempo evitando el uso del mouse. Esto es un error, puesto que son pocos los usuarios que destinan tiempo a leer la documentación de un programa antes de comentar a utilizarlo (mucho menos podrán conocer y memorizar sus comandos de uso); además el uso de comandos aumenta la posibilidad de realizar acciones involuntarias, lo cual puede llegar a ser atemorizante para los usuarios. Una aplicación amigable es aquella que muestra todas las posibles acciones en pantalla; el teclado deberá utilizarse sólo cuando sea imprescindible, como en el llenado de formularios u otras acciones similares.

-  Evitar diálogos innecesarios: existen aplicaciones que ante una acción reiterativa muestran un cuadro de diálogo con un mensaje de éxito. Esto puede resultar extremadamente molesto para un usuario que ya conoce las consecuencias de su acción. Por eso se recomienda el uso de cuadros de diálogo sólo para advertencias o sugerencias críticas (relacionadas a acciones no reversibles).

-  Prevención de errores: un usuario aprenderá más rápido a utilizar y confiar en una aplicación si sabe que no cometerá errores en su uso o si sabe que estos pueden ser revertidos rápidamente. Para esto el diseñador debe saber acotar las posibilidades de acción del usuario, quitando la mayor cantidad de objetos de error posibles; además debe cuidar que cada acción crítica del programa pueda ser revertida en caso de ser requerido.

 Flexibilidad ante todo: no se debe confundir el control con la falta de flexibilidad. Si un usuario, por ejemplo, desea no incorporar una imagen en una tarjeta de presentación utilizando un formato que si la requiere, el software a lo más debería advertir sobre la falta de la foto, pero no prohibirle que termine el proceso de elaboración de su tarjeta. Un desarrollador nunca sabrá los alcances finales y usos definitivos de su software hasta que sea utilizado por sus usuarios, por lo que es mejor enfocar los esfuerzos en mejorar la robustez del software antes que caer en un control excesivo.

-  Manejo de preferencias de usuario: con la tecnología de hoy no es difícil incorporar mecanismos de almacenamiento personalizado de preferencias para los usuarios. Recordar elementos tan sencillos como la configuración del idioma o la aparición de ciertos cuadros de diálogo facilitan enormemente el trabajo de quienes utilizan una aplicación.

 

En resumen una buena interfaz:

-  Disminuye la resistencia natural del usuario a utilizar la aplicación.

-  Reduce los tiempos de aprendizaje.

-  Reduce los errores de uso.

-  Mejora la percepción pública del software.

-  Mejora la calidad de vida de los usuarios (facilita su labor).

 

 
 
 
 
Comments