ANSI C-ben mi a legelfogadottabb módszer módosítható karakterláncok definiálására?
char str[] = "Hello world!";
printf("before: %s\n",str);
str[0] = 'R';
printf("after: %s\n",str);
Ansi C-ben stringet vagy char típúsú (vagy integer jellegű) tömbben tárolod, vagy láncolt listában.
Ha a hossz nem változik, akkor tömböt érdemes, amit indexelve egy-egy karaktert módosíthatsz benne.
Nem voltam ezek szerint elég érthető. Az #1-es válaszoló példája tökéletesen mutatja hogy mit nem szabad csinálni, mit szeretnék elkerülni!
char str[] = "Hello world!";
Ez a sor mentheti a "Hello world!" szöveget írásvédett területre is ezért ne szabad felülírni ANSI C-ben. Ha megpróbáljuk lehet hogy sikerül, lehet hogy elszáll a program, ez implementációtól függ.
Jelenleg a legjobb ötletem erre az hogy lefoglalok egy memóriaterületet dinamikusan, memcpy-vel vagy strcpy függvényekkel átmásolom a tartalmát, használom, majd a végén felszabadítom. Érezhető hogy az így egy kicsit ágyúval verébre probléma.
Másik megoldás lehet hogy így definiálom:
char str[] = {'H', 'e', 'l', 'l' .... , 'd', '\0'};
Ezután csak rábízom az optimizerre a dolgot. Érezhető hogy hosszú szövegek estén nem éppen a legszebb megoldás.
"Érezhető hogy az így egy kicsit ágyúval verébre probléma.
"
Ilyen a C nyelv, ott így működik.
Tesztelgettem egy kicsit a dolgot és megnéztem assembly-ben mi történik linux alatt gcc-vel. -ansi -pedantic -O2 kapcsolókat nyomtam be neki.
A szöveget egy írásvédett helyre menti char[] típusként. Ha több változót is ugyan azzal a szöveggel definiálsz, nem rakja be kétszer a memóriába, ugyan arra a helyre fognak mutatni. A következő program True szöveggel tér vissza:
#include <stdio.h>
int main(void) {
char* hello = "Hello World!";
char* world = "Hello World!";
if(hello == world)
printf("True\n");
else
printf("False\n");
return 0;
}
Ha megpróbálom módosítani a szövegeket, elszáll a program.
Ha char* helyett char[] típusként definiálom a változót, érdekes módon a program automatikusan _átmásolja_ az írásvédett területen lévő char[] szöveget a stackre, ezért lehet módosítani. Úgy tűnik ez az elvárt viselkedés. #1-es valószínűleg mégis jó, de nem azért amit írt. Bizony írásvédett de végrehajt egy memcpy-t a háttérben a programozó tudta nélkül.
A konklúzió az hogy ha nem akarod módosítani, akkor mindig char*-t használj, ha igen akkor mindig char[]-t. Tudni kell róla hogy az utóbbi lassabb és memóriaigényesebb ezért ha nem kötelező akkor ne használjuk. Rejtély megoldva.
C++-ban átalakították és const char[] típusként kell definiálni hogy ne másoljon és jelezze is hogy ez egy konstans, nem kéne módosítani. Így nincs belőle probléma.
Kapcsolódó kérdések:
Minden jog fenntartva © 2024, www.gyakorikerdesek.hu
GYIK | Szabályzat | Jogi nyilatkozat | Adatvédelem | Cookie beállítások | WebMinute Kft. | Facebook | Kapcsolat: info(kukac)gyakorikerdesek.hu
Ha kifogással szeretne élni valamely tartalommal kapcsolatban, kérjük jelezze e-mailes elérhetőségünkön!