Python Tutorial

Python is an easy-to-learn, general-purpose programming language used for web development, data science, AI, automation, scripting, and more. It prioritizes readability with its clean, indentation-based syntax.

What is Python?

  • Created by Guido van Rossum, released in 1991.
  • Current version: Python 3.x (Python 2 is end-of-life).
  • Interpreted, dynamically typed, multi-paradigm.
  • Popular for: web (Django, Flask, FastAPI), ML/AI (TensorFlow, PyTorch, scikit-learn), automation, scripting.
Python
# Hello World - Python
print("Hello, World!")

# Run script
# python3 hello.py

# Python version
import sys
print(sys.version)
► Try It Yourself

Syntax & Comments

Python
# This is a single-line comment

"""
This is a
multi-line docstring (triple quotes)
"""

# Python uses INDENTATION (4 spaces) for blocks - no braces {}
if True:
    print("Indented block")
    if True:
        print("Nested block")

# Semicolons are optional (not recommended)
a = 1; b = 2

# Line continuation
total = 1 + 2 + 3 + \
        4 + 5

# Multiple assignment
x, y, z = 1, 2, 3
a = b = c = 0
► Try It Yourself

Variables

Python
# No declaration keyword needed
name = "Alice"
age = 25
height = 5.9
is_admin = True

# Dynamic typing
x = 10
x = "now a string"  # OK in Python

# Type hints (optional, Python 3.5+)
def greet(name: str) -> str:
    return f"Hello, {name}"

# Check type
type(name)    # <class 'str'>
type(age)     # <class 'int'>
isinstance(age, int)  # True

# Constants (convention: UPPER_CASE - not enforced)
MAX_SIZE = 100
PI = 3.14159

# Delete variable
del x
► Try It Yourself

Data Types

TypeExampleMutable?
int42, -7, 0No
float3.14, -0.5, 2e10No
complex3+4jNo
str"hello", 'world'No
boolTrue, FalseNo
list[1, 2, 3]Yes
tuple(1, 2, 3)No
set{1, 2, 3}Yes
dict{"key": "value"}Yes
NoneNone-
bytesb"hello"No
Python
# Type conversion
int("42")        # 42
float("3.14")    # 3.14
str(42)          # "42"
bool(0)          # False
list("abc")      # ['a', 'b', 'c']
tuple([1, 2])    # (1, 2)
set([1, 1, 2])   # {1, 2}
► Try It Yourself

Strings

Python
s = "Hello, World!"

len(s)             # 13
s.upper()          # "HELLO, WORLD!"
s.lower()          # "hello, world!"
s.title()          # "Hello, World!"
s.strip()          # remove whitespace
s.lstrip(" ")      # left strip
s.rstrip("!")      # right strip
s.replace("World", "Python")  # "Hello, Python!"
s.split(", ")      # ['Hello', 'World!']
", ".join(["a","b","c"])  # "a, b, c"
s.find("World")    # 7
s.startswith("He") # True
s.endswith("!")    # True
s.count("l")       # 3
s.isdigit()        # False
s.isalpha()        # False
s.isalnum()        # False

# Slicing: s[start:stop:step]
s[0:5]    # "Hello"
s[-6:]    # "orld!"
s[::-1]   # reverse: "!dlroW ,olleH"
s[::2]    # every 2nd char

# f-strings (Python 3.6+) - preferred
name, age = "Alice", 25
msg = f"Name: {name}, Age: {age}, Born: {2025 - age}"
msg = f"Pi: {3.14159:.2f}"   # format specifier

# Other string formatting
"Hello, {}!".format("World")
"Hello, %s!" % "World"

# Raw string (no escape processing)
path = r"C:\Users\name\file.txt"

# Multi-line
text = """
Line 1
Line 2
"""
► Try It Yourself

Lists

Python
fruits = ["apple", "banana", "cherry"]

# Access
fruits[0]        # "apple"
fruits[-1]       # "cherry"
fruits[1:3]      # ["banana", "cherry"]

# Modify
fruits.append("date")       # add to end
fruits.insert(1, "avocado") # insert at index
fruits.extend(["elderberry", "fig"])
fruits.remove("banana")     # remove by value
fruits.pop()                # remove and return last
fruits.pop(1)               # remove at index
fruits.clear()              # empty list

# Searching
"apple" in fruits           # True
fruits.index("cherry")      # 2
fruits.count("apple")       # 1

# Sorting
fruits.sort()               # in-place (ascending)
fruits.sort(reverse=True)   # descending
fruits.sort(key=len)        # by string length
sorted_copy = sorted(fruits) # returns new list
fruits.reverse()

# Copy
copy = fruits.copy()        # shallow copy
copy = fruits[:]            # slice copy

# List operations
[1, 2] + [3, 4]  # [1, 2, 3, 4]
[0] * 5          # [0, 0, 0, 0, 0]
len(fruits)      # length
min([1,3,2])     # 1
max([1,3,2])     # 3
sum([1,2,3])     # 6
list(range(5))   # [0, 1, 2, 3, 4]
list(range(1, 6, 2)) # [1, 3, 5]

# Unpacking
a, b, *rest = [1, 2, 3, 4, 5]
# a=1, b=2, rest=[3,4,5]
► Try It Yourself

Dictionaries

Python
person = {
    "name": "Alice",
    "age": 25,
    "hobbies": ["coding", "reading"]
}

# Access
person["name"]           # "Alice"
person.get("email")      # None (no error)
person.get("email", "N/A") # "N/A" default

# Modify
person["age"] = 26
person["email"] = "alice@example.com"
del person["age"]
person.pop("age")        # remove and return

# Check key
"name" in person         # True

# Iterate
for key in person:                     print(key)
for key, val in person.items():        print(key, val)
for key in person.keys():              print(key)
for val in person.values():            print(val)

# Merge (Python 3.9+)
merged = person | {"role": "admin"}

# Dictionary methods
person.keys()    # dict_keys([...])
person.values()  # dict_values([...])
person.items()   # dict_items([(...)])
person.update({"age": 26, "city": "Mumbai"})
person.setdefault("country", "India")  # add if missing

# Dict comprehension
squares = {n: n**2 for n in range(1, 6)}
# {1:1, 2:4, 3:9, 4:16, 5:25}
► Try It Yourself

Functions

Python
def greet(name, greeting="Hello"):
    """Greet a person by name."""
    return f"{greeting}, {name}!"

greet("Alice")           # "Hello, Alice!"
greet("Bob", "Hi")       # "Hi, Bob!"
greet(name="Carol", greeting="Hey")  # keyword args

# *args (variable positional args)
def add(*nums):
    return sum(nums)
add(1, 2, 3, 4)  # 10

# **kwargs (variable keyword args)
def info(**kwargs):
    for key, val in kwargs.items():
        print(f"{key}: {val}")
info(name="Alice", age=25)

# Combined
def func(pos, *args, keyword=True, **kwargs):
    pass

# Return multiple values
def minmax(lst):
    return min(lst), max(lst)
lo, hi = minmax([3, 1, 4, 1, 5])

# First-class functions
def apply(func, value):
    return func(value)
apply(str.upper, "hello")  # "HELLO"
► Try It Yourself

Comprehensions

Python
# List comprehension
squares = [x**2 for x in range(10)]
evens   = [x for x in range(20) if x % 2 == 0]
words   = [w.upper() for w in ["hello", "world"]]

# Nested
matrix = [[i * j for j in range(1, 4)] for i in range(1, 4)]

# Dict comprehension
inv = {v: k for k, v in {"a": 1, "b": 2}.items()}

# Set comprehension
unique_lengths = {len(w) for w in ["hi", "hello", "hey"]}

# Generator expression (lazy evaluation - memory efficient)
gen = (x**2 for x in range(1000000))
next(gen)  # 0
sum(x for x in range(100))  # 4950
► Try It Yourself

Classes & OOP

Python
class Animal:
    # Class variable (shared)
    kingdom = "Animalia"

    def __init__(self, name, sound):
        self.name  = name   # instance variable
        self.sound = sound

    def speak(self):
        return f"{self.name} says {self.sound}"

    def __repr__(self):
        return f"Animal(name={self.name!r})"

    @classmethod
    def from_dict(cls, data):
        return cls(data["name"], data["sound"])

    @staticmethod
    def breathes(): return True

class Dog(Animal):  # inheritance
    def __init__(self, name, breed):
        super().__init__(name, "Woof")
        self.breed = breed

    def speak(self):     # override
        return super().speak() + " *wags tail*"

    def fetch(self):
        return f"{self.name} fetches the ball!"

rex = Dog("Rex", "Labrador")
rex.speak()          # "Rex says Woof *wags tail*"
isinstance(rex, Dog)    # True
isinstance(rex, Animal) # True

# Dunder (magic) methods
class Vector:
    def __init__(self, x, y):
        self.x, self.y = x, y
    def __add__(self, o): return Vector(self.x+o.x, self.y+o.y)
    def __str__(self):    return f"({self.x}, {self.y})"
    def __len__(self):    return 2
    def __eq__(self, o):  return self.x==o.x and self.y==o.y
► Try It Yourself

Exception Handling

Python
try:
    result = 10 / 0
except ZeroDivisionError:
    print("Cannot divide by zero!")
except (TypeError, ValueError) as e:
    print(f"Type or value error: {e}")
except Exception as e:
    print(f"Unexpected error: {e}")
else:
    print("No exception occurred")  # runs if no exception
finally:
    print("Always runs (cleanup)")   # always runs

# Raise exceptions
def validate_age(age):
    if not isinstance(age, int):
        raise TypeError("Age must be an integer")
    if age < 0 or age > 150:
        raise ValueError(f"Invalid age: {age}")
    return age

# Custom exception
class DatabaseError(Exception):
    def __init__(self, message, code=None):
        super().__init__(message)
        self.code = code

raise DatabaseError("Connection failed", code=503)

# Context managers (with statement)
with open("file.txt", "r") as f:
    content = f.read()
# file automatically closed after block
► Try It Yourself

File I/O

Python
# Read file
with open("data.txt", "r", encoding="utf-8") as f:
    content = f.read()           # entire file as string
    # or
    lines = f.readlines()        # list of lines
    # or
    for line in f:               # iterate line by line
        print(line.strip())

# Write file (overwrites)
with open("output.txt", "w", encoding="utf-8") as f:
    f.write("Hello, File!\n")
    f.writelines(["line1\n", "line2\n"])

# Append to file
with open("log.txt", "a") as f:
    f.write("New log entry\n")

# JSON
import json
data = {"name": "Alice", "age": 25}

# Write JSON
with open("data.json", "w") as f:
    json.dump(data, f, indent=2)

# Read JSON
with open("data.json") as f:
    loaded = json.load(f)

# JSON string
json_str = json.dumps(data, indent=2)
parsed   = json.loads(json_str)

# CSV
import csv
with open("data.csv", "w", newline="") as f:
    writer = csv.DictWriter(f, fieldnames=["name","age"])
    writer.writeheader()
    writer.writerow({"name": "Alice", "age": 25})
► Try It Yourself
Tip: Use pathlib.Path for modern file path handling: from pathlib import Path; p = Path("folder") / "file.txt"

Virtual Environments

A virtual environment isolates project packages so one project can use different dependencies from another.

Terminal
python -m venv .venv

# Windows PowerShell
.venv\Scripts\Activate.ps1

# macOS / Linux
source .venv/bin/activate

python -m pip install requests pytest
python -m pip freeze > requirements.txt

Type Hints

Python stays dynamic at runtime, but type hints make your code easier to read, test, and analyze with tools.

Python
from typing import Iterable

def average(values: Iterable[float]) -> float:
    values = list(values)
    if not values:
        raise ValueError("values cannot be empty")
    return sum(values) / len(values)

user: dict[str, str] = {"name": "Aisha", "role": "student"}

Testing

Automated tests catch regressions and prove your functions behave as expected. Start with small units and clear assertions.

Python + pytest
def add(a: int, b: int) -> int:
    return a + b

def test_add() -> None:
    assert add(2, 3) == 5
    assert add(-1, 1) == 0