
계층 구조
파이썬의 라이브러리 체계는 크게 모듈 > 클래스 > 메서드 순으로 구성
모듈(Module): 관련 있는 코드들을 모아놓은 파일 ( ~.py)
클래스(Class): 객체를 만들기 위한 설계도
메서드(Method): 클래스 내부에서 정의된 함수
표준 라이브러리(Standard Library)
datetime
datetime (모듈/라이브러리)
├── datetime (클래스): 날짜와 시간을 모두 다룸
│ └── now() (메서드): 현재 시간을 가져옴
├── timedelta (클래스): 기간(차이)을 다룸
│ └── total_seconds() (메서드): 전체 초를 계산함
└── date (클래스): 날짜만 다룸
from datetime import datetime, timedelta
datetime : 날짜와 시간을 표현하고 다루는 클래스
- 연, 월, 일까지만 넣어도 만들 수 있고, 뒤에 시간, 분, 초, 마이크로초는 기본값이 0
timedelta : 시간 간격(차이)을 나타내는 클래스 (몇일,몇시간 차이)
- 주로 datetime끼리의 뺄셈 결과, 혹은 datetime ± timedelta 연산에 사용
from datetime import datetime
now = datetime.now()
print(now)
dt = datetime(2025, 9, 29, 15, 30, 0)
print(dt)
d1 = datetime(2025, 9, 29)
print(d1)
d2 = datetime(2025, 9, 29, 12, 30)
print(d2)
d3 = datetime(2025, 9, 29, 12, 30, 45)
print(d3)
print(now.year)
print(now.month)
print(now.day)
print(now.hour)
print(now.minute)
print(now.second)
print(now.strftime("%Y-%m-%d %H:%M:%S"))
s = "2025-10-01 12:00:00"
dt = datetime.strptime(s, "%Y-%m-%d %H:%M:%S")
print(dt)
from datetime import timedelta
delta_days = timedelta(days=5)
delta_time = timedelta(hours=2, minutes=30)
now = datetime.now()
print(now + timedelta(days=5))
print(now - timedelta(hours=3))
dt1 = datetime(2025, 9, 29, 12, 0, 0)
dt2 = datetime(2025, 10, 1, 15, 0, 0)
diff = dt2 - dt1
print(diff)
print(diff.days)
print(diff.total_seconds())
timedelta
timedelta 는 단순히 며칠, 몇 초 차이만 계산
- "9월 1일 - 5일" → "8월 27일"처럼 자동으로 월·연도까지 넘어감.
- 반대로 + 연산하면 자동으로 다음 달/다음 해로 올라감
from datetime import datetime, timedelta
d = datetime(2025, 9, 1)
result = d - timedelta(days=5)
print(result)
d1 = datetime(2025, 1, 3)
print(d1 - timedelta(days=5))
print(datetime.now())
print(datetime.utcnow())
print(datetime.today())
from datetime import datetime
d = datetime(2025, 9, 29)
print(d.weekday())
d2 = datetime(2025, 10, 5)
print(d2.weekday())
print(d.isoweekday())
print(d2.isoweekday())
now = datetime.now()
print(now.strftime("%Y-%m-%d %H:%M:%S"))
print(now.strftime("%A, %B %d"))
s = "2025-10-01 12:30:00"
dt = datetime.strptime(s, "%Y-%m-%d %H:%M:%S")
%Y: 연도(2025)
%m: 월(01~12)
%d: 일(01~31)
%H: 시(00~23)
%M: 분(00~59)
%S: 초(00~59)
%A: 요일 이름(Monday)
%B: 월 이름(September)
date
from datetime import datetime, date
today = date.today()
print(f"오늘 날짜: {today}")
now = datetime.now()
only_date = now.date()
print(f"현재 시간 포함: {now}")
print(f"날짜만 추출: {only_date}")
String
| 상수 | 값 | 활용 예시 |
|---|
string.ascii_lowercase | "abcdefghijklmnopqrstuvwxyz" | 소문자 알파벳만 필요할 때 |
string.ascii_uppercase | "ABCDEFGHIJKLMNOPQRSTUVWXYZ" | 대문자 알파벳만 필요할 때 |
string.ascii_letters | "abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ" | 대소문자 구분 없이 알파벳 전체 |
string.digits | "0123456789" | 숫자만 필요할 때 (비밀번호, 난수 등) |
string.hexdigits | "0123456789abcdefABCDEF" | 16진수 처리할 때 |
string.octdigits | "01234567" | 8진수 처리할 때 |
string.punctuation | !"#$%&'()*+,-./:;<=>?@[\]^_{ }~` | 특수문자 집합 (비밀번호 생성 등) |
string.whitespace | " \t\n\r\x0b\x0c" | 공백/탭/줄바꿈 문자 식별할 때 |
string.printable | 모든 출력 가능한 문자(숫자, 알파벳, 기호, 공백 포함) | 문자열이 출력 가능한지 체크할 때 |
사용 예시
import random, string
s = "12345"
print(all(ch in string.digits for ch in s))
s = "hello \t world\n"
cleaned = "".join(ch for ch in s if ch not in string.whitespace)
print(cleaned)
all_chars = string.ascii_letters + string.digits + string.punctuation
password = "".join(random.choice(all_chars) for _ in range(12))
print(password)
- random.choice(all_chars) : all_chars 문자열에서 무작위로 문자 하나를 선택.
"".join([...])
- 리스트나 제너레이터에서 나온 문자들을 빈 문자열("")로 이어붙임
Random
| 함수 / 상수 | 설명 | 활용 예시 |
|---|
random.random() | 0.0 이상 1.0 미만의 실수(float) 반환 | 난수 생성, 확률 계산 |
random.randint(a, b) | a 이상 b 이하의 정수 반환 | 주사위 굴리기, 범위 내 난수 생성 |
random.randrange(start, stop, step) | range(start, stop, step) 중 하나를 무작위 선택 | 짝수/홀수 난수 뽑기 |
random.uniform(a, b) | a 이상 b 이하의 실수(float) 반환 | 소수점 포함 난수 필요할 때 |
random.choice(seq) | 시퀀스(리스트, 튜플, 문자열 등)에서 임의의 요소 1개 선택 | 리스트에서 무작위 값 뽑기 |
random.choices(seq, k=n) | 시퀀스에서 중복 허용하여 n개 뽑기 | 랜덤 샘플링 (복원 추출) |
random.sample(seq, k=n) | 시퀀스에서 중복 없이 n개 뽑기 | 랜덤 샘플링 (비복원 추출) |
random.shuffle(seq) | 시퀀스 요소를 제자리에서 무작위로 섞음 (리턴값 없음) | 카드 섞기, 순서 무작위화 |
random.seed(x) | 난수 발생 시드(seed) 설정 → 같은 시드면 결과 동일 | 재현 가능한 난수 생성 (테스트용) |
math
| 기능 / 상수/함수 | 설명 | 사용 예시 | 결과 |
|---|
math.pi | 원주율 π 값 | math.pi | 3.141592653589793 |
math.e | 자연로그의 밑 e | math.e | 2.718281828459045 |
math.sqrt(x) | 제곱근 | math.sqrt(16) | 4.0 |
math.pow(x, y) | x의 y승 (float 반환) | math.pow(2, 3) | 8.0 |
math.factorial(x) | 계승(n!) | math.factorial(5) | 120 |
math.gcd(a, b) | 최대공약수 | math.gcd(48, 18) | 6 |
math.lcm(a, b) | 최소공배수 (Python 3.9+) | math.lcm(12, 18) | 36 |
math.floor(x) | 내림 | math.floor(3.7) | 3 |
math.ceil(x) | 올림 | math.ceil(3.2) | 4 |
math.trunc(x) | 정수 부분만 취함 | math.trunc(-3.9) | -3 |
math.log(x) | 자연로그 ln(x) | math.log(math.e) | 1.0 |
math.log10(x) | 밑 10 로그 | math.log10(1000) | 3.0 |
math.log2(x) | 밑 2 로그 | math.log2(8) | 3.0 |
math.degrees(x) | 라디안 → 도(degree) | math.degrees(math.pi) | 180.0 |
math.radians(x) | 도(degree) → 라디안 | math.radians(180) | 3.141592653589793 |
math.sin(x) | 사인 (라디안 단위) | math.sin(math.pi/2) | 1.0 |
math.cos(x) | 코사인 (라디안 단위) | math.cos(0) | 1.0 |
math.tan(x) | 탄젠트 (라디안 단위) | math.tan(math.pi/4) | 0.9999999999999999 ≈ 1 |
math.isqrt(x) | 제곱근의 정수값 (내림) | math.isqrt(17) | 4 |
math.isfinite(x) | 유한한 값인지 검사 | math.isfinite(10**100) | True |
math.isinf(x) | 무한대인지 검사 | math.isinf(float('inf')) | True |
math.isnan(x) | NaN(Not a Number) 판별 | math.isnan(float('nan')) | True |
enum
- 열거형을 정의하기 위한 라이브러리(재할당 불가)
- 문자열이나 숫자를 사용하면 오타나 중복 실수가 생길 수 있음
- Enum을 사용하면 정해진 값만 허용 하도록 강제 가능, 가독성 좋아짐
- Enum → 기본 열거형
- IntEnum → 정수 기반 열거형 (비교 연산 가능)
- StrEnum → 문자열 기반 열거형 (Python 3.11 이상)
- auto() → 값 자동 할당
from enum import Enum, IntEnum, auto, StrEnum
class Number(IntEnum):
ONE = 1
TWO = 2
class Fruit(StrEnum):
APPLE = "apple"
BANANA = "banana"
class AutoEnum(Enum):
A = auto()
B = auto()
from enum import Enum
from fastapi import FastAPI
class ModelName(str, Enum):
alexnet = "alexnet"
resnet = "resnet"
lenet = "lenet"
app = FastAPI()
@app.get("/models/{model_name}")
async def get_model(model_name: ModelName):
if model_name is ModelName.alexnet:
return {"model_name": model_name, "message": "Deep Learning FTW!"}
if model_name.value == "lenet":
return {"model_name": model_name, "message": "LeCNN all the images"}
return {"model_name": model_name, "message": "Have some residuals"}
typing
타입 힌트(type hint)를 정의하고 활용할 수 있게 해주는 표준 라이브러리
파이썬은 원래 동적 타입 언어라서 변수 타입을 강제하지 않지만, typing을 이용하면 코드의 가독성, 유지보수성, 그리고 IDE/도구(예: mypy, PyCharm)에서의 정적 분석을 강화할 수 있다.
- typing은 변수, 함수 매개변수, 반환값의 타입을 명시할 때 사용.
- 실행 시에는 강제하지 않지만, 정적 타입 체커(mypy 등)가 검증할 수 있음.
| 타입 | 설명 | 사용 예시 |
|---|
Any | 어떤 타입이든 가능 (제한 없음) | def f(x: Any): ... |
Union[T1, T2] (Py3.10+에서는 T1 \| T2) | 여러 타입 중 하나 허용 | def f(x: Union[int, str]): ... `def f(x: int |
Optional[T] (= Union[T, None]) | 값이 없을 수도 있음 | def f(name: Optional[str]): ... |
List[T] | 리스트 | nums: List[int] = [1, 2, 3] |
Dict[K, V] | 키-값 딕셔너리 | data: Dict[str, int] = {"a": 1} |
Tuple[T1, T2, ...] | 고정된 길이 튜플 | point: Tuple[int, int] = (3, 5) |
Set[T] | 집합 | tags: Set[str] = {"a", "b"} |
Callable[[Args...], Return] | 함수 타입 | def apply(op: Callable[[int, int], int]): ... |
Literal[...] | 특정 값만 허용 | status: Literal["open", "closed"] |
Annotated[T, meta...] | 타입에 추가 메타데이터 부여 | user_id: Annotated[int, Path(gt=0)] |
TypedDict | 딕셔너리 구조 정의 | class User(TypedDict): name: str age: int |
Final | 상수 개념, 재할당 불가 | MAX: Final = 100 |
ClassVar[T] | 클래스 변수임을 명시 | class C: counter: ClassVar[int] = 0 |
Self (Py3.11~) | 자기 자신 타입 | class Node: def clone(self) -> Self: ... |
TypeVar | 제네릭 타입 변수 | T = TypeVar("T") def first(items: List[T]) -> T: ... |
from typing import List, Dict, Optional, Union, Callable
def process_scores(scores: List[int]) -> Dict[str, float]:
return {"avg": sum(scores) / len(scores)}
def greet(name: Optional[str] = None) -> str:
if name:
return f"Hello, {name}!"
return "Hello!"
def stringify(value: Union[int, float]) -> str:
return str(value)
def operate(x: int, y: int, op: Callable[[int, int], int]) -> int:
return op(x, y)
print(process_scores([80, 90, 100]))
print(greet())
print(greet("Kihoon"))
print(stringify(3.14))
print(operate(3, 5, lambda a, b: a + b))
외부 라이브러리(설치 필요)
Pydantic
- 설치 : pip install pydantic
| 기능 / 클래스 | 설명 | 활용 예시 |
|---|
BaseModel | 데이터 검증 및 직렬화/역직렬화의 기본 클래스 | 요청/응답 데이터 구조 정의, 타입 검증 |
BaseSettings (pydantic_settings) | 환경 변수(.env, OS 환경변수)를 Python 클래스 속성으로 자동 매핑 | 설정값 관리 (DB 접속정보, API 키 등) |
Field() | 각 필드에 제약조건/기본값/메타데이터를 부여 | 최소/최대 길이, 기본값, 설명 지정 |
validator (v1) / field_validator (v2) | 특정 필드 값이 유효한지 검사하는 커스텀 검증 로직 추가 | 이메일 형식 확인, 비밀번호 규칙 검증 |
model_validate() | dict/JSON → 모델 객체 변환 및 자동 검증 | API 응답 데이터를 객체로 변환 |
model_dump() | 모델 객체 → dict 변환 | DB 저장, JSON 변환 시 사용 |
constr, conint, conlist | 제약조건이 걸린 타입(문자열/정수/리스트) | 문자열 길이 제한, 숫자 범위 제한 |
EmailStr, AnyUrl | 내장된 특수 타입 (이메일/URL 검증용) | 이메일, URL 입력값 유효성 검사 |
StrictStr, StrictInt | 타입을 엄격히 강제하는 버전 | "123"을 int로 자동 변환 ❌ |
ConfigDict (v2) | 모델 전역 설정 (예: extra="forbid", str_to_lower=True) | 추가 필드 금지, 문자열 자동 소문자 변환 |
PositiveInt, NonNegativeFloat | 값에 수학적 제약조건을 둔 타입 | 나이, 가격, 수량 등 음수 불가 값 검증 |
RootModel | 단일 값이나 컬렉션(list, dict)을 루트로 가지는 모델 정의 | 단순 JSON 배열 응답 검증 |
예시

| 구분 | BaseModel | BaseSettings |
|---|
| 주 용도 | API 요청/응답, 일반 데이터 검증 | 앱 환경설정, DB 연결 정보, API 키 관리 |
| 데이터 소스 | 코드에서 직접 값 전달 (User(id=1, ...)) | 환경변수, .env 파일, OS 환경 |
| 기본값 | 클래스 속성으로 지정 | 클래스 속성으로 지정 (환경변수로 덮어씀) |
| 검증 기능 | 타입 검증, 제약조건 가능 | 타입 검증, 제약조건 가능 |
| 직렬화 | .model_dump() | .model_dump() |
BaseModel
- 클래스를 BaseModel을 상속해서 정의하면
- 데이터 검증(Validation) + 변환(Parsing) + 직렬화(Serialization) 기능이 자동으로 붙음


BaseSettings(환경 설정용 모델)
- BaseModel과 비슷하게 데이터 검증 + 직렬화 기능을 가지지만,
- 환경 변수(Environment Variable)나 .env 파일에서 값을 자동으로 읽어와서 클래스 속성에 매핑해줌


FastAPI
| 기능 / 클래스 | 설명 | 활용 예시 |
|---|
FastAPI() | FastAPI 애플리케이션 인스턴스 생성 | app = FastAPI() |
APIRouter | 라우터 모듈화 (엔드포인트를 파일 단위로 분리 가능) | router = APIRouter(prefix="/users") |
| HTTP 메서드 데코레이터 | @app.get, @app.post, @app.put, @app.delete 등 요청 처리 함수 지정 | @app.get("/items") |
Depends | 의존성 주입(Dependency Injection) 기능 제공 | DB 세션, 인증 로직 주입 |
Request, Response | HTTP 요청/응답 객체 | 쿠키, 헤더, 응답 제어 |
Query, Path, Body | 요청 파라미터/바디 검증 및 메타데이터 지정 | q: str = Query(..., min_length=3) |
BackgroundTasks | 요청과 별도로 백그라운드 작업 실행 | 이메일 발송, 로그 저장 |
status | HTTP 상태 코드 상수 모음 | status.HTTP_201_CREATED |
HTTPException | API 에러 발생 시 HTTP 응답 리턴 | raise HTTPException(404, "Not Found") |
tortoise ORM
| 기능 / 클래스 | 설명 | 활용 예시 |
|---|
Model | ORM 모델 정의를 위한 기본 클래스 | class User(Model): ... |
fields | 모델의 필드 정의 (IntField, CharField, ForeignKeyField 등) | name = fields.CharField(max_length=50) |
Tortoise.init() | DB 연결 및 모델 초기화 | await Tortoise.init(db_url="sqlite://...") |
Tortoise.generate_schemas() | 정의된 모델 기반으로 DB 테이블 생성 | await Tortoise.generate_schemas() |
QuerySet | ORM 쿼리 결과 집합 (비동기) | await User.filter(age__gte=18) |
ForeignKeyField | 일대다(1:N) 관계 정의 | user = fields.ForeignKeyField("models.User") |
ManyToManyField | 다대다(N:M) 관계 정의 | tags = fields.ManyToManyField("models.Tag") |
OneToOneField | 일대일(1:1) 관계 정의 | profile = fields.OneToOneField("models.Profile") |
pydantic_model_creator | ORM 모델을 Pydantic 모델로 자동 변환 | User_Pydantic = pydantic_model_creator(User) |
annotate, aggregate | 집계/통계 쿼리 지원 | await User.annotate(count=Count("posts")) |
python-jose
jose.jwt 모듈 — (JWT 인코딩/디코딩 핵심)
| 메서드 | 설명 | 예시 |
|---|
jwt.encode(claims, key, algorithm='HS256') | 주어진 데이터(claims)를 비밀키(key)로 서명하여 JWT 문자열을 생성 | jwt.encode({"sub": "kihoon"}, SECRET_KEY, "HS256") |
jwt.decode(token, key, algorithms=['HS256']) | JWT 문자열을 검증하고 payload(데이터)로 복호화 | jwt.decode(token, SECRET_KEY, ["HS256"]) |
jwt.get_unverified_header(token) | 서명을 검증하지 않고 헤더 부분만 추출 | jwt.get_unverified_header(token) → {'alg': 'HS256', 'typ': 'JWT'} |
jwt.get_unverified_claims(token) | 서명 검증 없이 payload(claims)만 읽기 (⚠️보안상 신뢰 금지) | jwt.get_unverified_claims(token) |
jose.exceptions 모듈 — (예외 클래스)
- from jose import JWTError, ExpiredSignatureError, JWTClaimsError
| 예외 클래스 | 발생 조건 | 설명 |
|---|
JWTError | JWT 관련 전반적 오류 (서명 실패, 구조 문제 등) | 가장 일반적인 오류 (보통 이걸로 처리) |
ExpiredSignatureError | "exp" 만료 시간이 지남 | 토큰 유효기간 초과 시 발생 |
JWTClaimsError | claim 값이 예상과 다름 | 예: "aud" 또는 "iss" 불일치 |
JWSError | JWS 서명 관련 오류 | |
JWEError | 암호화된 JWT(JWE) 처리 중 오류 | |
from jose import jwt, JWTError
try:
payload = jwt.decode(token, SECRET_KEY, algorithms=["HS256"])
except JWTError:
raise HTTPException(status_code=401, detail="Invalid token")
jose.constants — (상수 정의)
- from jose.constants import ALGORITHMS
| 상수 | 설명 |
|---|
ALGORITHMS.HS256, ALGORITHMS.HS384, ALGORITHMS.HS512 | HMAC + SHA 알고리즘 |
ALGORITHMS.RS256, ALGORITHMS.RS512 | RSA 서명 알고리즘 |
ALGORITHMS.ES256, ALGORITHMS.ES512 | ECDSA 서명 알고리즘 |
from jose.constants import ALGORITHMS
jwt.encode(payload, key, algorithm=ALGORITHMS.HS256)
jose.utils — (기초 암호화 유틸리티)
- from jose.utils import base64url_encode, base64url_decode
| 메서드 | 설명 |
|---|
base64url_encode(data: bytes) | URL-safe Base64 인코딩 |
base64url_decode(data: str) | Base64 URL-safe 디코딩 |
from jose.utils import base64url_encode, base64url_decode
b64 = base64url_encode(b"hello")
base64url_decode(b64)
(선택) JWK / JWS / JWE 관련 — 고급용
- FastAPI 인증 구현에서는 거의 안 쓰지만 참고용
| 모듈 | 용도 | 간단 설명 |
|---|
from jose import jws | JSON Web Signature | HMAC, RSA, ECDSA 서명/검증 |
from jose import jwe | JSON Web Encryption | 암호화된 JWT 처리 |
from jose import jwk | JSON Web Key | 공개키/비밀키 관리 |
from jose import jwa | JSON Web Algorithms | 알고리즘 내부 처리 모듈 |
passlib
- 비밀번호 해싱/검증 전용 보안 라이브러리
- 즉, 비밀번호를 안전하게 저장하고 비교하기 위한 표준 도구
핵심 객체: CryptContext
- 여러 해싱 알고리즘(bcrypt, argon2, pbkdf2 등)을 한곳에서 관리하고, 비밀번호 해싱과 검증을 담당
pwd_context = CryptContext(
schemes=["bcrypt"],
deprecated="auto",
)
- schemes: 사용할 해싱 알고리즘 리스트 (보통 "bcrypt", "argon2", "pbkdf2_sha256")
- deprecated: 이전 해시 버전을 자동으로 감지하여 경고 또는 업데이트 처리
- 보통 bcrypt 단독 사용이 가장 보편적
주요 메서드
| 메서드 | 설명 | 예시 |
|---|
hash(password) | 비밀번호를 암호화하여 해시 문자열 생성 | pwd_context.hash("1234") |
verify(plain, hashed) | 평문 비밀번호와 해시 비교 | pwd_context.verify("1234", hashed_pw) |
identify(hashed) | 주어진 해시가 어떤 알고리즘으로 만들어졌는지 확인 | pwd_context.identify(hashed_pw) → 'bcrypt' |
needs_update(hashed) | 해시가 오래된 알고리즘이면 True 반환 | pwd_context.needs_update(hashed_pw) |
update(**settings) | Context 설정을 동적으로 변경 | pwd_context.update(schemes=["argon2"]) |
encrypt(password) | (구버전) hash()와 동일하지만 deprecated | ❌ 사용 비추천 |
예시
from passlib.context import CryptContext
pwd_context = CryptContext(schemes=["bcrypt"], deprecated="auto")
hashed_pw = pwd_context.hash("mysecret")
print(hashed_pw)
pwd_context.verify("mysecret", hashed_pw)
pwd_context.verify("wrongpass", hashed_pw)
from passlib.hash import bcrypt
hashed = bcrypt.hash("1234")
print(bcrypt.verify("1234", hashed))
주요 해싱 알고리즘 객체들 (내부적으로 CryptContext가 사용)
| 알고리즘 | 객체 / 모듈 | 특징 |
|---|
| bcrypt | from passlib.hash import bcrypt | 가장 널리 쓰이는 안전한 해시, salt 자동 생성 |
| argon2 | from passlib.hash import argon2 | 가장 강력한 알고리즘 중 하나 (메모리 기반) |
| pbkdf2_sha256 | from passlib.hash import pbkdf2_sha256 | Django에서 기본으로 사용되는 알고리즘 |
| sha256_crypt | from passlib.hash import sha256_crypt | 단순 SHA 기반 (현재는 보안상 비추천) |
| md5_crypt | from passlib.hash import md5_crypt | 오래된 알고리즘 (❌ 비추천) |
설정 파일 기반 관리 (고급용)
- passlib은 .ini 스타일 설정 파일을 사용 가능
[passlib]
schemes = bcrypt, pbkdf2_sha256
default = bcrypt
deprecated = pbkdf2_sha256
pwd_context = CryptContext.from_path("passlib.ini")
FastAPI에서의 전형적 사용 구조
from passlib.context import CryptContext
pwd_context = CryptContext(schemes=["bcrypt"], deprecated="auto")
def get_password_hash(password: str) -> str:
return pwd_context.hash(password)
def verify_password(plain: str, hashed: str) -> bool:
return pwd_context.verify(plain, hashed)
Statistics
- 파이썬 statistics 모듈은 별도의 외부 라이브러리(NumPy, Pandas 등) 설치 없이,
- 파이썬 기본 리스트(List) 등을 사용하여 기본적인 통계 수치를 계산할 수 있게 해주는 표준 라이브러리
- statistics.mean(data): 산술 평균 (가장 많이 씀)
- statistics.median(data): 중앙값 (이상치에 영향을 덜 받음)
- statistics.mode(data): 최빈값 (가장 자주 나온 값)
- statistics.stdev(data): 표본 표준편차 (가장 많이 씀)
- statistics.variance(data): 표본 분산
- statistics.pstdev(data): 모표준편차 (데이터가 모집단 전체일 때)