ProgrammierungC Entwickler

Was passiert bei der Übergabe von Zeigern und Arrays an eine Funktion in C? Welche Unterschiede gibt es, welche Fallstricke bestehen und wie kann man typische Fehler vermeiden?

Bestehen Sie Vorstellungsgespräche mit dem Hintsage-KI-Assistenten

Antwort.

Bei der Übergabe eines Zeigers oder Arrays an eine Funktion in C wird tatsächlich eine Kopie des Wertes des Zeigers (also der Speicheradresse) übergeben, nicht das Array oder den Inhalt des Speichers selbst. Historisch gesehen werden Arrays in C nicht nach Wert übergeben — stattdessen wird ein Zeiger auf das erste Element des Arrays an die Funktion übergeben. Dieses Mechanismus spart Speicher, kann aber zu unerwünschten Nebenwirkungen führen, wenn er falsch verwendet wird.

Problem — Verwirrung zwischen Zeigern und Arrays: Häufig denken Entwickler, dass innerhalb der Funktion das äußere Array nicht verändert werden kann oder dass die Funktion automatisch die Größe des übergebenen Arrays kennt. In der Praxis verliert die Funktion die ursprüngliche Größe des Arrays und kann leicht über dessen Grenzen hinausgehen.

Lösung — Immer die Größe des Arrays als separates Argument explizit übergeben, den Unterschied zwischen einer Zeigerkopie und einer Objektkopie klar verstehen und nicht vergessen, dass alle Änderungen über den Zeiger die ursprünglichen Daten widerspiegeln.

Beispiel für die korrekte Übergabe eines Arrays:

void print_array(const int* arr, size_t size) { for (size_t i = 0; i < size; ++i) printf("%d ", arr[i]); } int main() { int nums[] = {1,2,3,4,5}; print_array(nums, sizeof(nums)/sizeof(nums[0])); return 0; }

Schlüsselpunkte:

  • Es wird die Adresse des Arrays übergeben, nicht eine Kopie der Elemente.
  • Die Größe des Arrays muss explizit übergeben werden.
  • Änderungen der Elemente innerhalb der Funktion ändern das äußere Array.

Fangfragen.

Kann eine Funktion die Länge des übergebenen Arrays erfahren, wenn es als int arr[10] deklariert wurde?

Antwort: Nein, innerhalb der Funktion gibt der Ausdruck sizeof(arr) die Größe des Zeigers und nicht die des gesamten Arrays zurück. Die Größe muss separat übergeben werden.

Ist die Übergabe eines Arrays als int arr[] und als int arr in Funktionen dasselbe?*

Antwort: Ja, in der Funktionssignatur ist es äquivalent — in beiden Fällen wird ein Zeiger auf int übergeben. Die Unterschiede bestehen lediglich in der Syntax.

Werden die ursprünglichen Array-Elemente geändert, wenn die Elemente innerhalb der Funktion verändert werden?

Antwort: Ja, da ein Zeiger übergeben wurde, verändert die Funktion den Speicher, auf den er zeigt.

Typische Fehler und Anti-Pattern

  • Größe des Arrays nicht als Argument übergeben (Überlauf).
  • Verwendung von sizeof(arr) zur Bestimmung der Größe des Arrays in der Funktion (falsches Ergebnis).
  • Verwechseln von int arr[10] mit int* arr in verschiedenen Kontexten.

Beispiel aus dem Leben

Negativer Fall

Das Projekt implementierte eine Funktion zur Initialisierung von Arrays, die die Größe innerhalb der Funktion über sizeof(arr) / sizeof(arr[0]) bestimmte. In der Testphase funktionierte die Funktion, aber beim Verarbeiten anderer Arrays überschritt sie die Grenzen des Speichers oder arbeitete nicht korrekt.

Vorteile:

  • Die Signatur der Funktion war einfacher.

Nachteile:

  • Das Programm stürzte ab oder arbeitete nicht korrekt mit anderen Daten.

Positiver Fall

Die Funktion akzeptierte immer die Größe des Arrays als separaten Parameter, die Länge wurde von der aufrufenden Seite berechnet. Innerhalb der Funktion wurde nur mit den übergebenen Parametern gearbeitet.

Vorteile:

  • Garantie, dass keine Grenzüberschreitung stattfindet.
  • Sicherer, robuster und portabler Code.

Nachteile:

  • Notwendigkeit, die Größe explizit zu übergeben, Aufruf ist etwas länger.