2.9 Utilidades

2.9.1 El operador sizeof

Este operador nos permite conocer el número de bytes de una variable o el número de bytes ocupados por un array.

Sintaxis:

sizeof(variable) 

Parámetros:

Variable: cualquier tipo de variable o array (int, float, byte)

Ejemplo:

Este operador es muy práctico para trabajar con arrays (por ejemplo strings de texto) cuando queremos cambiar el tamaño del array sin alterar otras partes del programa.

El programa del ejemplo imprime carácter a carácter un string de texto. Prueba el siguiente programa cambiando la frase:

char myStr[] = "esto es una prueba";
int i;

void setup(){
   Serial.begin(9600);
}

void loop() { 
   for (i = 0; i < sizeof(myStr) - 1; i++){
      Serial.print(i, DEC);
      Serial.print(" = ");
      Serial.write(myStr[i]); 
      Serial.println();
   }
   delay(5000); // ralentiza el programa…
}

2.9.2 El operador PROGMEM

Este operador almacena datos en la memoria flash en vez de hacerlo en la RAM del sistema. Este operador PROGMEM debe de ser usado únicamente con los tipos de datos definidos en la librería ‘pgmspace.h’. Este operador ordena al compilador que almacene los datos especificados en la línea del operador en la memoria flash en vez de hacerlo en la RAM del sistema donde iría normalmente.

El operador PROGMEM forma parte de la librería ‘pgmspace.h’, por lo tanto debes incluir esta librería al comienzo de tu sketch:

#include <avr/pgmspace.h>

Sintaxis:

dataType variableName[] PROGMEM = {dataInt0, dataInt1, dataInt3…};

  • program memory dataType –cualquier tipo de variable de los incluidos abajo (program memory data types)
  • variableName – el nombre del array que quieres almacenar en memoria flash.

Hay que tener en cuenta que, dado que el operador utilidad PROGMEM es un modificador variable, no hay una regla fija sobre donde colocarla dentro de la línea de especificaciones. La experiencia muestra que las dos siguientes ubicaciones de PROGMEN tienden a funcionar bien:

dataType variableName[] PROGMEM = {};   //esta ubicación de PROGMEN funciona. 
PROGMEM  dataType  variableName[] = {}; // y esta también 

Pero no esta otra: 

dataType PROGMEM variableName[] = {};   // ni lo intentes…

PROGMEM puede ser usado con una simple variable, sin embargo, debido a la complejidad de su uso, sólo merece la pena usarla cuando quieres almacenar en memoria flash un bloque relativamente grande de datos (generalmente un array).

El uso del operador PROGMEM implica dos operaciones bien diferenciadas: almacenamiento en memoria flash y lectura usando métodos (funciones) específicos definidos en la librería ‘pgmspace.h’ para devolver los datos a la memoria RAM del sistema afín de poder usarlos dentro del sketch.

Tal y como hemos mencionado antes, es esencial usar los tipos de datos especificados en pgmspace.h. Por alguna extraña razón, el compilador no admite los tipos de datos ordinarios. Detallamos debajo la lista completa de variables (“program memory data types”). Parece ser que la “program memory” no se lleva nada bien con los números en coma flotante, así que mejor evitarlos.

 prog_char      - ‘char’ con signo (1 byte) -127 a 128
 prog_uchar     - ‘char’ sin signo (unsigned) (1 byte) 0 a 255
 prog_int16_t   - ‘ int’ con signo (2 bytes) -32,767 a 32,768
 prog_uint16_t  - ‘int’ sin signo (2 bytes) 0 a 65,535
 prog_int32_t   - ‘long’ con signo (4 bytes) -2,147,483,648 a * 2,147,483,647.
 prog_uint32_t  - long´’ sin signo (4 bytes) 0 a 4,294,967,295

Ejemplo

Este ejemplo muestra como leer y escribir variables tipo unsigned char´ (1 byte) e ‘int’ en PROGMEM.

#include <avr/pgmspace.h>  // abrir librería ‘pgmspace.h’
// almacenar en PROGMEM algunos ‘unsigned ints
PROGMEM  prog_uint16_t charSet[]  = { 65000, 32796, 16843, 10, 11234};

// save some chars
prog_uchar signMessage[] PROGMEM  = {"EL CHORIZO NINJA. EL NUEVO ÉXITO DEL CINE ESPAÑOL"};
unsigned int displayInt;
int k;    // contador
char myChar;  

// leer un ‘int’ de dos bytes de la PROGMEM y almacenarlo en “displayint”
 displayInt = pgm_read_word_near(charSet + k)

// leer un ‘chart’ de un byte de la PROGMEM y almacenarlo en “myChart”
myChar =  pgm_read_byte_near(signMessage + k);