Was ist der richtige Weg, um eine C -Funktion zu schreiben, die ein Char -Array zurückgibt?

StackOverflow https://stackoverflow.com/questions/8311131

  •  25-10-2019
  •  | 
  •  

Frage

Ich bin mit Java ziemlich vertraut, nicht so in C.

Wenn ich in Java eine Methode habe, die etwas tut und eine Zeichenfolge zurückgibt, würde sie so aussehen:

private String doSomething(...) {
    String s;
    // do something;
    return s;
}

Das syntaktische Äquivalent in C würde nicht funktionieren und ist einfach falsch:

char* doSomething(...) {
    char s[100];
    // do something;
    return s;
}

Natürlich kann ich:

char* doSomething(...) {
    char *s;
    s = malloc(100 * sizeof(char));
    // do something;
    return s;
}

Was würde funktionieren (glaube ich!) Aber ich sehe selten Codes, die so tun (liegt es, weil es unnötig den Haufen füllt?)

Am häufigsten sehe ich:

bool doSomething(char *s) {
    // do something that copies chars to s
    return true;
}

Und die Anrufaussagen wären:

char s[100];
doSomething(s);

Was ist, wenn ich die Größe des Char -Arrays erst in der Funktion selbst kenne? dh ich wäre nicht in der Lage, das Char -Array außerhalb der Funktion zu deklarieren und es dann weiterzugeben.

Was würde das sein Korrekt Weg, um mit einem solchen Szenario umzugehen?

War es hilfreich?

Lösung

Ein Beispiel für statische Zuordnungsfall (Sie sind verpflichtet, über die maximale Puffergröße zur Kompilierungszeit nachzudenken)

buf[MAX_NO];
do(buf, MAX_NO);

_Bool do(char *s, size_t len) { 
// use len as boundary in your operations
}

oder dynamische Zuordnungsfall (mit malloc wie Sie sagten und Zeiger zum Speichern des Pufferorts und der Größe und Größe verwenden)

char *s = NULL;
size_t final_len;
do(&s, &final_len);

_Bool do(char** s, size_t* final_len) {
    size_t len = discoverSize();
    char* buf = (char*) malloc(sizeof(char) * len);

    *s = buf; //save memory location
    *final_len = len; //save buffer size
    // use len as boundary in your operations

}

// do whatever
free(s); //remember to free the buffer for politeness

Andere Tipps

Lassen Sie den Anrufcode für die Zuweisung des Speichers verantwortlich sein. Geben Sie den Puffer und die Länge des Puffers in Beispiel 2 ein:

bool doSomething(char *s, size_t buflen)
{ 
    // do something that copies chars to s up to max of buflen
    return true; 
} 

Dies reduziert dazu, Lecks zu reduzieren, da der aufrufende Code die Kontrolle über die Speicherverwaltung unterliegt.

Wenn Sie die richtige Größe der zurückgegebenen Zeichenfolge nicht kennen, verwenden Sie die malloc Lösung. Natürlich musst du free Die Zeichenfolge, nachdem Sie damit fertig sind.

Sie können ein Array in C nicht zurückgeben

Sie können a zurückgeben Zeiger und Sie sollten lernen (indem Sie ein gutes lesen Buchen beim Programmieren in der C Sprache) Der Unterschied zwischen Arrays und Zeigern.

Eine gemeinsame Idiom ist es, einen dynamisch zugewiesenen Zeiger zurückzugeben. Dann sollten Sie eine Konvention haben, die mitteilt, wer den Zeiger befreien wird.

Sie können auch eine Struktur mit einem Array zurückgeben.

Addenda

Wenn Sie einen Müllsammler in C haben möchten, versuchen Sie es mit Boehms Müllsammler

Der sicherste Weg ist, die Verantwortung für die Zuweisung des Anrufers zu überlassen, wie von anderen gesagt.

Wenn Sie jedoch keinen Wiedereintrittscode und keine Einfachheit von Java benötigen, lautet das syntaktische Arbeitsäquivalent in C:

char* doSomething(...) {
    static char s[100];
    // do something;
    return s;
}
Lizenziert unter: CC-BY-SA mit Zuschreibung
Nicht verbunden mit StackOverflow
scroll top