Python 3.15 Cheat Sheet

This page is a condensed reference to Python, refreshed for Python 3.15. It covers the syntax you use every day and the features that are new this release, including lazy imports, frozendict, built-in sentinels, and unpacking in comprehensions. You can also download the information as a printable cheat sheet:

Free Bonus: What's New in Python 3.15 Cheat Sheet

Get a What's New in Python 3.15 Cheat Sheet (PDF) that sums up every new feature from this tutorial on a single page:

What's New in Python 3.15 Cheat Sheet

Practice with hands-on coding exercises, quizzes, and guided learning paths. Not sure where to begin? Start here.

New to Python, or coming back to it?

What’s New in Python 3.15

  • Python 3.15 is released on October 1, 2026
  • New syntax is additive, but some old APIs are gone
  • Upgrade your own tools now, let servers wait for 3.15.1
  • The upgraded JIT compiler is 8-9% faster on benchmarks
  • Labels below mark what’s new this release
Language: Shell Filename: Run Python 3.15 With One uv Command
$ uv run --python 3.15 python
Language: Shell Filename: Find Slow Code With the New Profiler
$ python -m profiling.sampling run app.py
$ python -m profiling.sampling attach 5171

Curious what else 3.15 brings?

Getting Started

Language: Shell Filename: Start the Interactive Shell
$ python
Language: Shell Filename: Run a Script
$ python my_script.py

Not set up yet?

Comments

  • Always add a space after the #
  • Use comments to explain “why” of your code
Language: Python Filename: Write Comments
# This is a comment
# print("This code will not run.")
print("This will run.")  # Comments are ignored by Python

Not sure what belongs in a comment?

Data Types

  • Python is dynamically typed
  • Use None to represent missing or optional values
  • issubclass() checks if a class is a subclass
Language: Python Filename: Type Investigation
type(42)                # <class 'int'>
type(3.14)              # <class 'float'>
type("Hello")           # <class 'str'>
type(None)              # <class 'NoneType'>

isinstance(3.14, float)  # True
issubclass(int, object)  # True - all inherit
Language: Python Filename: Type Conversion
int("42")                # 42
float("3.14")            # 3.14
str(42)                  # "42"
list("abc")              # ["a", "b", "c"]

Think you’ve got types down?

Variables & Assignment

  • Variables are created when first assigned
  • Use descriptive variable names
  • Follow snake_case convention
Language: Python Filename: Basic Assignment
name = "Leo"           # String
age = 7                # Integer
height = 5.6           # Float
is_cat = True          # Boolean
flaws = None           # None type
Language: Python Filename: Parallel & Chained Assignments
x, y = 10, 20          # Assign multiple values
a = b = c = 0          # Same value, 3 names
Language: Python Filename: Augmented Assignments
counter += 1
numbers += [4, 5]
permissions |= write

Why does += behave differently on lists?

Strings

  • It’s recommended to use double-quotes for strings
  • Use "\n" to create a line break in a string
Language: Python Filename: Creating Strings
single = 'Hello'
double = "World"
multi = """Multiple
line string"""
Language: Python Filename: String Operations
greeting = "me" + "ow!"  # "meow!"
repeat = "Meow!" * 3     # "Meow!Meow!Meow!"
length = len("Python")   # 6
Language: Python Filename: String Methods
"a".upper()                     # "A"
"A".lower()                     # "a"
" a ".strip()                   # "a"
"abc".replace("bc", "ha")       # "aha"
"a b".split()                   # ["a", "b"]
"-".join(["a", "b"])            # "a-b"
Language: Python Filename: String Indexing & Slicing
text = "Python"
text[0]      # "P" (first)
text[-1]     # "n" (last)
text[1:4]    # "yth" (slice)
text[:3]     # "Pyt" (from start)
text[3:]     # "hon" (to end)
text[::2]    # "Pto" (every 2nd)
text[::-1]   # "nohtyP" (reverse)
Language: Python Filename: String Formatting
# f-strings
name = "Aubrey"
age = 2
f"Hello, {name}!"               # "Hello, Aubrey!"
f"{name} is {age} years old"    # "Aubrey is 2 years old"
f"Debug: {age=}"                # "Debug: age=2"
f"{3.14159:.2f}"                # "3.14"

# Raw strings keep escape sequences
r"C:\new"                       # "C:\\new"

Want to go deeper on strings?

Numbers & Math

Language: Python Filename: Arithmetic Operators
10 + 3    # 13
10 - 3    # 7
10 * 3    # 30
10 / 3    # 3.3333333333333335
10 // 3   # 3
10 % 3    # 1
2 ** 3    # 8
Language: Python Filename: Useful Functions
abs(-5)              # 5
round(3.7)           # 4
round(3.14159, 2)    # 3.14
min(3, 1, 2)         # 1
max(3, 1, 2)         # 3
sum([1, 2, 3])       # 6

Surprised by floating-point results?

Conditionals

  • Python uses indentation for code blocks
  • Use 4 spaces per indentation level
Language: Python Filename: If-Elif-Else
if age < 13:
    category = "child"
elif age < 20:
    category = "teenager"
else:
    category = "adult"
Language: Python Filename: Comparison Operators
x == y    # Equal to
x != y    # Not equal to
x < y     # Less than (x <= y for or equal)
x > y     # Greater than (x >= y for or equal)
Language: Python Filename: Logical Operators
if age >= 18 and has_car:
    print("Roadtrip!")

if is_weekend or is_holiday:
    print("No work today.")

Still fuzzy on truthiness?

Loops

  • range(5) generates 0 through 4
  • Use enumerate() to get index and value
  • break exits the loop, continue skips to next
  • Be careful with while to not create an infinite loop
Language: Python Filename: For Loops
# Loop through range
for i in range(5):      # 0, 1, 2, 3, 4
    print(i)

# Loop through collection
fruits = ["apple", "banana"]
for fruit in fruits:
    print(fruit)

# With enumerate for index
for i, fruit in enumerate(fruits):
    print(f"{i}: {fruit}")
Language: Python Filename: While Loops
while True:
    answer = input("Enter 'quit' to exit: ")
    if answer == "quit":
        break
    print(f"You entered: {answer}")

Ready to test yourself on loops?

Functions

  • Define functions with def
  • Always use () to call a function
  • Add return to send values back
  • Create anonymous functions with the lambda keyword
  • Use a sentinel default when None is a valid argument
Language: Python Filename: Defining Functions
def greet():
    return "Hello!"

def greet_person(name):
    return f"Hello, {name}!"

def add(x, y=10):    # Default parameter
    return x + y
Language: Python Filename: Calling Functions
greet()                   # "Hello!"
add(5, 3)                 # 8
add(7)                    # 17
Language: Python Filename: Return Values
def get_min_max(numbers):
    return min(numbers), max(numbers)

minimum, maximum = get_min_max([1, 5, 3])
Language: Python Filename: Built-in Sentinels (New in 3.15)
MISSING = sentinel("MISSING")

def get(config, key, default=MISSING):
    value = config.get(key, default)
    if value is MISSING:
        raise KeyError(key)
    return value
Language: Python Filename: Lambda Functions
square = lambda x: x**2
result = square(5)  # 25

numbers = [1, 2, 3, 4]
squared = list(map(lambda x: x**2, numbers))
evens = list(filter(lambda x: x % 2 == 0, numbers))

When is None a bad default?

Classes

  • Classes are blueprints for objects
  • You commonly use classes to encapsulate data
  • Inside a class, you provide methods for interacting with the data
  • .__init__() is the constructor method
  • self refers to the instance
Language: Python Filename: Defining Classes
class Dog:
    def __init__(self, name, age):
        self.name = name
        self.age = age

    def bark(self):
        return f"{self.name} says Woof!"

# Create instance
my_dog = Dog("Frieda", 3)
print(my_dog.bark())  # Frieda says Woof!
Language: Python Filename: Class Attributes & Methods
class Cat:
    species = "Felis catus"   # Class attribute

    def __init__(self, name):
        self.name = name      # Instance attribute

    def meow(self):
        return f"{self.name} says Meow!"
Language: Python Filename: Inheritance
class Animal:
    def __init__(self, name):
        self.name = name

    def speak(self):
        pass

class Dog(Animal):
    def speak(self):
        return f"{self.name} barks!"

Not sure when to reach for a class?

Exceptions

  • When Python runs and encounters an error, it creates an exception
  • Use specific exception types when possible
  • else runs if no exception occurred
  • finally always runs, even after errors
  • Python 3.15 suggests the attribute you probably meant
Language: Python Filename: Try-Except
try:
    number = int(input("Enter a number: "))
    result = 10 / number
except ValueError:
    print("That's not a valid number!")
except ZeroDivisionError:
    print("Cannot divide by zero!")
else:
    print(f"Result: {result}")
finally:
    print("Calculation attempted")
Language: Python Filename: Common Exceptions
ValueError         # Invalid value
TypeError          # Wrong type
IndexError         # List index out of range
KeyError           # Dict key not found
FileNotFoundError  # File doesn't exist
Language: Python Filename: Smarter Error Messages (New in 3.15)
>>> ratings = [4.5, 3.8]
>>> ratings.push(4.9)
AttributeError: 'list' object has no
attribute 'push'. Did you mean '.append'?
Language: Python Filename: Raising Exceptions
def validate_age(age):
    if age < 0:
        raise ValueError("Age cannot be negative")
    return age

Raise, or return?

Collections

  • A collection is a container that stores multiple items
  • If an object is a collection, then you can loop through it
  • Use len() to get the size of a collection
  • You can check if an item is in a collection with the in keyword
  • Some collections may look similar, but each data structure solves specific needs
  • A frozendict with hashable values can be a dict key
Language: Python Filename: Lists
# Creating lists
empty = []
nums = [5]
mixed = [1, "two", 3.0, True]

# List methods
nums.append("x")         # Add to end
nums.insert(0, "y")      # Insert at index 0
nums.extend(["z", 5])    # Extend with iterable
nums.remove("x")         # Remove first "x"
last = nums.pop()        # Pop returns last element

# List indexing and checks
fruits = ["banana", "apple", "orange"]
fruits[0]                # "banana"
fruits[-1]               # "orange"
"apple" in fruits        # True
len(fruits)              # 3
Language: Python Filename: Tuples
# Creating tuples
point = (3, 4)
single = (1,)    # Note the comma!
empty = ()

# Basic tuple unpacking
point = (3, 4)
x, y = point
x                # 3
y                # 4

# Extended unpacking
first, *rest = (1, 2, 3, 4)
first            # 1
rest             # [2, 3, 4]
Language: Python Filename: Sets
# Creating Sets
a = {1, 2, 3}
b = set([3, 4, 4, 5])

# Set Operations
a | b            # {1, 2, 3, 4, 5}
a & b            # {3}
a - b            # {1, 2}
a ^ b            # {1, 2, 4, 5}
Language: Python Filename: Dictionaries
# Creating Dictionaries
empty = {}
pet = {"name": "Leo", "age": 42}

# Dictionary Operations
pet["sound"] = "Purr!"   # Add key and value
pet["age"] = 7           # Update value
age = pet.get("age", 0)  # Get with default
del pet["sound"]         # Delete key
pet.pop("age")           # Remove and return

# Dictionary Views
pet.keys()         # dict_keys(['name'])
pet.values()       # dict_values(['Leo'])
pet.items()        # dict_items([('name', 'Leo')])
Language: Python Filename: Immutable Dictionaries (New in 3.15)
>>> config = frozendict({"debug": True})
>>> config | {"debug": False}
frozendict({'debug': False})
>>> config["debug"] = False
TypeError: 'frozendict' object does not
support item assignment

List, set, or dictionary?

Comprehensions

  • Comprehensions are condensed for loops, often faster
Language: Python Filename: List Comprehensions
# Basic
squares = [x**2 for x in range(10)]

# With condition
evens = [x for x in range(20) if x % 2 == 0]

# Nested
matrix = [[i*j for j in range(3)]
          for i in range(3)]
Language: Python Filename: Other Comprehensions
# Dictionary comprehension
words = ["hello", "world"]
lengths = {word: len(word) for word in words}

# Set comprehension
unique = {len(word) for word in words}

# Generator expression
sum_squares = sum(x**2 for x in range(1000))
Language: Python Filename: Unpacking in Comprehensions (New in 3.15)
>>> temps = [[18.2, 21.7], [17.9]]
>>> [*t for t in temps]
[18.2, 21.7, 17.9]
>>> parts = [{"host": "db"}, {"port": 5432}]
>>> {**p for p in parts}
{'host': 'db', 'port': 5432}

Comprehension or generator?

File I/O

Language: Python Filename: File Operations
# Read an entire file
with open("file.txt", mode="r", encoding="utf-8") as file:
    content = file.read()

# Write a file
with open("out.txt", mode="w", encoding="utf-8") as file:
    file.write("Hello, World!\n")

# Append to a File
with open("log.txt", mode="a", encoding="utf-8") as file:
    file.write("New log entry\n")
Language: Python Filename: UTF-8 by Default (New in 3.15)
# 3.15 defaults to UTF-8 for text files,
# whatever the operating system's locale says
open("notes.txt").read()

# Opt back in to the locale encoding
open("legacy.txt", encoding="locale")

Wondering what UTF-8 by default changes?

Imports & Modules

  • Prefer explicit imports over import *
  • Group imports: standard library, third-party libraries, user-defined modules
  • lazy imports work at module level, outside try
  • lazy from pathlib import Path works, too
Language: Python Filename: Import Styles
# Import entire module
import math
result = math.sqrt(16)

# Import specific function
from math import sqrt
result = sqrt(16)

# Import with alias
import numpy as np
array = np.array([1, 2, 3])
Language: Python Filename: Lazy Imports (New in 3.15)
import sys

lazy import json        # Bound, not loaded

"json" in sys.modules   # False
json.dumps({"a": 1})    # Imports on first use
"json" in sys.modules   # True

Should your imports be lazy?

Virtual Environments

  • Use a venv to isolate a project’s packages from the system-wide ones
Language: Shell Filename: Create Virtual Environment
$ python -m venv .venv
Language: Windows PowerShell Filename: Activate Virtual Environment (Windows)
PS> .venv\Scripts\activate
Language: Shell Filename: Activate Virtual Environment (Linux & macOS)
$ source .venv/bin/activate

Virtual environments still confusing?

Packages

Language: Shell Filename: Install Packages
$ python -m pip install requests
Language: Shell Filename: Save Requirements & Install from File
$ python -m pip freeze > requirements.txt
$ python -m pip install -r requirements.txt

Not sure how to pin dependencies?

Miscellaneous

Truthy Falsy
-42 0
3.14 0.0
"John" ""
[1, 2, 3] []
("apple", "banana") ()
{"key": None} {}
None
Language: Python Filename: Pythonic Constructs
# Swap variables
a, b = b, a

# Remove duplicates
unique_unordered = list(set(my_list))

# Remove duplicates, preserve order
unique = list(dict.fromkeys(my_list))

More 3.15 Highlights (New in 3.15)

Feature What It Does
math.integer Integer-only math
re.prefixmatch() Clearer re.match()
json.loads(array_hook=) Custom JSON array type
.take_bytes() Cut bytes from a buffer
TaskGroup.cancel() Cancel an asyncio group
math.fmax() Two-float max, NaN-safe

Want more idioms like these?

Ready to go beyond the cheat sheet?

You can download this information as a printable cheat sheet:

Free Bonus: What's New in Python 3.15 Cheat Sheet

Get a What's New in Python 3.15 Cheat Sheet (PDF) that sums up every new feature from this tutorial on a single page:

What's New in Python 3.15 Cheat Sheet