ProgrammatieC ontwikkelaar

Beschrijf de verschillen tussen de incrementeeroperaties (i++) en (++i) in de programmeertaal C. Wat is hun semantiek, wanneer moet je welke variant gebruiken en wat zijn de gevaren in complexe expressies?

Slaag voor sollicitatiegesprekken met de Hintsage AI-assistent

Antwoord

In de programmeertaal C verhogen de postfix (i++) en prefix (++i) incrementeeroperaties de waarde van een variabele met 1, maar de geretourneerde waarde verschilt:

  • i++ (postfix): geeft eerst de huidige waarde terug en verhoogt deze daarna.
  • ++i (prefix): verhoogt eerst de waarde en geeft daarna de nieuwe waarde terug.

Voorbeeld:

int i = 5; int a = i++; // a == 5, i == 6 int j = 5; int b = ++j; // b == 6, j == 6

In eenvoudige expressies is het verschil onbeduidend, maar in complexe expressies (bijvoorbeeld met meerdere incrementeeroperaties tegelijk) kan er onbepaald gedrag optreden.

Vervelend Vraag

Wat zal de waarde van de variabele a zijn na het uitvoeren van de expressie int a = i++ + ++i;, als i = 1?

Antwoord:

De berekening hangt af van de volgorde van operandberekeningen, die door de standaard niet wordt gegarandeerd, en leidt ook tot onbepaald gedrag (undefined behavior), omdat de variabele i meer dan eens wordt gewijzigd tussen opeenvolgend gebruik van de waarde. Dit is niet acceptabel!

Voorbeeld van dergelijke code:

int i = 1; int a = i++ + ++i; // onbepaald gedrag! Gebruik dit niet!

Voorbeelden van echte fouten door onbekendheid met de nuances van het onderwerp


Verhaal

In een groot project werd de indexberekening in een array geschreven als arr[i++] = getValue(++i); — de ontwikkelaar wilde de oude waarde bewaren terwijl hij tegelijkertijd de nieuwe verkreeg. In verschillende compilers varieerde het gedrag: soms overschreef de ene waarde de andere, soms crashte het programma. De reden was onaanvaardbare meervoudige wijzigingen van i in één expressie.


Verhaal

In een embedded project werd de teller verhoogd als onderdeel van een complexe expressie: if (buffer[i++] == TERMINATOR && ++i < SIZE) ... — op 'hardware' resulteerde dit soms in een onjuiste index vanwege verschillende berekeningsvolgordes, wat leidde tot het lezen van niet-geïnitieerde gegevens.


Verhaal

Bij het porteren van code naar een andere compiler leidde het verschil in implementatie van de operandberekeningsvolgorde ertoe dat een loop zoals while (arr[i++] && i < MAX && arr[++i]) zich onvoorspelbaar gedroeg. De bug werd alleen ontdekt door de resultaten van de testfase op het apparaat van de klant.