As a Python program grows, keeping everything in a single file stops making sense. Python lets you split code across multiple files called modules, and pull pieces of one module into another using the import statement. This is also how you get access to Python's huge standard library, and to third-party packages you install with pip.

A module is really just a .py file. If you have a file named math_utils.py, that file is automatically a module named math_utils that any other file in the same project can import.

Basic import

import math

print(math.sqrt(16))
print(math.pi)

Output:

4.0
3.141592653589793

After import math, everything inside the module is accessed through the math. prefix. This keeps names organized and avoids collisions — two different modules can both have a function called parse() without conflicting, because you always call them as module_a.parse() and module_b.parse().

from ... import ...

If you only need one or two things from a module, you can import them directly into your current namespace, skipping the prefix:

from math import sqrt, pi

print(sqrt(25))
print(pi)

Output:

5.0
3.141592653589793

This is convenient, but use it sparingly in larger files — importing many names this way makes it harder to tell, later, which module a given function actually came from.

Aliasing with as

You can rename a module (or a specific import) as you bring it in, which is extremely common for libraries with long names:

import numpy as np
from datetime import datetime as dt

arr = np.array([1, 2, 3])
now = dt.now()

np and pd (for pandas) are such strong conventions in the Python data ecosystem that most developers recognize them instantly, even though they're just aliases you could technically name anything.

Your Own Modules

Importing your own files works exactly the same way. If main.py and math_utils.py are in the same folder:

# math_utils.py
def square(x):
    return x * x

# main.py
import math_utils

print(math_utils.square(5))

Output:

25

Modules vs Packages

A package is just a folder of modules, marked as importable by containing an __init__.py file (in modern Python this file can even be empty). So import numpy is really importing a whole package made up of many individual modules working together, while import math is importing a single module. From the calling code's point of view, the import syntax looks identical either way — you don't need to know or care whether something is one file or a whole folder of them.

Once you're pulling in modules from outside the standard library, you'll need pip to install them first.