2010-08-18 30 views
5

Estoy tratando de pasar una matriz de cadenas de caracteres (cadenas de estilo C) a una función. Sin embargo, no quiero colocar un tamaño máximo en la longitud de cada cadena que entra en la función, ni tampoco quiero asignar las matrices dinámicamente. Aquí está el código que he escrito en primer lugar:Al pasar matriz de cadenas de caracteres a la función

#include <stdio.h> 
#include <stdlib.h> 
#include <string.h> 

void fun(char *s[]) 
{ 
    printf("Entering Fun\n"); 
    printf("s[1]=%s\n",(char *)s[1]); 
} 

int main(void) 
{ 
    char myStrings[2][12]; 

    strcpy(myStrings[0],"7/2/2010"); 
    strcpy(myStrings[1],"hello"); 
    fun(myStrings); 

    return(0); 
} 

Tengo una falla seg cuando se ejecuta y la siguiente advertencia del compilador: stackov.c: En la función 'main': stackov.c: 17: advertencia: pasando el argumento 1 de 'diversión' desde el puntero incompatible tipo stackov.c: 5: nota: esperado 'char **' pero el argumento es del tipo 'char (*) [12]'

Sin embargo, cuando cambio el main() a la siguiente funciona:

int main(void) 
{ 
    char myStrings[2][12]; 
    char *newStrings[2]; 

    strcpy(myStrings[0],"7/2/2010"); 
    strcpy(myStrings[1],"hello"); 
    newStrings[0]=myStrings[0]; 
    newStrings[1]=myStrings[1]; 
    fun(newStrings); 

    return(0); 
} 

¿No es la matriz [2] [12] lo mismo que una matriz de punteros de caracteres cuando se pasa a una función?

Respuesta

7

No, char array[2][12] es una matriz bidimensional (matriz de matrices). char *array[2] es una matriz de punteros.

char array[2][12] parece:

7/2/2010\0\x\x\xhello\0\x\x\x\x\x\x 

donde \ 0 es NUL y \ x es indeterminada.

mientras

char *array[2] es:

0x CAFEBABEDEADBEEF 

(suponiendo 32-bit)

El primero tiene 24 caracteres contiguos, el segundo tiene dos punteros (a los inicios de cuerdas en otra parte).

2

¿No es la matriz [2] [12] lo mismo que una matriz de punteros de caracteres cuando se pasa a una función?

No, es una matriz bidimensional. La diferencia es que una matriz de punteros contiene punteros, pero array[2][12] es en realidad una matriz de matrices, sin punteros involucrados.

Por cierto que podría hacer:

char* mystrings[2]={"aha", "haha"}; 
fun(mystrings); 
+0

Esto tiene la ventaja de almacenar solo el número real de caracteres necesarios para las cadenas. El inconveniente es que también se asigna un puntero (adicional) para cada cadena. Pero la facilidad de uso de los punteros es la principal ventaja. –

+0

Sí, sé que esto funcionó, pero para la aplicación real, no pude inicializar la matriz en tiempo de compilación. – Mike

+0

@Mike: cuando lo utiliza en una función, la matriz se inicializa en realidad en tiempo de ejecución. – jpalecek

0

Su matriz se declara como una matriz 2-D, pero desea pasarlo a la función como si fuera una matriz 1-D de punteros de cadena.

La respuesta de Tom es correcta, puede omitir el tamaño de la primera dimensión de las declaraciones de matriz multidimensionales para los parámetros de la función.

Su segunda solución funciona porque pasa explícitamente una matriz 1-D de punteros a la función.Por supuesto, requiere la sobrecarga adicional de la matriz de punteros, además de la matriz de cadenas 2-D original.

1

char myStrings[2][12]; declara myStrings como una matriz de matrices de caracteres. Esto significa que myStrings se almacena como los 24 bytes

7/2/2010.???hello.?????? 
‘——————————’‘——————————’ 
myStrings[0]myStrings[1] 

donde . representa un carácter nulo y ? representa un byte sin inicializar.

char *newStrings[2]; declara newStrings como una matriz de punteros a los caracteres. Esto significa que newStrings se almacena como el 2 × sizeof(char*) bytes

[..][..] 

donde [..] representa un objeto de puntero (todavía no inicializado).

Si desea pasar cadenas de diferentes longitudes a su función, debe pasar una serie de punteros, no una matriz de matrices. Como puede ver arriba, estos son diseños diferentes.

Indicaciones generales: cada vez que estás cerca de los punteros, diagramas de sorteo (en la pizarra o la pizarra si es posible, de lo contrario en el papel) que muestra los diversos objetos en la memoria, con flechas que indican lo que se señala dónde. Hay dos tipos de programadores en C: los que dibujan tales diagramas cuando encuentran punteros, y los realmente experimentados que dibujan los diagramas en sus cabezas.

+0

Estoy confundido por su afirmación: "Tenga en cuenta que sus llamadas subsiguientes a strcpy intentan escribir en un puntero que no se haya inicializado. Fue una pura equivocación que el programa diera el resultado que quería en lugar de fallar". ¿Qué quieres decir? Además, ¿a qué te refieres con un "puntero que no se haya inicializado"? Gracias – Mike

+0

@Mike: Lo siento, este bit fue un error de mi parte (leí mal el código). – Gilles

+0

No hay problema. Solo quería asegurarme de no perderme nada. – Mike

Cuestiones relacionadas