convertendo char ** in char * o char
Domanda
Ho un vecchio programma in cui viene utilizzata una funzione di libreria e non ho quella libreria.
Quindi sto scrivendo quel programma usando le librerie di c ++. In quel vecchio codice c'è una funzione che si chiama così
* string = newstrdup (" Alcune stringhe vanno qui ");
la variabile stringa è dichiarata come char ** string;
Che cosa potrebbe fare in quella funzione denominata " newstrdup " ? Ho provato molte cose ma non so cosa stia facendo ... Qualcuno può aiutare
Soluzione
ci deve essere un motivo per cui hanno scritto un "nuovo" versione di strdup. Quindi ci deve essere un caso angolare che gestisce diversamente. come forse una stringa nulla restituisce una stringa vuota.
La risposta di litb è un sostituto di strdup , ma penso che ci sia un motivo per cui hanno fatto quello che hanno fatto.
Se vuoi usare strdup direttamente, usa un define per rinominarlo, piuttosto che scrivere un nuovo codice.
Altri suggerimenti
La funzione viene utilizzata per creare una copia delle stringhe c. Ciò è spesso necessario per ottenere una versione scrivibile di una stringa letterale. Loro (letterali stringa) non sono di per sé scrivibili, quindi una tale funzione li copia in un buffer scrivibile allocato. Puoi quindi passarli a funzioni che modificano il loro argomento dato, come strtok
che scrive nella stringa che deve tokenizzare.
Penso che puoi inventarti qualcosa del genere, dal momento che si chiama new strdup :
char * newstrdup(char const* str) {
char *c = new char[std::strlen(str) + 1];
std::strcpy(c, str);
return c;
}
Dovresti liberarlo una volta fatto usando la stringa usando
delete[] *string;
Un modo alternativo di scriverlo è usare malloc
. Se la libreria è vecchia, potrebbe averla usata, che C ++ ha ereditato da C:
char * newstrdup(char const* str) {
char *c = (char*) malloc(std::strlen(str) + 1);
if(c != NULL) {
std::strcpy(c, str);
}
return c;
}
Ora, dovresti liberare la stringa usando libero
quando fatto:
free(*string);
Preferisci la prima versione se stai scrivendo con C ++. Ma se il codice esistente utilizza gratuito
per deallocare nuovamente la memoria, utilizzare la seconda versione. Attenzione che la seconda versione restituisce NULL
se non è disponibile memoria per duplicare la stringa, mentre la prima genera un'eccezione in quel caso. Un'altra nota dovrebbe essere presa sul comportamento quando passi un argomento NULL
al tuo newstrdup
. A seconda della tua libreria che può essere consentita o potrebbe non essere consentita. Quindi inserire i controlli appropriati nelle funzioni sopra, se necessario. Esiste una funzione chiamata strdup
disponibile nei sistemi POSIX, ma che non consente argomenti NULL
né utilizza l'operatore C ++
nuovo per allocare memoria .
Ad ogni modo, ho cercato su google codesearch le funzioni newstrdup
e ne ho trovate alcune. Forse la tua libreria è tra i risultati:
La riga * string = newstrdup (" Alcune stringhe vanno qui ");
non mostra alcuna stranezza a newstrdup
. Se string
ha il tipo char **
, newstrdup
sta semplicemente restituendo char *
come previsto. Presumibilmente string
era già impostato in modo da puntare a una variabile di tipo char *
in cui inserire il risultato. Altrimenti il ??codice sta scrivendo attraverso un puntatore non inizializzato.
newstrdup sta probabilmente creando una nuova stringa che è un duplicato della stringa passata; restituisce un puntatore alla stringa (che è esso stesso un pointier per i caratteri).
Sembra che abbia scritto una funzione strdup () per operare su un puntatore esistente, probabilmente per riassegnarlo a una nuova dimensione e quindi riempire il suo contenuto. Probabilmente lo sta facendo per riutilizzare lo stesso puntatore in un ciclo in cui * string cambierà frequentemente evitando al contempo una perdita su ogni chiamata successiva a strdup ().
Probabilmente lo implementerei come string = redup (& amp; string, " new contents ") .. ma sono solo io.
Modifica :
Ecco un frammento della mia funzione 'redup' che potrebbe fare qualcosa di simile a quello che hai pubblicato, in un modo diverso:
int redup(char **s1, const char *s2)
{
size_t len, size;
if (s2 == NULL)
return -1;
len = strlen(s2);
size = len + 1;
*s1 = realloc(*s1, size);
if (*s1 == NULL)
return -1;
memset(*s1, 0, size);
memcpy(*s1, s2, len);
return len;
}
Ovviamente, dovrei probabilmente salvare una copia di * s1 e ripristinarla se realloc () fallisce, ma non avevo bisogno di diventare paranoico.
Penso che devi guardare cosa sta succedendo con la stringa " variabile all'interno del codice come prototipo della funzione newstrdup () sembrerebbe identica alla versione strdup () della libreria.
Ci sono chiamate gratuite (* string) nel codice?
Sembrerebbe una cosa strana fare, a meno che non stia conservando internamente una copia della stringa duplicata e restituendo nuovamente un puntatore alla stessa stringa.
Ancora una volta, vorrei chiedere perché?