Dunder or magic methods in Python
Python Magic methods are the methods starting and ending with double
underscores ‘__’. They are defined by built-in classes in Python and
commonly used for operator overloading.
They are also called Dunder methods, Dunder here means “Double Under
(Underscores)”.
Python Magic Methods
Built in classes define many magic methods, dir() function can show you
magic methods inherited by a class.
Example:
This code displays the magic methods inherited by int class.
# code
print(dir(int))
Output
['__abs__', '__add__', '__and__', '__bool__', '__ceil__', '__class__',
'__delattr__', '__dir__', '__divmod__', '__doc__', '__eq__', '__float__',
'__floor__', '__floordiv__', '__format__', '__ge__', '_...
Python Magic Methods
Below are the lists of Python magic methods and their uses.
Initialization and Construction
• __new__: To get called in an object’s instantiation.
• __init__: To get called by the __new__ method.
• __del__: It is the destructor.
Numeric magic methods
• __trunc__(self): Implements behavior for math.trunc()
• __ceil__(self): Implements behavior for math.ceil()
• __floor__(self): Implements behavior for math.floor()
• __round__(self,n): Implements behavior for the built-in round()
• __invert__(self): Implements behavior for inversion using the ~
operator.
• __abs__(self): Implements behavior for the built-in abs()
• __neg__(self): Implements behavior for negation
• __pos__(self): Implements behavior for unary positive
Arithmetic operators
• __add__(self, other): Implements behavior for the + operator
(addition).
• __sub__(self, other): Implements behavior for the – operator
(subtraction).
• __mul__(self, other): Implements behavior for the * operator
(multiplication).
• __floordiv__(self, other): Implements behavior for the // operator
(floor division).
• __truediv__(self, other): Implements behavior for the / operator (true
division).
• __mod__(self, other): Implements behavior for the % operator
(modulus).
• __divmod__(self, other): Implements behavior for the divmod()
function.
• __pow__(self, other): Implements behavior for the ** operator
(exponentiation).
• __lshift__(self, other): Implements behavior for the << operator (left
bitwise shift).
• __rshift__(self, other): Implements behavior for the >> operator (right
bitwise shift).
• __and__(self, other): Implements behavior for the & operator (bitwise
and).
• __or__(self, other): Implements behavior for the | operator (bitwise
or).
• __xor__(self, other): Implements behavior for the ^ operator (bitwise
xor).
• __invert__(self): Implements behavior for bitwise NOT using the ~
operator.
• __neg__(self): Implements behavior for negation using the – operator.
• __pos__(self): Implements behavior for unary positive using the +
operator.
String Magic Methods
• __str__(self): Defines behavior for when str() is called on an instance of
your class.
• __repr__(self): To get called by built-int repr() method to return a
machine readable representation of a type.
• __unicode__(self): This method to return an unicode string of a type.
• __format__(self, formatstr): return a new style of string.
• __hash__(self): It has to return an integer, and its result is used for
quick key comparison in dictionaries.
• __nonzero__(self): Defines behavior for when bool() is called on an
instance of your class.
• __dir__(self): This method to return a list of attributes of a class.
• __sizeof__(self): It return the size of the object.
Comparison magic methods
• __eq__(self, other): Defines behavior for the equality operator, ==.
• __ne__(self, other): Defines behavior for the inequality operator, !=.
• __lt__(self, other): Defines behavior for the less-than operator, <.
• __gt__(self, other): Defines behavior for the greater-than operator, >.
• __le__(self, other): Defines behavior for the less-than-or-equal-to
operator, <=.
• __ge__(self, other): Defines behavior for the greater-than-or-equal-to
operator, >=.
Dunder or Magic Methods in Python
Let’s see some of the Python magic methods with examples:
1. __init__ method
The __init__ method for initialization is invoked without any call, when an
instance of a class is created, like constructors in certain other programming
languages such as C++, Java, C#, PHP, etc.
These methods are the reason we can add two strings with the ‘+’ operator
without any explicit typecasting.
# declare our own string class
class String:
# magic method to initiate object
def __init__(self, string):
self.string = string
# Driver Code
if __name__ == '__main__':
# object creation
string1 = String('Hello')
# print object location
print(string1)
Output
<__main__.String object at 0x7f538c059050>
Awesome — you’re diving into Python’s magic (dunder) methods that
handle numeric operations
Let’s break each one down with simple examples to show what they do and
how to implement them.
1. __trunc__(self) – math.trunc()
Rounds a number towards zero (drops decimal part).
import math
class MyNumber:
def __init__(self, value):
self.value = value
def __trunc__(self):
return int(self.value)
x = MyNumber(5.9)
print(math.trunc(x)) # Output: 5
2. __ceil__(self) – math.ceil()
Rounds up to the nearest integer.
import math
class MyNumber:
def __init__(self, value):
self.value = value
def __ceil__(self):
return int(self.value) + (self.value % 1 > 0)
x = MyNumber(5.1)
print(math.ceil(x)) # Output: 6
3. __floor__(self) – math.floor()
Rounds down to the nearest integer.
import math
class MyNumber:
def __init__(self, value):
self.value = value
def __floor__(self):
return int(self.value)
x = MyNumber(5.9)
print(math.floor(x)) # Output: 5
4. __round__(self, n)
Defines behavior for round(obj, n).
class MyNumber:
def __init__(self, value):
self.value = value
def __round__(self, n=0):
return round(self.value, n)
x = MyNumber(5.6789)
print(round(x, 2)) # Output: 5.68
5. __invert__(self) – ~obj
Bitwise inversion (used with ~ operator).
class MyNumber:
def __init__(self, value):
self.value = value
def __invert__(self):
return ~self.value
x = MyNumber(5)
print(~x) # Output: -6
6. __abs__(self) – abs(obj)
Returns absolute value.
class MyNumber:
def __init__(self, value):
self.value = value
def __abs__(self):
return abs(self.value)
x = MyNumber(-7)
print(abs(x)) # Output: 7
7. __neg__(self) – -obj
Defines behavior for negation.
class MyNumber:
def __init__(self, value):
self.value = value
def __neg__(self):
return -self.value
x = MyNumber(10)
print(-x) # Output: -10
8. __pos__(self) – +obj
Defines behavior for unary plus.
class MyNumber:
def __init__(self, value):
self.value = value
def __pos__(self):
return +self.value
x = MyNumber(7)
print(+x) # Output: 7
Summary Table:
Method Triggered by Purpose
__trunc__ math.trunc(obj) Truncates decimal part
__ceil__ math.ceil(obj) Rounds up
__floor__ math.floor(obj) Rounds down
__round__ round(obj, n) Rounds to n decimal places
__invert__ ~obj Bitwise NOT
__abs__ abs(obj) Absolute value
__neg__ -obj Negation
__pos__ +obj Unary plus
Let me know if you want a combined class implementing all of these
together!
Absolutely! Let’s deep dive into lists in Python — one of the most powerful
and flexible data structures.
We’ll explore definition, properties, and all major operations with easy-to-
understand examples.
What is a List in Python?
A list is an ordered, mutable (changeable) collection of items.
my_list = [10, 20, 30, "Python", True]
Allows:
• Mixed data types
• Duplicates
• Nesting (lists inside lists)
Basic List Syntax
# Empty list
empty = []
# List with elements
fruits = ["apple", "banana", "cherry"]
Accessing Elements
fruits = ["apple", "banana", "cherry"]
print(fruits[0]) # apple
print(fruits[-1]) # cherry (last item)
List Operations (with Examples)
1. Add Items
fruits = ["apple", "banana"]
fruits.append("cherry") # Add at end
fruits.insert(1, "mango") # Add at specific index
fruits.extend(["kiwi", "grape"]) # Add multiple items
print(fruits)
# ['apple', 'mango', 'banana', 'cherry', 'kiwi', 'grape']
2. Remove Items
fruits = ["apple", "banana", "cherry", "banana"]
fruits.remove("banana") # Removes first 'banana'
fruits.pop() # Removes last item
fruits.pop(0) # Removes item at index 0
del fruits[0] # Deletes item at index 0
fruits.clear() # Empties the list
print(fruits)
3. Update Items
fruits = ["apple", "banana", "cherry"]
fruits[1] = "mango"
print(fruits) # ['apple', 'mango', 'cherry']
4. Searching
fruits = ["apple", "banana", "cherry"]
print("banana" in fruits) # True
print(fruits.index("banana")) # 1
print(fruits.count("banana")) # 1
5. Sorting and Reversing
nums = [3, 1, 4, 2]
nums.sort() # Ascending
nums.sort(reverse=True) # Descending
nums.reverse() # Reverse current order
print(nums)
6. Looping through a List
fruits = ["apple", "banana", "cherry"]
for fruit in fruits:
print(fruit)
# or
for i in range(len(fruits)):
print(fruits[i])
7. Slicing a List
nums = [10, 20, 30, 40, 50]
print(nums[1:4]) # [20, 30, 40]
print(nums[:3]) # [10, 20, 30]
print(nums[::-1]) # [50, 40, 30, 20, 10] (reverse)
8. Nested Lists
matrix = [
[1, 2],
[3, 4],
[5, 6]
]
print(matrix[1]) # [3, 4]
print(matrix[1][0]) # 3
Built-in List Functions
Function Description
append(x) Adds x at the end
extend(iter) Adds all items from iterable
insert(i, x) Inserts x at index i
remove(x) Removes first occurrence of x
pop([i]) Removes and returns item at index
clear() Removes all items
index(x) Returns first index of x
count(x) Counts occurrences of x
sort() Sorts the list
reverse() Reverses the list
copy() Returns a shallow copy
List Summary
• Mutable (can change contents)
• Ordered (items have index)
• Supports indexing, slicing, nesting
• Many built-in methods to manipulate
Sure! Let’s dive into working with numeric and string data in Python,
covering both basic and slightly advanced topics with examples.
Working with Numeric Data in Python
1. Types of Numeric Data
Python has three main numeric types:
• int → integers (e.g., 5, -10)
• float → floating-point numbers (e.g., 3.14, -2.5)
• complex → complex numbers (e.g., 3 + 2j)
x=5 # int
y = 3.14 # float
z = 2 + 3j # complex
2. Basic Arithmetic Operations
a = 10
b=3
print(a + b) # Addition → 13
print(a - b) # Subtraction → 7
print(a * b) # Multiplication → 30
print(a / b) # Division → 3.333...
print(a // b) # Floor division → 3
print(a % b) # Modulus → 1
print(a ** b) # Exponentiation → 1000
3. Built-in Functions
print(abs(-7)) #7
print(round(3.1415, 2)) # 3.14
print(pow(2, 3)) #8
4. Math Module
import math
print(math.sqrt(16)) # 4.0
print(math.factorial(5)) # 120
print(math.pi) # 3.141592...
Working with String Data in Python
1. Creating Strings
s1 = 'Hello'
s2 = "World"
s3 = '''Multiline
String'''
2. String Concatenation & Repetition
print(s1 + " " + s2) # Hello World
print(s1 * 3) # HelloHelloHello
3. Accessing Characters and Slicing
text = "Python"
print(text[0]) #P
print(text[-1]) #n
print(text[1:4]) # yth
4. String Methods
s = " hello PYTHON "
print(s.strip()) # "hello PYTHON"
print(s.lower()) # " hello python "
print(s.upper()) # " HELLO PYTHON "
print(s.replace("PYTHON", "World")) # " hello World "
print(s.split()) # ['hello', 'PYTHON']
5. Checking Content
name = "Alice123"
print(name.isalpha()) # False (contains numbers)
print(name.isdigit()) # False
print(name.isalnum()) # True (letters + digits)
print(name.startswith("A")) # True
print(name.endswith("3")) # True
6. f-Strings and Formatting
name = "Bob"
age = 25
print(f"My name is {name} and I'm {age} years old.")
7. String Length
text = "Data Science"
print(len(text)) # 12
Tip: Type Conversion Between Strings and Numbers
num = "100"
converted = int(num) + 5 # 105
stringified = str(105) + " apples" # "105 apples"
Absolutely! Let's dive deep into functions in Python — covering everything
from basics to advanced features with examples.
What is a Function?
A function is a block of code that performs a specific task and runs only
when called. Functions help you reuse code and organize logic efficiently.
1. Defining and Calling a Function
def greet():
print("Hello from the function!")
greet() # Calling the function
2. Parameters and Arguments
def greet(name): # 'name' is a parameter
print(f"Hello, {name}!")
greet("Alice") # "Alice" is an argument
greet("Bob")
3. Return Statement
Functions can return values using return.
def add(a, b):
return a + b
result = add(3, 5)
print(result) # 8
4. Default Parameters
You can assign default values to parameters.
def greet(name="Guest"):
print(f"Hello, {name}!")
greet() # Hello, Guest
greet("Sam") # Hello, Sam
5. Multiple Return Values
def get_stats(numbers):
return min(numbers), max(numbers), sum(numbers)
low, high, total = get_stats([1, 2, 3])
print(low, high, total) # 1 3 6
6. Arbitrary Arguments
Use *args for any number of positional arguments:
def total(*args):
return sum(args)
print(total(1, 2, 3)) #6
print(total(10, 20, 30, 40)) # 100
Use **kwargs for any number of keyword arguments:
def describe_person(**kwargs):
for key, value in kwargs.items():
print(f"{key}: {value}")
describe_person(name="Alice", age=30)
7. Lambda Functions (Anonymous Functions)
Useful for short, one-line functions.
square = lambda x: x * x
print(square(5)) # 25
add = lambda a, b: a + b
print(add(3, 7)) # 10
8. Nested Functions
You can define functions inside other functions.
def outer():
def inner():
print("Inside inner function")
inner()
outer()
9. Recursion
A function calling itself.
def factorial(n):
if n == 0:
return 1
return n * factorial(n - 1)
print(factorial(5)) # 120
10. Docstrings (Documentation Strings)
You can document your functions like this:
def greet(name):
"""This function greets the person by name."""
print(f"Hello, {name}!")
print(greet.__doc__)
11. Type Hints (Optional)
def add(a: int, b: int) -> int:
return a + b
12. Higher-Order Functions
Functions that take other functions as arguments or return them.
def apply(func, value):
return func(value)
def double(x):
return x * 2
print(apply(double, 4)) # 8
Quick Summary:
Feature Keyword / Usage
Define a function def
Return value return
Default argument def f(x=5)
Variable args *args, **kwargs
Anonymous function lambda
Type hints def f(x: int) -> int:
Would you like to go deeper into any specific part (like recursion, lambda,
decorators, etc.) or get practice problems on functions?
Awesome! Let’s break down three core programming concepts in Python:
1. Boolean Expressions
2. Selection Structures (if-else)
3. Iteration Structures (loops)
We’ll explore each with definitions, syntax, examples, and tips.
1. Boolean Expressions in Python
What is a Boolean?
A Boolean expression evaluates to either True or False.
Boolean Values:
True
False
Comparison Operators:
Operator Meaning Example
== Equal to x == 5
!= Not equal to x != 3
> Greater than x > 10
< Less than x<4
>= Greater or equal x >= 8
<= Less or equal x <= 6
Logical Operators:
Operator Meaning
and True if both are True
or True if at least one is True
not Inverts the Boolean value
a=5
b = 10
print(a > 0 and b > 0) # True
print(a > 10 or b == 10) # True
print(not a > 10) # True
2. Selection Structure (Decision Making)
The if Statement
age = 18
if age >= 18:
print("You're an adult.")
The if-else Statement
if age >= 18:
print("You can vote.")
else:
print("You can't vote yet.")
The if-elif-else Statement
score = 75
if score >= 90:
print("Grade: A")
elif score >= 80:
print("Grade: B")
elif score >= 70:
print("Grade: C")
else:
print("Grade: F")
Short-hand if
x=5
y = 10
print("x is greater") if x > y else print("y is greater")
3. Iteration Structure (Loops)
Python supports two primary loops: for and while.
for Loop
Used for iterating over a sequence (like a list, string, or range).
for i in range(5): # 0 to 4
print(i)
Example with a List:
fruits = ["apple", "banana", "cherry"]
for fruit in fruits:
print(fruit)
Nested Loop:
for i in range(2):
for j in range(3):
print(f"i={i}, j={j}")
while Loop
Used when the number of iterations is not known in advance.
count = 0
while count < 5:
print(count)
count += 1
break, continue, and pass
• break → Exits the loop
• continue → Skips current iteration
• pass → Placeholder (does nothing)
for i in range(5):
if i == 3:
break
print(i) # 0, 1, 2
for i in range(5):
if i == 2:
continue
print(i) # 0, 1, 3, 4
for i in range(3):
pass # used to write later
Summary Table
Concept Description
Boolean Expression Evaluates to True or False
if, elif, else Decision-making based on conditions
for loop Loop over a sequence (list, range, string, etc.)
while loop Loop while a condition is True
break Exit loop early
continue Skip current loop iteration
pass Placeholder for future code
Great! Let's explore working with lists in Python in detail. Lists are ordered,
mutable (changeable), and allow duplicates, making them one of the most
commonly used data structures in Python.
1. Creating a List
# List of integers
numbers = [1, 2, 3, 4, 5]
# List of mixed data types
mixed = [1, "apple", True, 3.14]
# Empty list
empty = []
2. Accessing Elements
fruits = ["apple", "banana", "cherry"]
print(fruits[0]) # apple
print(fruits[-1]) # cherry (last item)
print(fruits[1:]) # ['banana', 'cherry']
3. Modifying Lists
Change Item:
fruits[1] = "blueberry"
print(fruits) # ['apple', 'blueberry', 'cherry']
Add Items:
fruits.append("orange") # Add to end
fruits.insert(1, "kiwi") # Add at index 1
print(fruits)
Extend List:
more_fruits = ["mango", "grape"]
fruits.extend(more_fruits)
4. Removing Items
fruits.remove("banana") # Removes first occurrence
fruits.pop() # Removes last item
fruits.pop(0) # Removes item at index 0
del fruits[1] # Deletes item at index 1
fruits.clear() # Empties the list
5. Looping Through a List
for fruit in fruits:
print(fruit)
# Using index
for i in range(len(fruits)):
print(fruits[i])
6. List Functions and Methods
Length, Sorting, Reversing:
numbers = [4, 2, 7, 1]
print(len(numbers)) #4
numbers.sort() # [1, 2, 4, 7]
numbers.reverse() # [7, 4, 2, 1]
Other Useful Methods:
Method Description
append() Add single item
extend() Add multiple items
insert() Insert item at specific position
remove() Remove specific item
pop() Remove item at given position or last
clear() Remove all items
index() Get index of item
Method Description
count() Count occurrences
sort() Sort list
reverse() Reverse list
copy() Returns a shallow copy
nums = [1, 2, 2, 3]
print(nums.count(2)) # 2
print(nums.index(3)) # 3
7. List Comprehensions (Short, elegant way to create lists)
squares = [x**2 for x in range(5)] # [0, 1, 4, 9, 16]
even = [x for x in range(10) if x % 2 == 0]
8. Copying Lists
a = [1, 2, 3]
b = a.copy()
# or
b = list(a)
# or
b = a[:]
Avoid doing: b = a (this creates a reference, not a copy)
9. Nested Lists
matrix = [[1, 2], [3, 4]]
print(matrix[0]) # [1, 2]
print(matrix[0][1]) # 2
10. Membership Testing & Iteration
if "apple" in fruits:
print("Found apple!")
for i, fruit in enumerate(fruits):
print(i, fruit)
Summary Table:
Task Example
Create list l = [1, 2, 3]
Access item l[0]
Slice list l[1:3]
Add item l.append(4)
Insert item l.insert(1, 10)
Task Example
Remove item l.remove(2)
Loop over list for x in l:
List comprehension [x**2 for x in range(5)]
Would you like to move on to tuples, sets, or dictionaries next, or see mini-
projects that use lists (like to-do apps, menu systems, etc.)?
Perfect! Let’s dive into working with a list of lists in Python — often referred
to as a 2D list or matrix. This is useful for representing grids, tables,
matrices, or any nested data.
1. What is a List of Lists?
A list of lists is simply a list where each element is itself a list.
matrix = [
[1, 2, 3],
[4, 5, 6],
[7, 8, 9]
]
2. Accessing Elements
print(matrix[0]) # [1, 2, 3] → first row
print(matrix[1][2]) # 6 → second row, third column
print(matrix[-1][0]) # 7 → last row, first column
3. Looping Through a List of Lists
a) Loop by Rows
for row in matrix:
print(row)
b) Loop by Rows and Columns
for row in matrix:
for item in row:
print(item, end=' ')
print()
c) With Indexes
for i in range(len(matrix)):
for j in range(len(matrix[i])):
print(f"matrix[{i}][{j}] = {matrix[i][j]}")
4. Modifying Elements
matrix[0][0] = 10
print(matrix[0]) # [10, 2, 3]
5. Adding Rows and Columns
Add a new row:
matrix.append([10, 11, 12])
Add a new column:
for row in matrix:
row.append(0)
6. Removing Rows and Columns
Remove a row:
del matrix[2] # Deletes 3rd row
Remove a column:
for row in matrix:
del row[1] # Deletes 2nd column
7. List Comprehension with List of Lists
# Create 3x3 matrix with all zeroes
zero_matrix = [[0 for _ in range(3)] for _ in range(3)]
# Multiply each value by 2
doubled = [[item * 2 for item in row] for row in matrix]
8. Common Use Cases
a) Sum of all elements
total = 0
for row in matrix:
total += sum(row)
b) Transposing a Matrix
(Switch rows with columns)
transposed = [[row[i] for row in matrix] for i in range(len(matrix[0]))]
9. Useful Functions
Task Code Example
Length of outer list len(matrix)
Length of row len(matrix[0])
Flatten 2D list [item for row in matrix for item in row]
All zeros 4x3 [[0]*3 for _ in range(4)]
10. Real Example: Student Marks Table
students = [
["Alice", 85, 90, 88],
["Bob", 78, 80, 85],
["Charlie", 92, 88, 91]
]
for student in students:
name = student[0]
scores = student[1:]
avg = sum(scores) / len(scores)
print(f"{name}'s average score: {avg}")
Bonus: Pretty Printing
for row in matrix:
print(' '.join(str(x) for x in row))
Would you like to explore matrix operations (like multiplication, diagonal
elements), or see real projects using list of lists (like a Sudoku board or Tic-
Tac-Toe game)?
Working with dates and times is super useful in Python — whether you’re
building reminders, event logs, or just formatting output.
Let’s break it down using the built-in datetime module (plus a bit of time and
calendar if needed).
1. Importing datetime module
import datetime
2. Getting Current Date and Time
from datetime import datetime
now = datetime.now()
print(now) # Full date & time
print(now.date()) # Just the date
print(now.time()) # Just the time
Attributes:
print(now.year)
print(now.month)
print(now.day)
print(now.hour)
print(now.minute)
print(now.second)
3. Creating Specific Dates and Times
from datetime import datetime
birthday = datetime(2000, 12, 15, 10, 30, 0)
print(birthday)
4. Formatting Dates (strftime)
Use .strftime() to convert date/time to a string format.
now = datetime.now()
print(now.strftime("%Y-%m-%d")) # 2025-04-22
print(now.strftime("%d/%m/%Y")) # 22/04/2025
print(now.strftime("%A, %B %d")) # Tuesday, April 22
Common Format Codes:
Code Meaning Example
%Y Year (4 digits) 2025
%y Year (2 digits) 25
%m Month (01–12) 04
%d Day (01–31) 22
%H Hour (00–23) 13
%I Hour (01–12) 01
%p AM/PM PM
%M Minute (00–59) 45
%S Second (00–59) 30
%A Weekday name Tuesday
%B Month name April
5. Parsing Date Strings (strptime)
Use .strptime() to convert a string into a datetime object.
from datetime import datetime
date_str = "22/04/2025"
parsed = datetime.strptime(date_str, "%d/%m/%Y")
print(parsed) # 2025-04-22 00:00:00
6. Working with timedelta (Date Arithmetic)
from datetime import timedelta, datetime
today = datetime.now()
one_week = timedelta(weeks=1)
future_date = today + one_week
past_date = today - timedelta(days=30)
print(future_date)
print(past_date)
7. Difference Between Two Dates
date1 = datetime(2025, 5, 1)
date2 = datetime(2025, 4, 22)
difference = date1 - date2
print(difference.days) # 9 days
print(difference.total_seconds()) # Seconds
8. Calendar Module (Optional)
import calendar
print(calendar.month(2025, 4))
print(calendar.isleap(2025)) # False
9. time Module (Optional)
import time
print(time.time()) # Seconds since 1970
print(time.ctime()) # Current time as string
10. Sleep / Delay
import time
print("Wait for 3 seconds...")
time.sleep(3)
print("Done!")
Summary
Task Tool / Method
Current datetime datetime.now()
Current date .date()
Format datetime .strftime("%Y-%m-%d")
Parse from string datetime.strptime()
Add/Subtract days timedelta(days=...)
Difference between dates date1 - date2
Pause execution time.sleep(seconds)
Bonus: Date of the Week
today = datetime.now()
print(today.strftime("%A")) # e.g. "Tuesday"
Want practice problems, mini-projects (like a countdown timer or reminder
tool), or more advanced date-time tasks (like timezone handling)?
Let's break down dictionaries in Python in full detail — they're powerful,
flexible, and super useful for managing key-value pairs (like JSON or
database records).
1. What is a Dictionary?
A dictionary is an unordered, mutable, indexed collection that stores data in
key: value pairs.
person = {
"name": "Alice",
"age": 25,
"city": "New York"
}
Keys must be unique and immutable (strings, numbers, tuples)
2. Accessing Dictionary Values
print(person["name"]) # Alice
Using .get() method (safe way):
print(person.get("age")) # 25
print(person.get("gender", "N/A")) # N/A if key not found
3. Adding or Updating Values
# Add a new key-value pair
person["email"] = "
[email protected]"
# Update value
person["age"] = 26
4. Removing Items
person.pop("city") # Removes key 'city'
del person["age"] # Another way to remove
person.clear() # Empties the dictionary
5. Looping Through a Dictionary
# Loop through keys
for key in person:
print(key, person[key])
# Loop through key-value pairs
for key, value in person.items():
print(f"{key}: {value}")
6. Dictionary Methods
Method Description
dict.get(k) Get value of key k, return None if missing
dict.keys() Return all keys
dict.values() Return all values
Method Description
dict.items() Return (key, value) pairs
dict.pop(k) Remove key k and return its value
dict.clear() Remove all items
dict.update() Merge another dict into this one
dict.copy() Returns a shallow copy
print(person.keys()) # dict_keys(['name', 'email'])
print(person.values()) # dict_values(['Alice', '
[email protected]'])
print(person.items()) # dict_items([('name', 'Alice'), ('email',
'
[email protected]')])
7. Creating Dictionaries
a) From Scratch
car = {"brand": "Toyota", "year": 2022}
b) Using dict() constructor
car = dict(brand="Toyota", year=2022)
c) From a list of tuples
pairs = [("a", 1), ("b", 2)]
d = dict(pairs)
8. Nested Dictionaries
students = {
"101": {"name": "Alice", "score": 85},
"102": {"name": "Bob", "score": 90}
}
print(students["101"]["score"]) # 85
9. Dictionary Comprehensions
squares = {x: x*x for x in range(1, 6)}
# Output: {1: 1, 2: 4, 3: 9, 4: 16, 5: 25}
10. Checking Key/Value Existence
if "name" in person:
print("Key exists!")
if "Alice" in person.values():
print("Value exists!")
11. Merging Dictionaries (Python 3.9+)
a = {"x": 1, "y": 2}
b = {"y": 3, "z": 4}
merged = a | b # {'x': 1, 'y': 3, 'z': 4}
Quick Summary Table
Feature Syntax Example
Create d = {"a": 1, "b": 2}
Access d["a"] or d.get("a")
Add/Update d["c"] = 3
Delete d.pop("a"), del d["b"], d.clear()
Keys/Values d.keys(), d.values(), d.items()
Loop for k, v in d.items():
Check key "a" in d
Comprehension {k: k*k for k in range(5)}
Nested Access d["key"]["subkey"]
Merge (3.9+) `d3 = d1
Would you like to practice this with mini-projects? (like a student grade
tracker, phonebook, or JSON-like data reader)?
Let’s dive deep into Tuples in Python — what they are, how to use them, and
why they’re awesome. Tuples are like lists, but immutable, meaning once
created, they can’t be changed.
1. What is a Tuple?
A tuple is an ordered, immutable, indexed collection that can hold multiple
items.
my_tuple = (1, 2, 3)
Tuples can contain different data types:
mixed = (1, "hello", True, 3.14)
2. Creating Tuples
# Normal tuple
t = (1, 2, 3)
# Tuple without parentheses (tuple packing)
t = 1, 2, 3
# Single-element tuple (must have a comma)
t = (5,) # tuple
t = (5) # just an int
# Empty tuple
t = ()
3. Accessing Tuple Elements
t = (10, 20, 30, 40)
print(t[0]) # 10
print(t[-1]) # 40
print(t[1:3]) # (20, 30)
4. Immutability of Tuples
Tuples cannot be changed after creation:
t[0] = 100 # Error: 'tuple' object does not support item assignment
5. Looping Through Tuples
t = ("apple", "banana", "cherry")
for item in t:
print(item)
6. Tuple Operations
Operation Example Result
Concatenation (1, 2) + (3, 4) (1, 2, 3, 4)
Repetition ("a",) * 3 ("a", "a", "a")
Membership "a" in ("a", "b") True
Length len((1, 2, 3)) 3
Operation Example Result
Index t.index("apple") Position of "apple"
Count t.count("banana") Number of times it appears
7. Tuple Methods
Tuples only have two methods:
t = (1, 2, 2, 3)
print(t.count(2)) # 2
print(t.index(3)) # 3
8. When to Use Tuples
Use Case Why Tuples?
Fixed data No accidental modifications
Faster than lists Less memory & immutable
Dictionary keys Only immutable types allowed
Multiple return values from funcs Easy to unpack
9. Tuple Packing and Unpacking
# Packing
point = (4, 5)
# Unpacking
x, y = point
print(x, y) # 4 5
You can also unpack in loops:
pairs = [(1, 'a'), (2, 'b'), (3, 'c')]
for num, letter in pairs:
print(num, letter)
10. Nested Tuples
nested = ((1, 2), (3, 4))
print(nested[0][1]) # 2
11. Convert Between List and Tuple
# List → Tuple
my_list = [1, 2, 3]
my_tuple = tuple(my_list)
# Tuple → List
my_list = list(my_tuple)
Summary Table
Feature Tuple Example Note
Create t = (1, 2) Fixed-size, immutable
Access t[0], t[-1] Supports indexing/slicing
Unpack a, b = t Tuple unpacking
Loop for x in t: Easy to iterate
Convert list(t) or tuple(l) List ↔ Tuple
Use in dict d[(x, y)] = value Valid as keys if immutable
Example Use Case: Returning Multiple Values
def get_stats(nums):
return (min(nums), max(nums), sum(nums)/len(nums))
stats = get_stats([10, 20, 30])
print(stats) # (10, 30, 20.0)
Want to try small tuple-based problems (like coordinate manipulation, or
student record handling)?