Python strings, dictionaries, sets, files, and OOP essentials
String operations
Length, slicing, search, replace, count vowels
s = "Hello, Python!"
# Length
length = len(s) # 14
# Slicing
first_five = s[:5] # 'Hello'
last_six = s[-6:] # 'Python!'
every_second = s[::2] # 'Hlo yhn'
# Search (membership testing)
has_py = "Py" in s # True
has_java = "Java" in s # False
# Replace
replaced = [Link]("Python", "World") # 'Hello, World!'
# Count vowels (case-insensitive)
vowels = set("aeiou")
count = sum(1 for ch in [Link]() if ch in vowels) # 4
print(length, first_five, last_six, has_py, replaced, count)
• Tip: Use .find() or .index() for positions. .find() returns -1 if not found; .index() raises
ValueError.
Dictionaries for student records
Store and retrieve records
# Dictionary of student records keyed by roll number
students = {
101: {"name": "Asha", "dept": "CSE", "gpa": 8.7},
102: {"name": "Ravi", "dept": "ECE", "gpa": 7.9},
# Retrieve
roll = 101
record = [Link](roll) # Safe retrieval; returns None if missing
print(record) # {'name': 'Asha', 'dept': 'CSE', 'gpa': 8.7}
# Insert / update
students[103] = {"name": "Meera", "dept": "ME", "gpa": 8.2}
students[102]["gpa"] = 8.1
# Iterate
for roll_no, info in [Link]():
print(f"{roll_no}: {info['name']} ({info['dept']}) -> GPA {info['gpa']}")
• Key design: Use roll numbers or unique IDs as keys for O(1) lookups.
Set operations
Union, intersection, difference, membership
cs = {"Asha", "Ravi", "Meera"}
math = {"Ravi", "Imran", "Leena"}
# Membership
is_member = "Asha" in cs # True
# Union (either)
either = cs | math # {'Asha', 'Ravi', 'Meera', 'Imran', 'Leena'}
# Intersection (both)
both = cs & math # {'Ravi'}
# Difference (in cs not in math)
only_cs = cs - math # {'Asha', 'Meera'}
# Symmetric difference (either but not both)
xor = cs ^ math # {'Asha', 'Meera', 'Imran', 'Leena'}
print(is_member, either, both, only_cs, xor)
• Use case: Fast membership tests, removing duplicates, and set algebra.
File operations with exceptions
Read and write a text file; count words and lines
def write_sample(path, lines):
try:
with open(path, "w", encoding="utf-8") as f:
for line in lines:
[Link](line + "\n")
except OSError as e:
print(f"Failed to write: {e}")
def read_and_counts(path):
try:
with open(path, "r", encoding="utf-8") as f:
text = [Link]()
words = [Link]()
lines = [Link]()
return {"words": len(words), "lines": len(lines)}
except FileNotFoundError:
print("File not found.")
except UnicodeDecodeError:
print("Encoding error while reading.")
except OSError as e:
print(f"I/O error: {e}")
return None
sample_lines = ["Hello world", "Python file I/O", "Count words and lines"]
path = "[Link]"
write_sample(path, sample_lines)
counts = read_and_counts(path)
print(counts) # {'words': 7, 'lines': 3}
Read line by line and handle input processing errors
def sum_integers_file(path):
total = 0
try:
with open(path, "r", encoding="utf-8") as f:
for i, line in enumerate(f, start=1):
line = [Link]()
if not line:
continue
try:
total += int(line)
except ValueError:
print(f"Skipping non-integer on line {i}: {line}")
return total
except OSError as e:
print(f"Error opening file: {e}")
return None
• Best practice: Use with open(...) for automatic closing. Catch specific exceptions first,
then general ones.
Basic object-oriented programming
Student class: attributes and methods
class Student:
def __init__(self, roll_no, name, dept, grades=None):
self.roll_no = roll_no
[Link] = name
[Link] = dept
[Link] = grades or [] # list of numbers
def add_grade(self, score):
if not isinstance(score, (int, float)):
raise TypeError("Score must be a number")
if score < 0 or score > 100:
raise ValueError("Score must be between 0 and 100")
[Link](score)
def gpa(self):
if not [Link]:
return 0.0
# Simple 10-point scale
return round(sum([Link]) / len([Link]) / 10, 2)
def info(self):
return f"{self.roll_no} - {[Link]} ({[Link]}), GPA: {[Link]()}"
# Create instances, access attributes, invoke methods
s1 = Student(101, "Asha", "CSE", [85, 90, 78])
s2 = Student(102, "Ravi", "ECE")
s2.add_grade(88)
s2.add_grade(76)
print([Link], [Link]) # Access attributes
print([Link]()) # Invoke method
print([Link]())
• Encapsulation: Validate data in methods; expose clean interfaces like add_grade() and
gpa().
Inheritance, overriding, and polymorphism
Inheritance and method overriding
class GraduateStudent(Student):
def __init__(self, roll_no, name, dept, advisor, thesis_title=None, grades=None):
super().__init__(roll_no, name, dept, grades)
[Link] = advisor
self.thesis_title = thesis_title
# Override info to include advisor
def info(self):
base = super().info()
extra = f" | Advisor: {[Link]}"
if self.thesis_title:
extra += f" | Thesis: {self.thesis_title}"
return base + extra
gs = GraduateStudent(201, "Meera", "CSE", advisor="Dr. Sen", thesis_title="ML for Healthcare",
grades=[92, 88, 95])
print([Link]())
Polymorphism via overriding (same interface, different behavior)
def print_student_card(student_obj):
# Works for Student or GraduateStudent because both implement info()
print(student_obj.info())
print_student_card(s1) # Uses [Link]
print_student_card(gs) # Uses [Link]
Simulated method overloading using default args and type checks
class Calculator:
def add(self, a, b=0):
# If b not given, treat as unary add-to-total
return a + b
calc = Calculator()
print([Link](5)) # 5 (interpreted as unary)
print([Link](5, 7)) # 12
• Note: Python doesn’t have true method overloading by signature; use default
parameters, *args, or [Link].
Quick practice tasks
• Strings: Write a function that returns the number of consonants in a sentence.
• Dictionaries: Add a function to search students by department and return average GPA.
• Sets: Given two course lists, return students who take exactly one of them.
• Files: Build a CLI script that reads a path, counts words, and prints the top 5 most
frequent.
• OOP: Extend Student to include attendance and compute an eligibility status.
If you want, tell me your syllabus or preferred difficulty, and I’ll turn this into exercises with
solutions.