Python Functions
A function is a reusable block of code that performs a specific task. It only runs when it is “called.”
- Input: Arguments.
- Process: Function Logic.
- Output: Return Value.
2. Why Functions Matter
- Reusability (DRY – Don’t Repeat Yourself): Write the logic once, use it everywhere.
- Modularity: Break a complex 1000-line program into 10 small, manageable functions.
- Maintainability: If the logic changes, you only update it in one place.
- Namespace Management: Helps avoid variable name conflicts (Scoping).
3. Basic Syntax & Execution
1. Defining a Function
We use the def keyword followed by the function name and parentheses.
def say_hello():
"""This function prints a greeting message."""
print("Hello! Welcome to Python.")2. Calling a Function
The function won’t execute until you call it by its name.
say_hello()4. Parameters vs. Arguments
- Parameter: The variable listed inside the parentheses in the def line (the placeholder).
- Argument: The actual value sent to the function when it is called (the real data).
def greet(name): # 'name' is the Parameter
print(f"Hi {name}")
greet("Rajkumar") # "Rajkumar" is the Argument5. The return Statement
print() only shows a value on your screen. return sends a value back to the program so it can be stored and used later.
def add(a, b):
return a + b
result = add(5, 10)
print(result * 2) # Output: 30A function stops the moment it hits a return. Any code written after it is ignored.
6. Argument Variations
1. Default Arguments
Provide a fallback value if the user forgets to pass an argument.
def power(num, exp=2):
return num ** exp
print(power(4)) # 16 (uses default 2)
print(power(4, 3)) # 64 (uses provided 3)2. Keyword Arguments
Specify which value goes to which parameter. Order doesn’t matter here.
def describe_pet(animal_type, pet_name):
print(f"I have a {animal_type} named {pet_name}.")
describe_pet(pet_name="Bruno", animal_type="Dog")3. Arbitrary Arguments *args
Used when you don’t know how many positional arguments will be passed. Stores them as a tuple.
def total_sum(*numbers):
return sum(numbers)
print(total_sum(1, 2, 3, 4, 5)) 4. Arbitrary Keyword Arguments **kwargs
Used for unknown named arguments. Stores them as a dictionary.
def user_profile(**data):
for key, value in data.items():
print(f"{key}: {value}")
user_profile(username="coder_x", level="Admin")7. Function Scope – LEGB Rule
Scope determines where a variable is accessible. Python follows the LEGB rule:
- Local: Inside the function.
- Enclosing: Inside nested functions.
- Global: At the top level of the script.
- Built-in: Python’s internal names (like len).
8. Lambda Functions – Anonymous
For short, one-time-use logic.
- Syntax: lambda arguments : expression
square = lambda x: x * x
print(square(5)) # 259. Recursion
A function that calls itself to solve smaller pieces of a problem.
- Base Case: Necessary to stop the recursion (prevents RecursionError).
def factorial(n):
if n == 1: return 1 # Base Case
return n * factorial(n - 1)10. Advanced – Decorators
Decorators allow you to “wrap” another function to add extra behavior without changing its code.
def my_decorator(func):
def wrapper():
print("Starting task...")
func()
print("Task complete.")
return wrapper
@my_decorator
def say_hi():
print("Hi!")11. Generators and yield
Generators are memory efficient. Unlike return, yield pauses the function and saves its state to continue later.
def count_to_three():
yield 1
yield 2
yield 3
for num in count_to_three():
print(num)
| Concept | Key Keyword | Purpose |
| Standard Function | def | Logical encapsulation. |
| Data Output | return | Sending results back. |
| Default Arg | param=val | Handling missing inputs. |
| Variable Args | *args / **kwargs | Handling unknown number of inputs. |
| One-Liner | lambda | Quick, small logic. |
| Memory Saver | yield | Handling massive data streams. |
| Behavior Mod | @decorator | Adding logic to existing functions. |