c ++: funksjon arg char ** er ikke det samme som char * []

stemmer
4

Jeg bruker g ++. Jeg bruker kode som hadde en main(int,char**), omdøpt så jeg kan kalle det. Jeg så på Bør jeg bruke char ** argv eller char * argv [] i C? , Hvor char**sies å være tilsvarende char* []. Dette ser ikke ut til å være sant i C ++ funksjonskall. For eksempel:

void f1(char** p){;}

void f2(char* p[]){

   f1(p);

 //...`

}

mislykkes med kompilatoren klager kan ikke konvertere char (*)[]til char**... Referansene jeg ser si at arrays konverteres til pekere for samtalen, men dette synes ikke å være tilfelle som:

void f3(char* [] p);

char caa[16][16];  
f3(caa);

også mislykkes. Jeg hadde antatt at så lenge som innholdet av indirekte var de samme (f.eks char*** ptrog char[][][] carray) typene var utskiftbare.

Kan noen gi en referanse jeg kan se som klargjør disse problemene?

Takk.

Publisert på 02/09/2009 klokken 22:06
kilden bruker
På andre språk...                            


2 svar

stemmer
12

Dette holder fortsatt sant i C ++. Hvis kompilatoren klager som du beskriver for første tilfellet er det ikke overholder reglene.

For å forklare det andre tilfellet, er det viktig å forstå hva som faktisk skjer. Et uttrykk for matrise type er implisitt kan omdannes til en tilsvarende pekertypen, dvs: T[n]-> T*. Hvis imidlertid Ti seg selv er en matrise, dette tilfelle ikke behandles spesielt, og matrise-til-pekeren forråtnelse ikke forplanter seg . Så T*[n]henfaller til T**, men T[x][y]vil bare forfall til T[y]*, og ikke lenger.

Fra gjennomføringen perspektiv dette er fornuftig, fordi råtnende videre, hvis det tillates, ville gi T**, som er pekeren til pekeren; mens 2D C matriser ikke er implementert som taggete arrays (dvs. rekke pekere til Arrays) - de danner et enkelt, sammenhengende hukommelsesblokk. Så, det er ingen T*"inside" array til å ta en adresse for å gi deg en T**. For de tillatte tilfeller vil imidlertid en typisk implementering bare tar adressen til matrisen som en helhet, og konverterer den til typen peker til enkelt element (når underliggende pekeren representasjon er den samme for alle typer, slik det vanligvis er tilfelle, er dette konvertering en no-op under kjøring).

Den normative referansen her er ISO C ++ 03, 4,2 [conv.array] / en:

En l-verdi eller r-verdi av typen “array av NT” eller “array av ukjent bundet av T” kan konverteres til en r-verdi av type “peker til T.” Resultatet er en peker til det første element i matrisen.

Svarte 02/09/2009 kl. 22:19
kilden bruker

stemmer
1
void f2(char* p[]){

kompilatoren klager " cannot convert char (*)[] to char**..."

Rar. char(*)[]er en peker til rekke tegn , men i koden biten funksjonen har char *p[]argument, hva betyr rekke pekere til røye ! Disse typene er faktisk annerledes (fordi array elementer har forskjellige størrelser), enn si kodebiten perfekt kompilerer. Du virkelig har feilstavet noe.

Sherlock Holmes-modus : eller er det en typedef involvert? ;-)

void f1(char** p){;}

typedef char type[];
void f2(type * p){
   f1(p);
}

Dette egentlig ikke kompilere og gir feil du refererte til.

Svarte 02/09/2009 kl. 22:42
kilden bruker

Cookies help us deliver our services. By using our services, you agree to our use of cookies. Learn more