5.1.7C Programming

Functions — declaration vs definition, prototypes, call by value

2,058 words9 min readdifficulty · medium

WHAT are these three things?


WHY does C need a prototype at all?

HOW the pieces fit in a file:

#include <stdio.h>
 
int add(int a, int b);          // 1. DECLARATION (prototype) — promise
 
int main(void) {
    int s = add(3, 4);          // 2. CALL — compiler checks against promise
    printf("%d\n", s);          // prints 7
    return 0;
}
 
int add(int a, int b) {         // 3. DEFINITION — fulfil the promise
    return a + b;
}

Figure — Functions — declaration vs definition, prototypes, call by value

Call by value — the COPY, derived step by step


Common Mistakes (Steel-manned)


Recall Explain it to a 12-year-old (Feynman)

Imagine you have a recipe machine. First you put up a sign saying "There's a machine called ADD that takes two numbers and gives one back" — that's the declaration. Later you actually build the machine with all its gears — that's the definition. When you use it, you don't hand over your real cookies; you give it photocopies of your numbers. The machine plays with the photocopies, hands you a result, and your real numbers at home are exactly as they were. That photocopy rule is called call by value. If you really want the machine to change your home stuff, you give it your home address (a pointer) instead of a copy.


Flashcards

What does a function declaration (prototype) specify?
The function's name, return type, and parameter types — but no body; ends with ;.
How many times may a function be defined vs declared?
Defined exactly once (One Definition Rule); declared as many times as you like.
Why does C require a prototype before a call?
The single-pass compiler must know the argument types and return type to check the call and convert arguments; otherwise it guesses (implicit int) and bugs appear.
In call by value, what gets passed to the function?
A copy of each argument's value, placed into the parameter (a fresh local in the stack frame).
Why doesn't a normal swap(a,b) change a and b in main?
It swaps local copies x and y; the originals are separate memory and untouched.
How do you make a function modify the caller's variable in C?
Pass the address (&var) and use a pointer parameter; dereference (*p) to edit the original.
Is a definition also a declaration?
Yes — a definition includes the signature, so it declares the function too. The reverse is not true.
Are parameter names required in a prototype?
No — int add(int, int); is valid; names are optional in declarations.
What is a stack frame's role in call by value?
It holds the copied parameters and locals for one call; destroyed on return, so changes don't escape.
Passing a pointer — is that still call by value?
Yes; the address value is copied. But since it points to the original, dereferencing edits the real data.

Connections

  • Pointers in C — how to escape call-by-value and edit caller data.
  • Stack and Function Call Mechanism — where the copies live.
  • Header Files and Separate Compilation — why declarations live in .h.
  • Arrays as Function Arguments — arrays "decay" to pointers (an exception that feels like call-by-reference).
  • Recursion — each recursive call gets its own copied parameters.
  • Scope and Lifetime of Variables — parameters are locals with function scope.

Concept Map

announced by

built by

used by

specifies

adds

has same

limited by

requires before call

lets compiler check

creates

holds

realizes

leaves

Function: named reusable machine

Declaration / Prototype

Definition

Function Call

Name, return type, param types

Body with braces

One Definition Rule

Single-pass compiler

Call by Value

Stack frame scratchpad

Argument value copied

Caller variables unchanged

Hinglish (regional understanding)

Intuition Hinglish mein samjho

Dekho, ek function teen stages se guzarta hai. Pehle declaration (prototype) — ye sirf ek promise hai: "bhai, ek function hai add jo do int leta hai aur ek int deta hai." Isme body nahi hoti, bas semicolon. Phir definition — yahan asli code likha jaata hai { ... } ke andar. Declaration kitni baar bhi likh sakte ho, par definition sirf ek baar. C compiler upar se neeche ek hi baar padhta hai, isliye agar tum add() call karne se pehle uska prototype nahi dikhaoge, to compiler guess karega aur bugs aa jaayenge. Isiliye prototype main ke upar likho.

Sabse important concept hai call by value. Jab tum function ko argument dete ho, C uss value ki photocopy bana ke parameter mein daal deta hai. Function us copy ke saath khelta hai, tumhare original variable ko haath nahi lagता. Isliye classic swap(a, b) kaam nahi karta — wo sirf andar ki copies x aur y swap karta hai, main ke a aur b waise ke waise rehte hain.

Agar sach mein original variable badalna hai, to value ki jagah uska address (&a) bhej do aur pointer parameter use karo (int *x), phir *x se original ko edit karo. Yaad rakho — ye bhi technically call by value hi hai, kyunki address ki value copy hoti hai, par wo address ghar ka pata hai, isliye edit ghar tak pahunch jaata hai. Mantra simple: Promise, Build, Photocopy.

Go deeper — visual, from zero

Test yourself — C Programming

Connections