[9일차-1] Python, 데이터분석

송정근·2026년 6월 1일

모듈, 패키지, 가상환경 그리고 NumPy 기초 정리

이번 글에서는 파이썬 코드를 파일 단위로 재사용하는 모듈(module), 여러 모듈을 폴더 단위로 묶는 패키지(package), 외부 라이브러리를 관리하는 가상환경과 requirements.txt, 그리고 데이터 분석의 핵심 라이브러리인 NumPy를 정리한다.


파이썬을 어느 정도 익히고 나면 코드가 점점 길어진다. 이때 모듈과 패키지를 사용하면 코드를 기능별로 나눌 수 있고, NumPy를 사용하면 대량의 수치 데이터를 빠르고 편리하게 처리할 수 있다.

1. 모듈

모듈(module)은 관련된 함수, 클래스, 변수들을 하나의 .py 파일로 묶어 재사용할 수 있게 만든 코드 단위이다.

모듈을 사용하면 다음과 같은 장점이 있다.

  • 기능별로 코드를 나눌 수 있다.
  • 같은 코드를 여러 파일에서 재사용할 수 있다.
  • 파일이 짧아져 가독성과 유지보수성이 좋아진다.
  • 이름 공간(namespace)이 분리되어 이름 충돌을 줄일 수 있다.

1.1 모듈 파일 만들기

예를 들어 과일과 관련된 기능을 fruit.py라는 파일로 분리할 수 있다.

# fruit.py

PI = 3.14


def print_fruit(name):
    print(f"{name}입니다.")


def add_quantity(quantity, amount):
    return quantity + amount


class Fruit:
    def __init__(self, name, quantity):
        self.name = name
        self.quantity = quantity

    def print_info(self):
        print(f"과일 이름: {self.name}")
        print(f"수량: {self.quantity}")

fruit.py 안에는 변수, 함수, 클래스가 함께 들어 있다. 이 파일 자체가 하나의 모듈이다.

1.2 다른 파일에서 모듈 전체 가져오기

같은 폴더에 있는 main.py에서 fruit.py를 사용할 수 있다.

# main.py

import fruit

fruit.print_fruit("사과")

result = fruit.add_quantity(10, 5)
print(result)

apple = fruit.Fruit("사과", 10)
apple.print_info()

출력 결과:

사과입니다.
15
과일 이름: 사과
수량: 10

import fruit로 모듈 전체를 가져오면 fruit.print_fruit()처럼 모듈명.이름 형태로 접근한다.

1.3 필요한 이름만 가져오기

모듈 전체가 아니라 필요한 함수나 클래스만 가져올 수도 있다.

from fruit import Fruit, add_quantity

apple = Fruit("사과", 10)
apple.print_info()

print(add_quantity(10, 5))

출력 결과:

과일 이름: 사과
수량: 10
15

이 방식은 코드가 짧아지는 장점이 있지만, 어떤 모듈에서 가져온 이름인지 덜 명확할 수 있다.

1.4 별칭 사용하기

모듈 이름이 길거나 자주 사용할 때는 as로 별칭을 붙일 수 있다.

import fruit as fr

fr.print_fruit("바나나")

출력 결과:

바나나입니다.

NumPy를 사용할 때 import numpy as np라고 쓰는 것도 같은 방식이다.

1.5 import 방식 비교

방식예시특징
모듈 전체 가져오기import fruit이름 출처가 명확하다.
일부만 가져오기from fruit import Fruit코드가 짧지만 이름 충돌에 주의해야 한다.
별칭 사용import fruit as fr긴 이름을 짧게 줄일 수 있다.

2. __name__과 직접 실행 여부

__name__은 현재 실행 중인 모듈의 이름을 담고 있는 내장 변수이다.

  • 파일을 직접 실행하면 __name__은 "__main__"이 된다.
  • 다른 파일에서 import되면 __name__은 모듈 이름이 된다.

2.1 직접 실행되는 코드와 import되는 코드 구분하기

# fruit.py

def hello():
    print("과일 모듈입니다.")


print("__name__ 값:", __name__)

if __name__ == "__main__":
    print("직접 실행되었습니다.")
    hello()

터미널에서 직접 실행하면 다음과 같다.

python fruit.py

출력 결과:

__name__ 값: __main__
직접 실행되었습니다.
과일 모듈입니다.

다른 파일에서 import하면 if __name__ == "__main__": 블록은 실행되지 않는다.

# main.py

import fruit

출력 결과:

__name__ 값: fruit

if __name__ == "__main__":는 테스트 코드나 직접 실행용 코드를 분리할 때 자주 사용한다.


3. 패키지

패키지(package)는 관련된 여러 모듈을 하나의 폴더로 묶어 계층적으로 관리하는 단위이다.

프로젝트가 커지면 하나의 파일에 모든 코드를 작성하기 어렵다. 이때 기능별로 모듈을 나누고, 관련 모듈들을 패키지로 묶으면 구조가 깔끔해진다.

3.1 패키지 구조

myproject/
├── main.py
└── fruits/
    ├── __init__.py
    ├── apple.py
    └── banana.py

fruits 폴더가 패키지이고, 그 안의 apple.py, banana.py가 모듈이다.

3.2 __init__.py

__init__.py는 패키지가 import될 때 실행되는 파일이다. 패키지의 공개 API를 정리할 때 사용할 수 있다.

# fruits/__init__.py

from .apple import info as apple_info
from .banana import info as banana_info

__all__ = ["apple_info", "banana_info"]

.은 현재 패키지를 의미한다. 즉, .apple은 같은 fruits 패키지 안의 apple.py를 뜻한다.

# fruits/apple.py

def info():
    return "사과입니다."
# fruits/banana.py

def info():
    return "바나나입니다."
# main.py

from fruits import apple_info, banana_info

print(apple_info())
print(banana_info())

출력 결과:

사과입니다.
바나나입니다.

패키지를 사용하면 fruits.apple, fruits.banana처럼 이름 공간을 나눌 수 있어 모듈 이름 충돌을 줄일 수 있다.


4. random 모듈

random 모듈은 무작위 값을 생성할 때 사용하는 파이썬 표준 라이브러리이다. 별도 설치 없이 사용할 수 있다.

import random

4.1 자주 사용하는 함수

아래 예제는 실행할 때마다 결과가 달라질 수 있다.

import random

print("random():", random.random())
print("randint(1, 6):", random.randint(1, 6))
print("randrange(1, 10):", random.randrange(1, 10))

fruits = ["사과", "바나나", "오렌지"]
print("choice:", random.choice(fruits))

numbers = list(range(1, 11))
print("sample:", random.sample(numbers, 3))

cards = ["A", "K", "Q", "J"]
random.shuffle(cards)
print("shuffle:", cards)

출력 결과 예시:

random(): 0.731...
randint(1, 6): 4
randrange(1, 10): 8
choice: 바나나
sample: [2, 9, 5]
shuffle: ['Q', 'A', 'J', 'K']
함수설명
random.random()0 이상 1 미만의 실수 반환
random.randint(a, b)a 이상 b 이하의 정수 반환
random.randrange(a, b)a 이상 b 미만의 정수 반환
random.choice(seq)시퀀스에서 값 하나 선택
random.sample(seq, k)중복 없이 k개 선택
random.shuffle(list)리스트 자체를 섞음

4.2 seed()

random.seed()는 난수 생성기의 초기값을 설정한다. 같은 시드를 사용하면 같은 순서의 난수가 생성된다.

import random

random.seed(2026)

print(random.randint(1, 10))
print(random.randint(1, 10))
print(random.randint(1, 10))

출력 결과:

2
6
9

난수 결과를 재현해야 하는 테스트, 디버깅, 머신러닝 실험에서 seed()가 중요하다.

4.3 의사난수

의사난수(pseudo-random number)는 완전히 무작위로 만들어진 값이 아니라 알고리즘에 의해 만들어진 “랜덤처럼 보이는 숫자”이다.

같은 시작값인 시드(seed)를 주면 같은 난수 순서가 만들어진다. 이 특성 덕분에 실험 결과를 재현할 수 있다.

보안이 중요한 난수에는 random보다 secrets 모듈을 사용하는 것이 적합하다. 예를 들어 인증 토큰이나 비밀번호 재설정 토큰을 만들 때는 secrets를 사용한다.


5. 가상환경과 모듈 설치

외부 라이브러리를 설치할 때는 프로젝트별로 독립된 가상환경을 사용하는 것이 좋다.

가상환경을 사용하면 프로젝트마다 서로 다른 패키지 버전을 사용할 수 있고, 전역 Python 환경이 지저분해지는 것을 막을 수 있다.

5.1 가상환경 생성

python -m venv venv

5.2 가상환경 활성화

Windows:

venv\Scripts\activate

macOS/Linux:

source venv/bin/activate

5.3 pip와 python 경로 확인

Windows:

where pip
where python

macOS/Linux:

which pip
which python

경로가 현재 프로젝트의 venv 안을 가리키는지 확인해야 한다.

5.4 패키지 설치

pip install numpy pandas

더 안전하게는 현재 실행 중인 Python의 pip를 사용하도록 다음 명령을 쓸 수 있다.

python -m pip install numpy pandas

pip이 다른 Python을 가리킬 수 있으므로, 실무에서는 python -m pip install ... 형태를 자주 사용한다.

5.5 패키지 목록 확인

pip list

현재 환경에 설치된 패키지 이름과 버전을 확인할 수 있다.


6. requirements.txt

requirements.txt는 프로젝트에 필요한 외부 패키지와 버전을 기록하는 파일이다. 이 파일이 있으면 다른 사람도 같은 환경을 쉽게 재현할 수 있다.

6.1 requirements.txt 생성

pip freeze > requirements.txt

생성된 파일 예시는 다음과 같다.

numpy==2.4.6
pandas==2.3.3

직접 작성할 수도 있다.

numpy
pandas

버전을 고정하지 않으면 설치 시점의 최신 버전이 설치될 수 있다.

6.2 requirements.txt로 설치

pip install -r requirements.txt

다른 환경에서 이 명령을 실행하면 requirements.txt에 적힌 패키지가 자동으로 설치된다.

출처 및 참고 자료

본 정리는 강의 내용과 아래 자료를 참고하여 학습 목적으로 작성하였습니다.

https://ryuzyproject.tistory.com/293

profile
기록하며 성장하는 개발자

0개의 댓글