01 Basics
python.basics
Core building blocks: comments, variables, naming, I/O, and every operator category. Reference covers Python 3.12+ (notes flag anything version-specific).
Comments
# single-line comment """ Multi-line string used as a block comment (not a true comment, but the common convention) """
Variables & multiple assignment
x = 10 # dynamic typing, no declaration keyword name = "Rushit" a, b, c = 1, 2, 3 # multiple assignment x = y = z = 0 # chained assignment a, b = b, a # swap without a temp variable
Constants & naming conventions
MAX_SIZE = 100 # convention only — Python has no true constants PI = 3.14159 # naming conventions variable_name = 1 # snake_case for variables/functions class ClassName: ... # PascalCase for classes _private = 1 # leading underscore: "internal use" hint __very_private = 1 # name-mangled inside classes __dunder__ = 1 # reserved for language/magic methods
Input / Output
name = input("Enter name: ") # ALWAYS returns a str
age = int(input("Age: ")) # convert manually if you need a number
print("Hello", name, sep=", ", end="!\n")
print(f"{name} is {age}") # f-string (see Strings section)
Type conversion & inspection
Conversion functions (int(), float(), str(), list()…) are documented as built-ins below. Quick inspection tools:
type(3.14) # -> <class 'float'> isinstance(3.14, float) # -> True isinstance(3, (int, float)) # -> True (tuple of types allowed) id(name) # -> unique memory identity (int) help(str.split) # -> interactive docs in the REPL dir(list) # -> list of all attributes/methods
Operators
| Op | Meaning | Example | Result |
|---|---|---|---|
+ | Add | 5 + 2 | 7 |
- | Subtract | 5 - 2 | 3 |
* | Multiply | 5 * 2 | 10 |
/ | True division (always float) | 5 / 2 | 2.5 |
// | Floor division | 5 // 2 | 2 |
% | Modulo (remainder) | 5 % 2 | 1 |
** | Exponent | 5 ** 2 | 25 |
| Op | Meaning | Example | Result |
|---|---|---|---|
== != | Equal / not equal | 3 == 3 | True |
> < >= <= | Ordering | 5 >= 5 | True |
and | Both truthy | True and False | False |
or | Either truthy | True or False | True |
not | Negation | not True | False |
| Op | Same as |
|---|---|
+= -= *= /= | x = x + y, etc. |
//= %= **= | floor-div / mod / power, in place |
&= |= ^= >>= <<= | bitwise, in place |
| Op | Meaning | Example | Result |
|---|---|---|---|
& | AND | 6 & 3 | 2 |
| | OR | 6 | 3 | 7 |
^ | XOR | 6 ^ 3 | 5 |
~ | NOT (invert bits) | ~6 | -7 |
<< | Left shift | 1 << 3 | 8 |
>> | Right shift | 8 >> 2 | 2 |
| Op | Meaning | Example |
|---|---|---|
in | Value exists in container | 3 in [1,2,3] |
not in | Value absent | 5 not in [1,2,3] |
is | Same object identity (not equality) | a is b |
is not | Different identity | a is not None |
Operator precedence (high → low, abridged)
() # grouping ** # exponent (right-assoc) +x -x ~x # unary * / // % + - << >> & ^ | == != < > <= >= is is not in not in not and or := (walrus, lowest — used as an expression)
Walrus operator := 3.8+
Assigns and returns a value in the same expression — useful in while/if conditions and comprehensions.
# without walrus
data = get_data()
while data:
process(data)
data = get_data()
# with walrus
while (data := get_data()):
process(data)
# in a comprehension
results = [y for x in values if (y := transform(x)) is not None]02 Built-in Functions
python.builtins — docs.python.org/3/library/functions.html
All 69 built-ins always available with no import. Search above or scan cards below — each shows syntax, parameters, a working example, and its official doc link.
03 Strings
python.str
Strings are immutable sequences of Unicode code points.
Creating strings
'single quotes'
"double quotes"
'''triple single —
spans multiple lines'''
"""triple double — same, and the
convention for docstrings"""
r"raw string — \n is two chars, not a newline" # great for regex / Windows paths
f"f-string — inline {1 + 1} expressions" # see belowIndexing, slicing & core operations
s = "Python" s[0] # 'P' (indexing) s[-1] # 'n' (negative indexing, from the end) s[1:4] # 'yth' (slicing: start:stop, stop excluded) s[::-1] # 'nohtyP' (reverse via step -1) s[::2] # 'Pto' (every 2nd char) s + "3" # 'Python3' (concatenation) s * 2 # 'PythonPython' (repetition) 'y' in s # True (membership) s == "Python" # True (comparison, case-sensitive)
f-strings & format specifiers
name, pi = "Rushit", 3.14159
f"{name} scored {pi:.2f}" # -> 'Rushit scored 3.14' (2 decimal places)
f"{42:05d}" # -> '00042' (zero-padded width 5)
f"{1234567:,}" # -> '1,234,567' (thousands separator)
f"{pi:>10.2f}" # -> ' 3.14' (right-align, width 10)
f"{name=}" # -> "name='Rushit'" (debug spec, 3.8+)Escape characters & multiline
"Line1\nLine2" # \n newline, \t tab, \\ backslash, \' \" quotes """ This spans multiple physical lines """
String methods
04 Lists
python.list — mutable, ordered sequence
Creating & core operations
nums = [1, 2, 3] mixed = [1, "two", 3.0, [4, 5]] # nested list empty = [] nums[0] # 1 indexing nums[-1] # 3 negative indexing nums[0:2] # [1, 2] slicing nested = [[1,2],[3,4]] nested[1][0] # 3 nested access a, b, c = nums # unpacking first, *rest = nums # first=1, rest=[2, 3] [1,2] + [3,4] # [1, 2, 3, 4] concatenation [1,2] * 3 # [1,2,1,2,1,2] repetition 2 in nums # True membership
List methods
sorted() vs .sort()
nums = [3, 1, 2] new_list = sorted(nums) # returns a NEW sorted list; nums unchanged nums.sort() # sorts IN PLACE; returns None (common bug: x = nums.sort())
Shallow copy vs reference
a = [1, 2, 3] b = a # reference — b and a point to the SAME list b.append(4) # a is now [1, 2, 3, 4] too! c = a.copy() # or list(a), or a[:] — shallow copy, new outer list c.append(5) # a is unaffected import copy d = copy.deepcopy(a) # needed when a contains nested mutable objects
List comprehensions
squares = [x**2 for x in range(6)] # [0,1,4,9,16,25] evens = [x for x in range(10) if x % 2 == 0] # conditional grid = [[r*3+c for c in range(3)] for r in range(3)] # nested tagged = ["even" if x%2==0 else "odd" for x in range(4)] # if/else expr form
05 Tuples
python.tuple — immutable, ordered sequence
t = (1, 2, 3) single = (5,) # the COMMA makes it a tuple, not the parens not_a_tuple = (5) # this is just int 5 t[0] # 1 indexing t[1:] # (2, 3) slicing nested = (1, (2, 3), [4, 5]) a, b, c = t # unpacking first, *rest = t # first=1, rest=[2, 3] t.count(2) # 1 only 2 methods exist: count, index t.index(3) # 2
| Tuple | List | |
|---|---|---|
| Mutable | No | Yes |
| Syntax | (1, 2) | [1, 2] |
| Methods | count, index | 11 methods (append, sort, …) |
| Hashable | Yes (if elements are) | No — can't be a dict key |
| Typical use | Fixed records, dict keys, function returns | Growing collections |
06 Sets
python.set — unordered, unique elements
s = {1, 2, 3}
empty = set() # NOT {} — that creates an empty dict!
s.add(4)
s.remove(1) # KeyError if missing
s.discard(99) # no error if missing
a, b = {1,2,3}, {2,3,4}
a | b # union -> {1,2,3,4}
a & b # intersection -> {2,3}
a - b # difference -> {1}
a ^ b # symmetric difference -> {1,4}
a <= b # subset? -> False
a >= b # superset? -> False
a.isdisjoint(b) # False (they share elements)
evens = {x for x in range(10) if x % 2 == 0} # set comprehension
frozen = frozenset([1, 2, 3]) # immutable, hashable setSet methods
07 Dictionaries
python.dict — key-value mapping, insertion-ordered (3.7+)
d = {"name": "Rushit", "year": 2}
d["name"] # 'Rushit' access (KeyError if missing)
d.get("gpa") # None .get() — safe, no KeyError
d.get("gpa", 0.0) # 0.0 .get() with default
d["year"] = 3 # update
d["branch"] = "CS" # add new key
del d["branch"] # remove
d.pop("year") # remove + return value
nested = {"student": {"name": "Rushit", "skills": ["Python", "SQL"]}}
nested["student"]["skills"]
merged = {**d, **{"gpa": 8.5}} # dict unpacking merge (or d | other, 3.9+)
d.keys() # view of keys (dict_keys)
d.values() # view of values
d.items() # view of (key, value) pairsDictionary methods
Comprehension & iteration patterns
squares = {x: x**2 for x in range(5)} # dict comprehension
for k in d: ... # iterates keys
for k in d.keys(): ... # same, explicit
for v in d.values(): ... # iterates values
for k, v in d.items(): ... # iterates pairs (most common)08 Control Flow
python.control_flow
if score >= 90:
grade = "A"
elif score >= 75:
grade = "B"
else:
grade = "C"
grade = "A" if score >= 90 else "B" # ternary / conditional expression
for i in range(5): # 0..4
if i == 3:
break # exit loop entirely
if i == 1:
continue # skip to next iteration
print(i)
else:
print("loop finished without break") # runs only if no break
while attempts < 3:
attempts += 1
else:
print("while finished without break")
if debug:
pass # no-op placeholdermatch / case 3.10+
match command.split():
case ["go", direction] if direction in ("n","s","e","w"):
move(direction)
case ["go", _]:
print("unknown direction")
case ["quit"]:
exit()
case _:
print("unrecognized command") # wildcard / default09 Comprehensions
python.comprehensions — loop, condition and expression fused into one line
# normal approach
squares = []
for x in range(10):
squares.append(x**2)
# comprehension approach
squares = [x**2 for x in range(10)]
# list comprehension with condition
evens = [x for x in range(10) if x % 2 == 0]
# nested list comprehension (flatten a 2D grid)
grid = [[1,2],[3,4]]
flat = [n for row in grid for n in row] # [1, 2, 3, 4]
# dict comprehension
squares_map = {x: x**2 for x in range(5)}
# set comprehension
unique_lengths = {len(w) for w in ["hi","bye","yo"]}
# generator expression — lazy, computed one item at a time, no [] brackets
gen = (x**2 for x in range(10**6)) # doesn't build the whole list in memory
sum(x**2 for x in range(10)) # generator expr passed directly to sum()10 Functions
python.functions
Defining & calling
def greet(name, greeting="Hello"):
"""Return a greeting string. (this is a docstring)"""
return f"{greeting}, {name}!"
greet("Rushit") # positional argument -> uses default greeting
greet("Rushit", greeting="Hi") # keyword argument
greet(name="Rushit", greeting="Hi")Parameter kinds compared
def f(a, b): # positional or keyword — most common
...
def f(a, b=10): # default argument — evaluated ONCE at def time (careful with mutables)
...
def f(*args): # collects extra positional args into a tuple
...
def f(**kwargs): # collects extra keyword args into a dict
...
def f(a, /, b, *, c): # a = positional-only, b = either, c = keyword-only
... # / marks end of positional-only section
# * marks start of keyword-only section
def f(a, b, *args, c, **kwargs): # realistic mix, all forms together
...Return values
def divmod_(a, b):
return a // b, a % b # multiple return values -> packed as a tuple
q, r = divmod_(17, 5) # unpacked on the caller's side -> q=3, r=2Annotations, scope & closures
def add(a: int, b: int) -> int: # annotations — hints only, not enforced at runtime
return a + b
count = 0
def increment():
global count # without this, count += 1 below raises UnboundLocalError
count += 1
def outer():
total = 0
def inner(x):
nonlocal total # modifies the ENCLOSING function's variable, not global
total += x
inner(5)
return total
def make_multiplier(n): # closure: inner() "remembers" n after make_multiplier returns
def multiplier(x):
return x * n
return multiplier
times3 = make_multiplier(3)
times3(10) # -> 30Recursion, first-class & higher-order functions
def factorial(n):
return 1 if n <= 1 else n * factorial(n - 1) # recursion
def apply_twice(fn, x): # functions are first-class: pass them like any value
return fn(fn(x))
apply_twice(lambda x: x*2, 3) # -> 12 (higher-order function: takes a function as arg)11 Lambda & Functional Programming
python.functional
square = lambda x: x ** 2 # anonymous, single-expression function square(5) # -> 25 list(map(lambda x: x*2, [1,2,3])) # [2, 4, 6] list(filter(lambda x: x % 2 == 0, range(10))) # [0, 2, 4, 6, 8] from functools import reduce reduce(lambda acc, x: acc + x, [1,2,3,4]) # -> 10 (running accumulation) list(zip([1,2,3], ['a','b','c'])) # [(1,'a'), (2,'b'), (3,'c')] list(enumerate(['a','b','c'], start=1)) # [(1,'a'), (2,'b'), (3,'c')] any(x > 5 for x in [1,2,8]) # True — at least one truthy all(x > 0 for x in [1,2,8]) # True — every element truthy
Realistic combinations
data = [("Rushit", 82), ("Aman", 91), ("Zoya", 76)]
sorted(data, key=lambda x: x[1]) # sort by score ascending
sorted(data, key=lambda x: x[1], reverse=True) # descending
max(data, key=lambda x: x[1]) # ('Aman', 91)
min(data, key=lambda x: x[1]) # ('Zoya', 76)12 Iterators & Generators
python.iterators
Iterable -> has __iter__() e.g. a list, tuple, str, dict Iterator -> has __next__() AND __iter__() e.g. what iter(list) produces nums = [1, 2, 3] # iterable, not itself an iterator it = iter(nums) # -> iterator object next(it) # 1 next(it) # 2 next(it) # 3 next(it) # raises StopIteration — the loop-ending signal
Generator functions (yield)
def countdown(n):
while n > 0:
yield n # pauses here, resumes on next next() call
n -= 1
for x in countdown(3): # 3, 2, 1 — computed lazily, one at a time
print(x)
def chain_gen():
yield from countdown(2) # delegate to another generator/iterable
yield from [10, 20]
list(chain_gen()) # [2, 1, 10, 20]
gen_expr = (x**2 for x in range(5)) # generator expression, same laziness as yield
13 Object-Oriented Programming
python.oop
class Student:
school = "Nirma University" # class attribute — shared by all instances
def __init__(self, name, gpa): # constructor
self.name = name # instance attribute
self.gpa = gpa
def summary(self): # instance method — needs self
return f"{self.name}: {self.gpa}"
@classmethod
def from_string(cls, data): # class method — receives the class (cls)
name, gpa = data.split(",")
return cls(name, float(gpa))
@staticmethod
def is_passing(gpa): # static method — no self/cls, just grouped in the class
return gpa >= 5.0
@property
def status(self): # property — call like an attribute, no ()
return "Good standing" if self.gpa >= 7 else "At risk"
s = Student("Rushit", 8.5)
s.summary()
Student.from_string("Aman,7.2")
Student.is_passing(6.0)
s.status # no parentheses — properties act like read-only attributesInheritance & polymorphism
class Person:
def __init__(self, name):
self.name = name
def greet(self):
return f"Hi, I'm {self.name}"
class Student(Person): # single inheritance
def __init__(self, name, roll_no):
super().__init__(name) # call the parent's __init__
self.roll_no = roll_no
def greet(self): # method overriding
return super().greet() + f" ({self.roll_no})"
class TA(Student, Person): # multiple inheritance (MRO decides lookup order)
pass
for p in [Person("A"), Student("B", 1)]:
print(p.greet()) # polymorphism — same call, different behaviorEncapsulation & abstract classes
class Account:
def __init__(self, balance):
self._balance = balance # "protected" convention (single underscore)
self.__pin = 1234 # "private" convention (name-mangled)
from abc import ABC, abstractmethod
class Shape(ABC):
@abstractmethod
def area(self): # subclasses MUST implement this
...
class Circle(Shape):
def __init__(self, r): self.r = r
def area(self): return 3.14159 * self.r ** 2
Shape() # TypeError — can't instantiate an abstract class directlyCommon dunder (magic) methods
| Method | Triggered by |
|---|---|
__init__(self, ...) | Object creation — the constructor |
__str__(self) | str(obj) / print(obj) — readable form |
__repr__(self) | repr(obj) — unambiguous, debug-friendly form |
__len__(self) | len(obj) |
__getitem__(self,k) | obj[k] |
__setitem__(self,k,v) | obj[k] = v |
__iter__(self) | Makes the object iterable (for x in obj) |
__next__(self) | next(obj) when obj is an iterator |
__eq__(self, other) | obj == other |
__lt__(self, other) | obj < other |
__add__(self, other) | obj + other |
__enter__ / __exit__ | with obj: — context manager protocol |
14 Exception Handling
python.exceptions
try:
result = 10 / divisor
except ZeroDivisionError:
result = 0
except (TypeError, ValueError) as e: # multiple exceptions + alias
print(f"bad input: {e}")
else:
print("ran only if no exception was raised")
finally:
print("always runs — cleanup goes here")
raise ValueError("gpa must be between 0 and 10") # raise manually
class InvalidGPAError(Exception): # custom exception
pass
raise InvalidGPAError("gpa out of range")Exception quick reference
| Exception | Usually happens when | Example |
|---|---|---|
Exception | Base class for (almost) all built-in exceptions | except Exception as e: |
ValueError | Right type, invalid value | int("abc") |
TypeError | Wrong type used in an operation | "2" + 2 |
IndexError | Sequence index out of range | [1,2][5] |
KeyError | Dict key doesn't exist | {}["x"] |
FileNotFoundError | Path doesn't exist on disk | open("missing.txt") |
ZeroDivisionError | Dividing by zero | 5 / 0 |
AttributeError | Attribute/method doesn't exist | "x".push() |
ImportError | Name can't be imported from a module | from math import fake |
ModuleNotFoundError | Module itself doesn't exist | import fakemodule |
15 File Handling
python.files
with open("data.txt", "r") as f: # ALWAYS prefer 'with' — see why below
content = f.read() # whole file as one string
# f.readline() # one line at a time
# f.readlines() # list of all lines
with open("data.txt", "w") as f: # 'w' overwrites the whole file
f.write("first line\n")
f.writelines(["second\n", "third\n"])
with open("data.txt", "a") as f: # 'a' appends without erasing
f.write("appended line\n")
with open("data.txt") as f:
f.seek(0) # move cursor to byte offset
pos = f.tell() # current cursor position| Mode | Meaning |
|---|---|
'r' | Read (default) — errors if file doesn't exist |
'w' | Write — creates file, truncates if it exists |
'a' | Append — creates file if missing, adds to the end |
'x' | Exclusive create — errors if the file already exists |
'b' | Binary mode suffix, e.g. 'rb', 'wb' |
'+' | Read and write, e.g. 'r+' |
with: it calls f.close() automatically — even if an exception happens inside the block — so file handles never leak.16 Modules & Imports
python.modules
import math # whole module -> use as math.sqrt()
from math import sqrt # just one name -> use as sqrt()
from math import * # everything (avoid — pollutes namespace, unclear origin)
import numpy as np # aliased import — very common convention
# your own module: save as helpers.py, then anywhere in the same project:
import helpers
helpers.my_function()
if __name__ == "__main__": # True only when this file is run directly,
main() # False when it's imported by another file# package layout
myproject/
├── main.py
└── mypackage/
├── __init__.py
└── utils.py
# inside main.py
from mypackage import utils
from mypackage.utils import helper_fn
from . import utils # relative import — only inside a package
import sys
sys.path # list of directories Python searches for modules
sys.path.append("/custom/path") # add a directory at runtime# command line — package management pip install pandas pip install pandas==2.2.0 pip freeze > requirements.txt # snapshot installed packages pip install -r requirements.txt # install from that snapshot python -m venv .venv # create a virtual environment .venv\Scripts\activate # activate on Windows source .venv/bin/activate # activate on macOS/Linux
17 Standard Library
python.stdlib — the modules used most in data work, scripting & backend code
18 Regular Expressions
python.re — docs.python.org/3/library/re.html
import re
re.search(r"\d+", "room 42") # -> Match object at first occurrence, or None
re.match(r"\d+", "42 room") # -> matches only at the START of the string
re.fullmatch(r"\d+", "42") # -> matches only if the WHOLE string fits
re.findall(r"\d+", "a1 b22 c333") # -> ['1', '22', '333'] (all matches, as strings)
re.finditer(r"\d+", "a1 b22") # -> iterator of Match objects (has .start()/.end())
re.sub(r"\d+", "#", "room 42") # -> 'room #' (replace matches)
re.split(r"\s+", "a b c") # -> ['a', 'b', 'c'] (split on a pattern)
pattern = re.compile(r"\d+") # pre-compile for reuse in a loop (faster)
pattern.findall("a1 b22")| Token | Meaning |
|---|---|
\d \D | digit / non-digit |
\w \W | word char (letter/digit/_) / non-word |
\s \S | whitespace / non-whitespace |
. | any char except newline |
[abc] [^abc] | one of a/b/c / none of a/b/c |
* + ? | 0+, 1+, 0-or-1 of the previous token |
{n,m} | between n and m repetitions |
^ $ | start / end of string (anchors) |
(...) | capturing group — retrievable via .group(1) |
(?:...) | non-capturing group |
Common patterns
email = r"[\w.+-]+@[\w-]+\.[\w.-]+"
phone_in = r"\d{10}" # simple 10-digit number
digits = r"\d+"
whitespace = r"\s+"
# extracting numbers from mixed text
re.findall(r"\d+\.?\d*", "Price: 199.99, Qty: 3") # ['199.99', '3']
# finding whole words only (word boundary)
re.findall(r"\bcat\b", "cat category concatenate") # ['cat']
# always use RAW strings for patterns — avoids \d becoming an invalid escape19 Date & Time
python.datetime
from datetime import date, time, datetime, timedelta
date.today() # date(2026, 8, 2) — today's date, no time
datetime.now() # datetime(2026, 8, 2, 14, 30, 5, ...)
time(14, 30) # time object, 2:30 PM, no date attached
datetime.now() + timedelta(days=7) # a week from now
datetime.now() - timedelta(hours=3) # 3 hours ago
d1, d2 = date(2026,1,1), date(2026,8,2)
(d2 - d1).days # -> 213 (difference as a timedelta)
now = datetime.now()
now.strftime("%Y-%m-%d %H:%M:%S") # datetime -> string
datetime.strptime("2026-08-02", "%Y-%m-%d") # string -> datetime| Code | Meaning | Example |
|---|---|---|
%Y | 4-digit year | 2026 |
%y | 2-digit year | 26 |
%m | month (01-12) | 08 |
%d | day of month | 02 |
%H | hour, 24h (00-23) | 14 |
%I | hour, 12h (01-12) | 02 |
%M | minute | 30 |
%S | second | 05 |
%A / %a | weekday name / abbreviated | Sunday / Sun |
%B / %b | month name / abbreviated | August / Aug |
%p | AM/PM | PM |
20 Python Data Handling Patterns
python.patterns — the snippets you reach for constantly
21 Syntax at a Glance
python.syntax_index — every core construct, compressed to its shape
22 Decorators
python.decorators — a function that wraps another function
def logger(func): # a decorator is just a function...
def wrapper(*args, **kwargs): # ...that returns a wrapper function
print(f"calling {func.__name__}")
result = func(*args, **kwargs)
print(f"done: {result}")
return result
return wrapper
@logger # sugar for: greet = logger(greet)
def greet(name):
return f"Hi {name}"
greet("Rushit") # prints the log lines, then returns "Hi Rushit"from functools import wraps
def logger(func):
@wraps(func) # preserves func.__name__ / __doc__ on the wrapper
def wrapper(*args, **kwargs):
return func(*args, **kwargs)
return wrapper
@logger
@staticmethod # stacking decorators — applied bottom-up
def utility(): ...
23 Context Managers
python.context_managers — guaranteed setup / teardown around a block
with open("f.txt") as f: # the classic example — guarantees f.close()
data = f.read()
class Timer: # writing your own — implement __enter__/__exit__
def __enter__(self):
import time
self.start = time.time()
return self # value bound to "as x"
def __exit__(self, exc_type, exc_val, exc_tb):
print(f"took {time.time() - self.start:.4f}s")
return False # False -> don't suppress exceptions
with Timer() as t:
do_something_slow()
from contextlib import contextmanager
@contextmanager # simpler way, using a generator
def timer():
import time
start = time.time()
yield # code inside the "with" block runs here
print(f"took {time.time() - start:.4f}s")
with timer():
do_something_slow()24 Type Hints
python.typing — hints only, not enforced at runtime (use mypy/pyright to check)
x: int = 5
name: str = "Rushit"
numbers: list[int] = [1, 2, 3] # modern generic syntax (3.9+)
data: dict[str, int] = {"a": 1}
point: tuple[int, str] = (1, "x")
maybe_name: int | None = None # union, modern syntax (3.10+)
def add(a: int, b: int) -> int: # param + return annotations
return a + b
from typing import Optional, Union, Any, Callable, TypeVar, TypedDict
def find(x: int) -> Optional[str]: ... # same as -> str | None
def parse(x: Union[int, str]) -> Any: ... # same as int | str (pre-3.10 style)
on_click: Callable[[int, int], None] # a function taking (int,int) -> None
T = TypeVar("T")
def first(items: list[T]) -> T: # generic function — works for any type
return items[0]
class Movie(TypedDict): # dict with a fixed, typed shape
title: str
year: int25 Dataclasses
python.dataclasses — auto-generates __init__, __repr__, __eq__ from field annotations
from dataclasses import dataclass, field
@dataclass
class Student:
name: str
gpa: float = 0.0 # default value
skills: list[str] = field(default_factory=list) # mutable default — needs field()
s = Student("Rushit", 8.5, ["Python", "SQL"])
print(s) # Student(name='Rushit', gpa=8.5, skills=['Python', 'SQL'])
s == Student("Rushit", 8.5, ["Python", "SQL"]) # True — __eq__ generated for free
@dataclass(frozen=True) # immutable — raises on attribute assignment after creation
class Point:
x: int
y: int26 Async Python
python.asyncio — concurrency for I/O-bound work (network calls, file/database I/O)
import asyncio
async def fetch(id): # 'async def' -> defines a coroutine function
await asyncio.sleep(1) # 'await' -> pause here, let other tasks run
return f"result {id}"
async def main():
result = await fetch(1) # run one coroutine and wait for it
task = asyncio.create_task(fetch(2)) # schedule concurrently, keep running
other_result = await task
results = await asyncio.gather(fetch(3), fetch(4), fetch(5)) # run several at once
asyncio.run(main()) # entry point — starts the event loopmultiprocessing for that instead).27 Special Syntax & Operators
python.operators — the symbols that trip people up out of context
| Symbol | Meaning | Example |
|---|---|---|
* | Unpack iterable into positional args / collect extra positional args | f(*args) · a, *rest = [1,2,3] |
** | Unpack dict into keyword args / collect extra keyword args / exponent | f(**kwargs) · 2**10 |
:= | Walrus — assign inside an expression | if (n := len(a)) > 5: |
/ | True division | 7 / 2 → 3.5 |
// | Floor division | 7 // 2 → 3 |
% | Modulo | 7 % 2 → 1 |
@ | Decorator syntax / matrix multiplication (numpy) | @staticmethod · A @ B |
| | Bitwise OR / set union / type union (3.10+) | a | b · int | None |
& | Bitwise AND / set intersection | a & b |
^ | Bitwise XOR / set symmetric difference | a ^ b |
~ | Bitwise NOT (inverts bits) | ~5 → -6 |
<< >> | Bit shift left / right | 1 << 4 → 16 |
is / is not | Identity comparison (same object in memory) | x is None |
in / not in | Membership test | "a" in "cat" |
28 Common Mistakes
python.gotchas — don't forget these