C/Visual C - pasar array para leerlo en otra función

 
Vista:

pasar array para leerlo en otra función

Publicado por txoco (7 intervenciones) el 16/03/2009 12:38:18
Hola a todos;

Soy nuevo en esto de c y al llegar el uso de funciones, punteros y arrays llegó el atasco.

Ahora estoy con el siguiente programa para practicar en el que pretendo cargar un array en una función y pasarlo a otra para leerlo:

#include <stdio.h>
#define tam 5

void carga ();
void muestra ();

int main()
{
void carga ();
void muestra ();
return 0;
}
//----------------- función carga---------------------
void carga ()
{
int vector [tam];
int i;

printf (" vamos a cargar el vector ");

for (i=0;i<tam;i++)
{
printf (" introduce un valor: ");
scanf ("%i",&vector [i]);
}
}
//--------------funcion muestra-----------
void muestra (int vector)
{
int i
for (i=0;i<tam;i++)
printf ("%i" , *vector[i] );

}

Me devuelve el siguiente error en el último printf : "cargarray.c:34: error: argumento de tipo inválido de ‘unary *’ (se tiene ‘int’)"
y si lo ejecuto se acaba el programa sin hacer nada.

La verdad es que estoy perdido y no se si estoy leyendo bien el array, si lo paso mal a la función o es otra cosa lo que falla.

¿Alguien puede ayudarme?

Gracias por la atención y un saludo.
Valora esta pregunta
Me gusta: Está pregunta es útil y esta claraNo me gusta: Está pregunta no esta clara o no es útil
0
Responder

RE:pasar array para leerlo en otra función

Publicado por Daniel (1 intervención) el 16/03/2009 16:06:19
Antes de nada, yo estoy aprendiendo este año tambien y según lo que doy en el laboratorio si vas a usar un vector de datos declaralo en el main, no en la funcion.

En el printf de mostrar ..... que tipo de dato es %i ??? Ademas el propio progama te lo indica: "argumento de tipo invalido" Fijate en el argumento entonces.
El vector es de tipo entero por lo que debe ser %d
f para float
c para caracter
s para cadena
etc

Para pasar el vector yo lo pasaria así:

main(){
.....
funcion(&vector)
.....
}

void funcion(tipovector *vector){
....
}

Saludos,
Daniel
Valora esta respuesta
Me gusta: Está respuesta es útil y esta claraNo me gusta: Está respuesta no esta clara o no es útil
0
Comentar

RE:pasar array para leerlo en otra función

Publicado por eduardo (82 intervenciones) el 17/03/2009 05:36:50
Pues a simple vista hay varios errores:
* En la función muestra() falta el punto y coma en la declaración del contador i.
* En main() no pasas ningún argumento a muestra() y así lo define tu prototipo, pero sin embargo en la declaración de muestra() especificas un parámetro pero un parámetro entero, mas no un vector de enteros e intentas tratarlo como un array.

Tu programa corregido podría ser asi:
#include <stdio.h>
#include <conio.h>

#define TAM 5

/* prototipos */
void carga( int *a, const int tamanio );
void muestra( const int *a, const int tamanio );

/* la funcion main() comienza la ejecuci¢n del programa */
int main()
{
int vector[TAM];

clrscr();

carga( vector, TAM );
muestra( vector, TAM );

getch(); /* pausa */
return 0; /* indica terminaci¢n exitosa */

} /* fin de main() */

void carga( int *a, const int tamanio )
{
register int i; /* contador */

printf( " Cargando el vector " );

for ( i = 0; i < tamanio; i++ ) {
printf( " Valor pos %2d: ", i + 1 );
scanf( "%i", &a[i] );
}
}

void muestra ( const int *a, const int tamanio )
{
register int i;

printf( " Mostrando el vector " );

for ( i = 0; i < tamanio; i++ )
printf ( "%4i " , a[i] );
}
Valora esta respuesta
Me gusta: Está respuesta es útil y esta claraNo me gusta: Está respuesta no esta clara o no es útil
0
Comentar

RE:pasar array para leerlo en otra función

Publicado por txoco (7 intervenciones) el 17/03/2009 12:00:06
Ok, muchas gracias a los dos.

Eduardo, tu programa funciona perfectamente.
Me temo que tendré que leer más sobre como pasar los arrays a funciones porque no entiendo la lógica de como lo haces.

Por lo que tenía entendido el nombre del vector es un puntero a la primera posición del array y para pasarlo a la función bastaba con llamarlo por su nombre.
Tu además pasas las expresiónes "const int *a" (entiendo que aquí pasas el vector) y "const int tamanio" (que no se a que se refiere. Si es el tamaño, ¿por que? si lo defino en la cabecera). Y en la main los llamas de otra forma (vector, tam).

Por otra parte declaras el vector en la main. ¿No se puede declarar en una función y pasarlo a otra sin que ninguna sea la main?

En fin tendré que empezar otra vez desde atrás, cuando te van saliendo los ejercicios es muy alentador pero cuando te atascas es de lo más frustrante.

Gracias por la atención.
Valora esta respuesta
Me gusta: Está respuesta es útil y esta claraNo me gusta: Está respuesta no esta clara o no es útil
0
Comentar

RE:pasar array para leerlo en otra función

Publicado por eduardo (82 intervenciones) el 18/03/2009 19:21:20
Es verdad lo que dices, el nombre del vector(y de cualquier array) es un puntero a su primer elemento, por tanto quiere decir que cuando pasamos un array a una función lo que se está pasando no es el array completo sino su dirección que viene a ser la misma que la dirección del primer elemento o sea:
&vecto[0] == &vector == vector.
Esto es una excepcion al método de paso de parámetros en C, EL PASO POR VALOR es el método por defecto en donde se pasa una copia del argumento a la función y los cambios que se hagan a la copia dentro de la función o procedimiento no afectan a los argumento desde donde se hizo la llamada. EL PASO POR REFERENCIA se lleva a cabo cuando se pasa la dirección de la variable como argumento y la función ya no trabaja sobre una copia, sino sobre el mismo dato que se ha pasado y los cambios que se hagan al valor al que apunta la dirección, se verán reflejados en el argumento de llamada. Este segundo enfoque es el que se emplea cuando pasamos arrays en C.

Cuando pasamos un vector a una función, hay cuatro formas de declarar la función, en el ejemplo podriamos haberlo declarado con cualquiera de las siguientes formas:

void carga( int a[TAM], const int tamanio );
void carga( int a[9855], int tamanio );
void carga( int a[], const int tamanio );
void carga( int *a, const int tamanio );

En el primer método el parámetro se declara como un vector delimitado con la misma dimensión del vector declarado en main(), aunque en realidad el vector del parámetro NO SE CREA, se convierte a un puntero.

En el segundo método el parámetro se declara como un vector delimitado con una dimensión cualquiera dado que dicho array NO SE CREA, se convierte a un puntero.

En el tercer método el parámetro se declara como un vector no delimitado, sólo especifica que se trata de un vector y el compilador lo convertirá a un puntero.

En el cuarto método el parámetro se declara como un puntero(el compilador ya no necesita convertir), dado que habíamos dicho que lo que se pasa es un puntero al primer elemento del vector pues entonces que lo reciba un puntero.
Un puntero puede ser indexado, hay un relación estrecha entre punteros y arrays.
Personalmente este último método es el que más utilizo para vectores.

Ahora bien, para los arrays de 2 dimensiones se declara como un array delimitado pero sólo se especifica la segunda dimensión(aunque puedes incluir la primera dimensión si lo deseas):
Sea:
int main()
{
int array[FILAS][COLUMNAS];

leer( array );

}

void leer( int b[][COLUMNAS] ) {}

En general cuando se pasa un array de "n" dimensiones a una función, el parámetro de la función debe declararse con todas las dimensiones excepto la primera, aunque si deseas puedes incuirla.

void leer( int c[][DIM2][DIM3]...[DIMn]) {}

A tu otra pregunta porque hago:
mostrar( const int *a, const int tamanio );

const es un especificador de tipo de almacenamiento donde se indica al compilador que la variable que le afecta NO DEBE SER MODIFICADA.
la función mostrar() se dedicará únicamente a imprimir los resultados del vector mas no a modificarlos por tanto la declaro como const para asegurarme que no se vayan a modificar accidentalmente, además es una buena práctica de programación declarar como const las variables en donde una función o procedimiento no la modifica o no debería modificarla.

Yo suelo pasar el tamanio de un vector a una función o procedimiento como dato aunque para tu ejemplo no era absolutamente necesario pasarlo, aunque podría darse el caso que necesites manipular el tamanio como variable y no como una constante simbólica. Si tu revisas algunos algoritmos de ordenamiento, necesitan la longitud del vector y que pasaría si el tamanio no está definido como una constante simbólica.
El tamanio de un vector dentro de una funcion no debería modificarse al menos para arrays estáticos por eso lo declaro como const.

Claro que podrías declarar el vector fuera de main(), y fuera de cualquier función o procedimiento pasando a ser un dato global en donde puede se visible desde cualquier función y desde cualquier parte del archivo fuente en tal caso ya no necesitas pasarlo como parámetro dado que como es visible puedes trabajar sobre él directamente. Esto no es recomendable salvo que no quede más remedio pues siempre trata de pasar las estructuras de datos como parámetros, esto evita que cualquier parte del código acceda a ello, es una técnica que promueve la PROTECCIÓN DE DATOS.

Bueno espero que me hayas entendido.
Salu2.
Valora esta respuesta
Me gusta: Está respuesta es útil y esta claraNo me gusta: Está respuesta no esta clara o no es útil
0
Comentar

RE:pasar array para leerlo en otra función

Publicado por txoco (7 intervenciones) el 19/03/2009 15:55:13
Hola;

Muy amable .
Muchas gracias por la explicación, me dejaste un poco más claro el tema de pasar arrays a funciones.

Cuando digo declarar el array fuera de la main() no me refería a declararlo como variable global, sino (en este ejemplo) declararlo dentro de la función carga y pasarlo a la muestra por ejemplo. Entiendo que sí se podría hacer pero por otra parte pienso que al acabar la función carga el array se borrará (a la manera de variable local) y no será posible recorrerlo con la siguiente aunque se pase por referencia.

Es en esto en lo que ahora tengo el lío (desde luego cuando pruebo no soy capaz de pasarlo de una función a otra).

Un saludo.
Valora esta respuesta
Me gusta: Está respuesta es útil y esta claraNo me gusta: Está respuesta no esta clara o no es útil
0
Comentar

RE:pasar array para leerlo en otra función

Publicado por eduardo (82 intervenciones) el 19/03/2009 17:24:52
Cuando la función donde se crea el array termine, porsupuesto que el array se destruirá PERO si tu llamas a una función mostrar() dentro de cargar() el array aun existe y la función mostrar() perfectamente puede referenciar al array.

#include <stdio.h>
#include <conio.h>

#define TAM 5

/* prototipo */
void cargar_y_mostrar( void );

/* la funcion main() comienza la ejecuci¢n del programa */
int main()
{
clrscr();

cargar_y_mostrar();

getch(); /* pausa */
return 0; /* indica terminaci¢n exitosa */

} /* fin de main() */

void cargar_y_mostrar( void )
{
int vector[TAM];
register int i; /* contador */

void mostrar( const int *a, const int tamanio ); /* prototipo */

printf( " Cargando el vector " );

for ( i = 0; i < TAM; i++ ) {
printf( " Valor pos %2d: ", i + 1 );
scanf( "%i", &vector[i] );
}

mostrar( vector, TAM );
}

void mostrar( const int *a, const int tamanio )
{
register int i;

printf( " Mostrando el vector " );

for ( i = 0; i < tamanio; i++ )
printf ( "%4i " , a[i] );
}

Por otro lado tienes el especificador de clase de almacenamieno static que aplicado a una variable local hace que funcione como una variable global, es decir hace que mantenga su valor entre llamadas a la función sin que se destruyan al salir de la misma.
Échale una ojeada a static.
Salu2
Valora esta respuesta
Me gusta: Está respuesta es útil y esta claraNo me gusta: Está respuesta no esta clara o no es útil
0
Comentar