Este es un análisis de la naturaleza y el uso de las variables en lenguaje C en el contexto de las aplicaciones para microcontroladores
Muchos de nosotros escuchamos la palabra «variable» en las clases de matemáticas mucho antes de saber mucho, si es que sabemos algo, acerca de la programación de computadoras. Una variable matemática es una cantidad cuyo valor no se conoce o no se limita a un número. Este uso es similar, aunque no idéntico, al concepto de una variable C.
Dos diferencias importantes: primero, en matemáticas, usualmente usamos una letra como x o y para representar una variable, mientras que en C usamos frecuentemente una palabra o frase descriptiva como contadorPulsos, velocidadMedia o cantidadVueltas. En segundo lugar, hay situaciones en las que usamos una variable de C para identificar una cantidad conocida y que no se pretende que cambie del valor original.
Variables en hardware
Las variables son convenientes e intuitivas para los programadores. Para el hardware computacional, por otro lado, no tienen un significado real. Los microprocesadores almacenan datos en registros y ubicaciones de memoria. Esta diferencia fundamental entre las personas que escriben el idioma de máquina y las máquinas que ejecutan este programa se supera mediante lenguajes de alto nivel como C, que maneja varios detalles asociados con la traducción entre variables basadas en texto y la realidad física de un procesador.
Los diseñadores de sistemas integrados trabajan a menudo con procesadores de 8 bits. En estos dispositivos, por lo general, el tamaño fundamental de los datos es un byte. La memoria se organiza de acuerdo con los bytes, el tamaño de los registros es de un byte y la CPU está diseñada para procesar datos de 8 bits. Esta es una limitación bastante incómoda porque hay muchas situaciones en las que el valor de una variable excederá el valor máximo de un número de 8 bits.
El lenguaje C no limita el tamaño de una variable a 8 bits, incluso cuando está trabajando con un procesador de 8 bits. Esto significa que una variable en el programa en lenguaje de máquina que ejecuta el microprocesador puede corresponder a múltiples registros o ubicaciones de memoria en el hardware. «Manualmente» administrar variables de múltiples bytes (es decir, a través del lenguaje ensamblador) no parece muy deseable, pero a los compiladores no les importa en absoluto, y hacen el trabajo muy bien.
Definiendo variables
El primer paso para usar una variable es definir esa variable. Los componentes esenciales de una definición de variable son el tipo y el nombre.
Hay muchos tipos de variables; La lista completa, así como los detalles de la implementación del hardware, variarán según el compilador que esté utilizando. Aquí hay unos ejemplos:
• char : un valor con signo de un byte
• int : un valor con signo de dos o cuatro bytes
• long : un valor con signo de cuatro bytes
• float : un valor de cuatro bytes que puede tener números después del punto decimal; en otras palabras, no está limitado a enteros
• bit : el valor de la variable puede ser cero o uno
Esta es una representación visual de cómo una serie de bits se interpreta de manera diferente en función de si una variable se considera con signo (utilizando la notación de complemento a dos) o sin signo:
El siguiente código muestra definiciones de variables que consisten solo en un tipo básico y un nombre (la forma más técnica de referirse al nombre es «identificador»):
1 2 3 |
int ADC_result; char ReceivedByte; float Reference_Voltage; |
Inicializando variables
En muchos casos, es una buena idea darle un valor inicial a una variable. Esto facilita la depuración y es esencial si la variable se utilizará antes de que le fije un valor conocido. Puede inicializar una variable en la definición, o en otra parte de su código, pero incluir el valor inicial en la definición es una buena manera de mantener el código organizado y desarrollar el hábito de inicializar siempre que sea necesario.
Aquí hay ejemplos de definiciones de variables que incluyen una inicialización:
1 2 3 |
int ADC_resultado = 0; char ReceivedByte = 0x00; float Referencia_Voltaje = 3.25; |
Definiciones de variables delicadas
Hay varias otras palabras que se pueden incluir en una definición de variable. Estos se utilizan para especificar con mayor precisión la naturaleza de la variable o para dar instrucciones al compilador sobre cómo implementar la variable en el hardware.
Las siguientes palabras clave podrían ser útiles en sus proyectos de programa para microcontroladores:
• unsigned : como habrá adivinado, esto le dice al compilador que interprete la variable como un valor sin signo en lugar de un valor con signo. Uno defino le mayoría de sus variables como sin signo, porque rara vez se necesitan números negativos.
• const : el calificador de tipo const indica al compilador que el valor de una variable no debe cambiar. Como dice al principio del artículo, a veces el valor de una «variable» C no es variable. Si usted comete un error en su código e intenta modificar el valor de una variable const, el compilador generará un error.
• volatile : los compiladores sofisticados no solo toman su código original y lo traducen directamente al lenguaje de máquina. También intentan hacer que el código funcione de manera más eficiente, y este proceso se conoce como «optimización». En general, la optimización es algo bueno. Sin embargo, de vez en cuando, puede arruinar el día, porque el compilador se optimiza solo en función del código y no puede tener en cuenta los eventos de hardware que interactúan con el código. Cuando una variable tiene el calificador de tipo volátil, el compilador sabe que debe tener cuidado con las optimizaciones relacionadas con esa variable.
• tipos de memoria, como xdata , idata y code : estas palabras obligan al compilador a ubicar una variable en una parte específica de la memoria del microprocesador. El tipo que aloja en la memoria de programa es particularmente útil: los recursos de RAM en un microcontrolador a menudo son mucho más limitados que la memoria de programa no volátil, y el tipo de memoria de código le permite utilizar memoria de programa adicional para almacenar datos que se usan en su programa pero nunca se modifican.
Aquí hay unos ejemplos:
1 2 3 4 |
unsigned char UART_byte; // The variable's range of acceptable values is 0 to 255. const float PI = 3.14159; volatile unsigned char ADC_Register /* The register can be modified by hardware, so we use the volatile qualifier to avoid optimizations that would cause the program to ignore hardware-generated events. */ unsigned char code CalibrationValue = 78; |
Uso de las variables
No hay mucho que decir acerca de cómo usar sus variables después de que se hayan definido. En realidad, con respecto a la variable en sí, la definición es la mayor parte del trabajo. Después de eso, usted simplemente incorpora el identificador de la variable en operaciones matemáticas, bucles, llamadas a funciones, etc. Un buen compilador no solo manejará los detalles de la implementación del hardware, sino que también buscará formas de optimizar el código con respecto a la velocidad de ejecución o el tamaño del programa.
Quizás el error más común relacionado con el uso variable es un desbordamiento. Esto se refiere a una situación en la que el valor asignado a una variable está fuera del rango numérico asociado con el tipo de datos de la variable.
Se debe pensar en todos los escenarios posibles relacionados con una variable determinada y luego elegir el tipo de datos en consecuencia.
Resumen
La funcionalidad de la variable básica proporcionada por el lenguaje C es intuitiva y directa, pero hay algunos detalles que pueden ayudarlo a hacer que una aplicación integrada sea más confiable y eficiente. Si tiene alguna duda relacionada con las variables de C, no dude en preguntar en nuestro grupo en Facebook Robots Didácticos.