Arrays Dins

  • November 2019
  • PDF

This document was uploaded by user and they confirmed that they have the permission to share it. If you are author or own the copyright of this book, please report to us by using this DMCA report form. Report DMCA


Overview

Download & View Arrays Dins as PDF for free.

More details

  • Words: 1,206
  • Pages: 5
NOTA: El siguiente documento requiere que tengas unos conocimientos medios de programación en fenix, así como que sepas hacer uso de los punteros (en especial los punteros a arrays).

Arrays Dinámicos en Fénix by Danko Casi todos los que programamos solemos hacer uso de los arrays o matrices en nuestros programas, debido a las ventajas o claridad que éstos nos brindan en muchos de los casos. Muchas veces conocemos el número de elementos que vamos a necesitar a lo largo del programa, pero hay ocasiones en las que no. En estos casos hay dos posibles soluciones: 1. Utilizar un array normal con un número de elementos que consideremos suficientemente grande. 2. Hacer uso de las funciones de memória junto con punteros para crear arrays dinámicos. Las ventajas de un método u otro son obvias. La primera forma es mucho más simple y en la mayoría de los casos será la que utilicemos. La segunda en cambio permite que no desaprobechemos memória (y para arrays muy grandes es recomendable utilizarla). En éste documento se abordará la creación de arrays dinámicos. Crear un array dinámico Para crear un array dínamico haremos uso de la función de memória alloc(bytes). Ésta reserva tantos bytes de memória como se le indiquen y devuelve un puntero a ella, por tanto necesitaremos una variable de tipo puntero ptr. A partir de ahí podremos acceder a los elmentos de nuestro array dinámico usando [ptr+elemento] o *(ptr+elemento) o ptr[elemento] (las tres significan lo mismo, pero la última es más comoda de usar). No obstante hay que tener algunas consideraciones: • Tenemos que tener en cuenta el tipo del array que queremos crear, ya que alloc reserva Bytes. Por ejemplo, si quermos crear un array de 1000 variables de tipo int deberemos reservar 4000 bytes de memória, ya que cada variable de tipo int ocupa 4 bytes. La zona de memória devuelta por alloc podría tener restos de un uso • anterior, por lo que debemos inicializarla. • La memória reservada debemos liberarla mediante la función free(pointer memória) a la que le pasamos como parámetro el puntero obtenido con alloc(); • Debemos de llevar cuidado de no acceder a elementos que sobrepasen el espacio reservado, ya que los resultados pueden ser impredecibles Veamos un ejemplo de un array dinámico: global int pointer mi_array; begin

mi_array = alloc(16); //reservamos 4 elementos (recuerda que el tamaño de un int son 4 bytes [mi_array] = 2; //el elemento 0 dle array pasa a valer 2 *mi_array = 1; //ahora el elemento 0 del array vale 1 mi_array[1] = 5; //el elemento 1 del array vale 5 mi_array[8] = 10; //El programa se compilará y se ejecutará, pero pueden producirse resultados inesperados end Como veis es muy sencillo crear un array dinámico y acceder a sus elementos. Inicializar todos los elementos del array a un número Debido a que la zona de memória devuelta por alloc podría tener restos de un uso anterior, es recomendable inicializar todos los valores del array. Para hacerlo de un modo sencillo podemos utilizar la función memset(pointer memoria,valor,bytes) que rellena un área de memória de tantos bytes como se le indiquen con el valor que se le pase como parámetro. Tras el alloc, podríamos poner: memset(mi_array,0,16); Y los cuatro elementos del array pasaran a valer 0. Redimensionar el array Una vez tenemos nuestro array creado podemos cambiar el número de elementos con la función realloc(pointer memoria, bytes): mi_array = realloc(mi_array,36); //mi_array tendrá 9 elementos mi_array[8] = 100; //ahora no hay ningun problema en acceder. Liberar la memória Es importante que liberemos la memória utilizada cuando hayamos terminado de trabajar con el array, para ello aremos uso de free: free(mi_array); Y esto es todo lo que necesitamos saber para crear arrays dinámicos.

Trabajando con arrays dinámicos Vamos a hacer un ejemplo de lo que podría ser una forma para trabajar con arrays dinámicos de enteros cómoda e intuitivamente. Éste método lo uso a modo de ejemplo, pero seguramente se pueden desarrollar métodos más apropiados. Para empezar necesitaremos crear un bloque type: type i_array pointer el; //Este será el puntero donde almacenemos el puntero devuelto por alloc len; //Longitud del array, para poder hacer por ejemplo un for(i=0;i<mi_array.len;i++)

st = 0;

//Para controlar si ya se ha reservado memória para el

array end Ahora crearemos unas funciones para trabajar con este tipo de datos que hemos creado. process i_dim(i_array pointer var, int elements) begin var.el = alloc(elements*4); //Reservamos memória para los elementos (*4 porque sizeof(int)=4) var.len = elements; memset(var.el,0,elements*4); //Inicializamos los elementos a 0 end Como veis, este proceso no tiene ningun misterio. Hemos tenido que usar un parametro de tipo i_array pointer para poder pasar las variables de tipo i_array por referéncia. Ahora la rutina para redimensionar: process i_redim(i_array pointer var, int elements) begin var.el = realloc(elements*4); //Como se ha explicado antes... var.len = elements; end Que tampoco tiene nada de especial... Si queremos evitar algunos errores (por ejemplo que se reserve memória cuando ya ha sido reservada, o que se redimensione sin haber reservado) aremos uso de la variable st del tipo i_array. Los procesos quedarían así: process i_dim(i_array pointer var,int elements); begin if(!(var.st)) //si var.st==0 (no se ha reservado memória todavia) var.el=alloc(elements*4); var.len=elements; var.st=1; //establecemos a 1 el valor de st. else //si ya se ha reservado memória, i_redim(var,elements); //redimensionamos el array(de modo que ahora podemos usar i_dim para redimensionar end memset(var.el,0,elements*4); //inicializamos a 0 end process i_redim(i_array pointer var, int elements); begin if(var.st) //si var.st<>0 (se ha reservado memória)

var.el=realloc(var.el,elements*4); var.len=elements; else

//si no

i_dim(var,elements); memória por primera vez end end

//reservamos

Como ves ahora podemos hacer uso tanto de i_dim como de i_redim para redimensionar el array una vez que ya ha sido creado, sin embargo hay una pequeña diferéncia entre un método u otro. Si usamos i_dim para redimensionar tambien estaremos incializando todos los valores a 0. Ésto se ha hecho así a propósito ya que a veces nos interesará mantener los valores (usaremos i_redim) y otras veces no. Por otro lado, no hay diferéncia entre crear el array con i_dim o con i_redim (tan sólo que en operaciones muy, muy largas el segundo sería algo más lento ya que tiene que hacer una comprobación más). Por último nos queda implementar la rutina de liberación de memória: process i_erase(i_array pointer var) begin free(var.el);var.len=0;var.st=0; //liberamos y "reseteamos" la variable de tipo i_array end Un posible programa de ejemplo utilizando todo esto sería: global i_array mi_array; begin i_dim(mi_array,4); //creamos un array de 4 elementos mi_array.el[0]=write(0,0,0,0, "Primer elmento del array"); mi_array.el[1]=write(0,0,10,0, "Segundo elemento del array"); mi_array.el[2]=write(0,0,20,0, "Tercer elemento del array"); mi_array.el[3]=write(0,0,30,0,"Cuarto elemento del array"); repeat frame; until(key(_enter)) borra_textos(); i_dim(mi_array,2); //redimensionamos a 2 elementos y inicializamos a0 mi_array.el[0]=write(0,0,0,0, "He borrado todo el texto"); mi_array.el[1]=write(0,0,10,0, "sin saber cuanto texto había :D"); repeat frame; until(key(_esc)) i_erase(mi_array); //liberamos end process borra_textos() private conta; begin for(conta=0;conta<mi_array.len;conta++)

delete_text(mi_array.el[conta]); end end Y esto es todo por ahora. Si quieres puedes implementar las funciones necesarias y el bloque type para trabajar con arrays que no sean de enteros, pero ten en cuenta los bytes que ocupa cada uno (sizeof(word)=2, sizeof(byte)=1,etc). Espero que por lo menos a alguno os haya sido útil, ya se que no está muy bien explicado pero se hace lo que se puede. Si tienes cualquier duda: [email protected] Danko

Related Documents

Arrays Dins
November 2019 23
Arrays
November 2019 37
Arrays
May 2020 23
Arrays
November 2019 37
Arrays
November 2019 39
Arrays
November 2019 46