Docs
Functions
Functions in C
š Introduction
A function is a self-contained block of code that performs a specific task. Functions allow you to break complex programs into smaller, manageable pieces. This promotes code reusability, readability, and easier debugging.
šÆ Why Use Functions?
Without Functions: With Functions:
āāāāāāāāāāāāāāāāāāāāāāāāāāā āāāāāāāāāāāāāāāāāāāāāāāāāāā
ā main() { ā ā main() { ā
ā // 100 lines for ā ā readInput(); ā
ā // reading input ā ā processData(); ā
ā ā ā displayResults(); ā
ā // 200 lines for ā ā } ā
ā // processing ā ā ā
ā ā ā void readInput() {...} ā
ā // 100 lines for ā ā void processData() {...}ā
ā // output ā ā void displayResults()...ā
ā } ā āāāāāāāāāāāāāāāāāāāāāāāāāāā
āāāāāāāāāāāāāāāāāāāāāāāāāāā
Hard to maintain Organized & Reusable
Benefits:
| Benefit | Description |
|---|---|
| Modularity | Break code into logical pieces |
| Reusability | Write once, use many times |
| Readability | Easier to understand |
| Debugging | Isolate and fix bugs easily |
| Collaboration | Different programmers work on different functions |
š Function Syntax
Structure:
return_type function_name(parameter_list) {
// Function body
// Statements
return value; // Optional, based on return_type
}
Components:
āāāā Return Type (what the function gives back)
ā
ā āāāā Function Name (identifier)
ā ā
ā ā āāāā Parameters (inputs)
ā ā ā
ā¼ ā¼ ā¼
int add (int a, int b)
{
return a + b; āāāā Return Statement
}
ā²
ā
āāāā Function Body (what it does)
š§ Function Types
1. No Return, No Parameters:
void greet(void) {
printf("Hello, World!\n");
}
// Call:
greet();
2. No Return, With Parameters:
void printSum(int a, int b) {
printf("Sum: %d\n", a + b);
}
// Call:
printSum(5, 3); // Output: Sum: 8
3. With Return, No Parameters:
int getRandomNumber(void) {
return 42;
}
// Call:
int num = getRandomNumber();
4. With Return, With Parameters:
int add(int a, int b) {
return a + b;
}
// Call:
int result = add(10, 20); // result = 30
š Function Declaration vs Definition
Declaration (Prototype):
Tells the compiler about the function's signature.
// Declaration (prototype) - usually at top of file or in header
int add(int a, int b); // With parameter names (optional)
int multiply(int, int); // Without parameter names (valid)
Definition:
The actual implementation of the function.
// Definition - the full function
int add(int a, int b) {
return a + b;
}
Complete Example:
#include <stdio.h>
// Declaration (prototype)
int square(int n);
void printLine(void);
int main() {
printLine();
printf("Square of 5: %d\n", square(5));
printLine();
return 0;
}
// Definitions
int square(int n) {
return n * n;
}
void printLine(void) {
printf("-------------------\n");
}
š Function Call Flow
main() square(5)
ā ā
ā Call square(5) ā
āāāāāāāāāāāāāāāāāāāāāāāāāāāāāāŗ ā
ā ā n = 5
ā ā Calculate 5 * 5
ā ā return 25
ā Receive 25 ā
āāāāāāāāāāāāāāāāāāāāāāāāāāāāāā ā
ā ā
ā¼ Continue execution ā¼
š„ Parameters and Arguments
Terminology:
- ā¢Parameters: Variables in function definition (formal parameters)
- ā¢Arguments: Values passed during function call (actual parameters)
// Parameters
// ā ā
int add(int a, int b) {
return a + b;
}
int main() {
int x = 5, y = 10;
int sum = add(x, y); // x and y are Arguments
// ā ā
// Arguments
}
Pass by Value:
C passes arguments by value - a copy is made.
void increment(int n) {
n = n + 1; // Changes local copy only!
printf("Inside: %d\n", n);
}
int main() {
int x = 5;
increment(x);
printf("Outside: %d\n", x); // Still 5!
return 0;
}
// Output:
// Inside: 6
// Outside: 5
š¤ Return Values
Single Return:
int max(int a, int b) {
if (a > b) {
return a;
}
return b;
}
Multiple Return Points:
int grade(int score) {
if (score >= 90) return 'A';
if (score >= 80) return 'B';
if (score >= 70) return 'C';
if (score >= 60) return 'D';
return 'F';
}
Return with Expression:
int factorial(int n) {
if (n <= 1) return 1;
return n * factorial(n - 1);
}
void Return:
void printError(int code) {
if (code == 0) {
return; // Early exit, no value
}
printf("Error code: %d\n", code);
}
š¢ Data Types for Return
| Return Type | Description | Example |
|---|---|---|
void | No return value | void printHello() |
int | Integer | int getAge() |
float | Floating point | float getAverage() |
double | Double precision | double calculatePi() |
char | Single character | char getGrade() |
int* | Pointer | int* createArray() |
š Standard Library Functions
C provides many built-in functions:
stdio.h:
printf("Hello"); // Print formatted output
scanf("%d", &n); // Read input
puts("String"); // Print string with newline
getchar(); // Read single character
string.h:
strlen(str); // String length
strcpy(dest, src); // Copy string
strcmp(s1, s2); // Compare strings
strcat(dest, src); // Concatenate strings
math.h:
sqrt(x); // Square root
pow(x, y); // x to the power y
abs(x); // Absolute value
sin(x), cos(x); // Trigonometric functions
stdlib.h:
malloc(size); // Allocate memory
free(ptr); // Free memory
rand(); // Random number
atoi(str); // String to integer
š Function Scope
Local Variables:
void function1() {
int x = 10; // Local to function1
printf("%d\n", x);
}
void function2() {
// x is NOT accessible here!
int y = 20; // Local to function2
}
Global Variables:
int globalVar = 100; // Accessible everywhere
void function1() {
printf("%d\n", globalVar); // Works!
}
void function2() {
globalVar = 200; // Modified!
}
Variable Scope Diagram:
āāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāā
ā Global Scope ā
ā int globalVar; ā
ā ā
ā āāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāā ā
ā ā function1() ā ā
ā ā int localA; // Only here ā ā
ā ā // globalVar accessible ā ā
ā āāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāā ā
ā ā
ā āāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāā ā
ā ā function2() ā ā
ā ā int localB; // Only here ā ā
ā ā // localA NOT accessible! ā ā
ā āāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāā ā
ā ā
āāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāā
šØ Best Practices
1. Naming Conventions:
// Good - descriptive names
int calculateArea(int length, int width);
void printStudentInfo(char* name, int age);
// Bad - vague names
int calc(int l, int w);
void print(char* n, int a);
2. Single Responsibility:
// Good - one task per function
int calculateSum(int arr[], int size);
void printArray(int arr[], int size);
// Bad - doing too much
void calculateAndPrintSum(int arr[], int size);
3. Function Length:
- ā¢Keep functions short (< 50 lines ideally)
- ā¢If too long, break into smaller functions
4. Documentation:
/**
* Calculates the factorial of a number.
*
* @param n The number to calculate factorial for
* @return The factorial of n, or -1 if n is negative
*/
int factorial(int n) {
if (n < 0) return -1;
if (n <= 1) return 1;
return n * factorial(n - 1);
}
ā ļø Common Mistakes
1. Forgetting Return:
// Wrong - should return something
int add(int a, int b) {
int sum = a + b;
// Forgot return!
}
// Correct
int add(int a, int b) {
return a + b;
}
2. Wrong Return Type:
// Wrong - returning float but declared int
int divide(int a, int b) {
return (float)a / b; // Truncated!
}
// Correct
float divide(int a, int b) {
return (float)a / b;
}
3. Missing Prototype:
int main() {
greet(); // Error: function not declared!
return 0;
}
void greet() {
printf("Hello!\n");
}
š Key Takeaways
- ā¢Functions divide code into reusable blocks
- ā¢Declare (prototype) before use, define anywhere
- ā¢C uses pass by value - copies are passed
- ā¢Use
returnto send back a value - ā¢
voidmeans no return value - ā¢Keep functions focused on one task
- ā¢Use descriptive function names
āļø Next Topic
Continue to Function Parameters to learn about different parameter passing techniques.