๋ชจ๋ธ ์๋น์ด๋?
- ํ์ต๋ ๋จธ์ ๋ฌ๋ ๋ชจ๋ธ(pkl ํ์ผ)์ ์๋ฒ์ ์ฌ๋ ค ์ธ๋ถ์์ HTTP ์์ฒญ๋ก ์ ๋ ฅ๊ฐ์ ๋ณด๋ด๋ฉด ์๋ฒ๊ฐ ๋ชจ๋ธ์ ์ด์ฉํด ์์ธก ๊ฒฐ๊ณผ๋ฅผ ๋ฐํํ๋ ๊ตฌ์กฐ๋ฅผ ์๋ฏธํ๋ค.
- ๋ก์ปฌ์์ ๊ฐ๋ฐํ pkl ํ์ผ์ FastAPI ์๋ฒ๊ฐ ์์๋ ๋ ๋ฉ๋ชจ๋ฆฌ์ ์ฌ๋ ค๋๊ณ , API ์์ฒญ์ด ์ฌ ๋๋ง๋ค predict ํจ์๋ก ์์ธก์ ํด์ฃผ๋ ๊ฒ
pkl, h5, pt, pb ๊ฐ์ ๋ชจ๋ธ ํ์ผ์ "์ ์ ํ์ผ"์ด๋ผ๊ณ ์๊ฐํด๋ ๋๋?
- ์ ์ ํ์ผ์ ์น ๊ฐ๋ฐ์์ CSS, JS, ์ด๋ฏธ์ง, ํฐํธ ๋ฑ ์๋ฒ์์ ๋ด์ฉ์ด ๋ฐ๋์ง ์๊ณ ๊ทธ๋๋ก ์ ๊ณต๋๋ ๋ฆฌ์์ค๋ฅผ ์๋ฏธํ๋ค.
- ๋จธ์ ๋ฌ๋ ๋ชจ๋ธ ํ์ผ๋ "๋ด์ฉ์ด ๋ฐ๋์ง ์๊ณ , ์๋ฒ๊ฐ ํ์ํ ๋๋ง๋ค ๋ถ๋ฌ์ ์ฌ์ฉํ๋ ํ์ผ"์ด๋ผ๋ ์ ์์ ๋์ ์๋ฏธ๋ก ์ ์ ํ์ผ๋ก ๋ณผ ์ ์๋ค.
- ์ฆ, ๋ชจ๋ธ ํ์ผ์ ์น ์ ์ ํ์ผ๊ณผ๋ ๋ชฉ์ ์ด ๋ค๋ฅด์ง๋ง, "์๋ฒ๊ฐ ํ์ํ ๋ ๋ถ๋ฌ์ ์ฌ์ฉํ๋ ๋ณํ์ง ์๋ ๋ฆฌ์์ค"๋ผ๋ ์ ์์๋ ์ผ์ข ์ ์ ์ ํ์ผ๋ก ๋ณผ ์ ์๋ค.
์ง๋ ฌํ๋?
- ์ง๋ ฌํ๋ ํ์ด์ฌ ๊ฐ์ฒด(์: ํ์ต๋ ๋ชจ๋ธ, ๋์ ๋๋ฆฌ, ๋ฆฌ์คํธ ๋ฑ)๋ฅผ ํ์ผ์ด๋ ๋คํธ์ํฌ๋ก ์ ์ฅํ๊ฑฐ๋ ์ ์กํ ์ ์๋๋ก ์ด์ง ๋ฐ์ดํฐ๋ก ๋ณํํ๋ ๊ณผ์
- ๋ฐ๋๋ก, ํ์ผ์์ ๋ค์ ๊ฐ์ฒด๋ก ๋ณต์ํ๋ ๊ณผ์ ์ ์ญ์ง๋ ฌํ๋ผ๊ณ ํ๋ค.
์์
- scikit-learn ๋ชจ๋ธ์ pickle๋ก ์ ์ฅํ ๋: ๋ชจ๋ธ ๊ฐ์ฒด๋ฅผ ์ด์ง ๋ฐ์ดํฐ๋ก ๋ณํ(์ง๋ ฌํ)ํด์ ํ์ผ๋ก ์ ์ฅ
- FastAPI์์ pickle ํ์ผ์ ๋ถ๋ฌ์ฌ ๋:์ด์ง ํ์ผ์ ํ์ด์ฌ ๊ฐ์ฒด๋ก ๋ณต์(์ญ์ง๋ ฌํ)
์ ํ์ํ๊ฐ?
- ๋ชจ๋ธ์ ๋งค๋ฒ ์ฌํ์ตํ์ง ์๊ณ , ์ ์ฅํด๋๋ค๊ฐ ํ์ํ ๋ ๋น ๋ฅด๊ฒ ๋ถ๋ฌ์์ ๋ฐ๋ก ์์ธก์ ์ฌ์ฉํ ์ ์๊ธฐ ๋๋ฌธ
- pickle ํ์ผ์ ์ญํ
- ํ์ต์ด ๋๋ ๋ชจ๋ธ ๊ฐ์ฒด(ํ์ด์ฌ ๋ฉ๋ชจ๋ฆฌ ์์ ๋ชจ๋ธ)๋ฅผ ๋ฐ๋ก ๋ฐฐํฌํ๊ฑฐ๋ ๋ค๋ฅธ ํ๊ฒฝ์์ ์ธ ์ ์์ผ๋
- ๊ทธ ๋ชจ๋ธ ๊ฐ์ฒด๋ฅผ ์ง๋ ฌํํด์ ์ด์ง ๋ฐ์ดํฐ(ํ์ผ)๋ก ๋ง๋ ๋ค ์ด ํ์ผ์ ๋ค๋ฅธ ๊ณณ(์๋ฒ, ๋ค๋ฅธ ๊ฐ๋ฐ์, ๋ฐฐํฌ ํ๊ฒฝ ๋ฑ)์ผ๋ก ์ ๋ฌํ๊ฑฐ๋ ์ ์ฅํ๋ค.
๋ชจ๋ธ ์์ฑ ๋ฐ ์ ์ฅ
import pickle
from sklearn.datasets import fetch_california_housing
from sklearn.ensemble import RandomForestRegressor
# ๋ฐ์ดํฐ ๋ถ๋ฌ์ค๊ธฐ
data = fetch_california_housing()
X = data.data
y = data.target
# ๋ชจ๋ธ ํ์ต
model = RandomForestRegressor()
model.fit(X, y)
# ๋ชจ๋ธ ์ ์ฅ
with open("california_model.pkl", "wb") as f:
pickle.dump(model, f)
- ๋ผ์ด๋ธ๋ฌ๋ฆฌ import
- pickle: ํ์ด์ฌ ๊ฐ์ฒด๋ฅผ ํ์ผ๋ก ์ ์ฅ(์ง๋ ฌํ)ํ๊ณ , ๋์ค์ ๋ค์ ๋ถ๋ฌ์ฌ ๋(์ญ์ง๋ ฌํ) ์ฌ์ฉํ๋ ํ์ค ๋ผ์ด๋ธ๋ฌ๋ฆฌ
- RandomForestRegressor: ๋๋ค ํฌ๋ ์คํธ ํ๊ท ๋ชจ๋ธ
- ๋ฐ์ดํฐ ๋ถ๋ฌ์ค๊ธฐ
- data = fetch_california_housing(): ์บ๋ฆฌํฌ๋์ ์ฃผํ ๊ฐ๊ฒฉ ๋ฐ์ดํฐ์ ์ ๋ด๋ ค๋ฐ์ data ๋ณ์์ ์ ์ฅ
- X = data.data: ์ ๋ ฅ ๋ฐ์ดํฐ(ํน์ฑ, feature) 8๊ฐ๋ฅผ X์ ์ ์ฅ
- y = data.target: ์์ธก ๋์(ํ๊น), ์ฆ ํด๋น ๊ตฌ์ญ์ ์ค๊ฐ ์ง๊ฐ(๋จ์: 10๋ง ๋ฌ๋ฌ)์ y์ ์ ์ฅ
- ๋ชจ๋ธํ์ต
- model = RandomForestRegressor(): ๋๋ค ํฌ๋ ์คํธ ํ๊ท ๋ชจ๋ธ ๊ฐ์ฒด๋ฅผ ์์ฑ
- model.fit(X, y): ์ ๋ ฅ ๋ฐ์ดํฐ(X)์ ์ ๋ต(y)์ผ๋ก ๋ชจ๋ธ์ ํ์ต์ํจ๋ค.
- ์ด ๊ณผ์ ์ ํตํด ๋ชจ๋ธ์ด "ํน์ฑ → ์ง๊ฐ"์ ๊ด๊ณ๋ฅผ ํ์ต
- ๋ชจ๋ธ์ ์ฅ
- open("california_model.pkl", "wb"): ๋ชจ๋ธ์ ์ ์ฅํ ํ์ผ์ ์ด์ง ์ฐ๊ธฐ ๋ชจ๋๋ก ์ฐ๋ค.
- pickle.dump(model, f): ํ์ต๋ ๋ชจ๋ธ ๊ฐ์ฒด๋ฅผ ํ์ผ์ ์ ์ฅ(์ง๋ ฌํ)
- ์ด๋ ๊ฒ ์ ์ฅ๋ pkl ํ์ผ์ ๋์ค์ FastAPI์์ ๋ถ๋ฌ์ ๋ฐ๋ก ์์ธก์ ์ฌ์ฉํ ์ ์๋ค.
- ์ ๋ฆฌํ๋ฉด ์บ๋ฆฌํฌ๋์ ์ง๊ฐ ๋ฐ์ดํฐ์ ์ ๋ถ๋ฌ์์ ๋๋ค ํฌ๋ ์คํธ ํ๊ท ๋ชจ๋ธ๋ก ํ์ตํ ๋ค ํ์ต๋ ๋ชจ๋ธ์ pkl ํ์ผ๋ก ์ ์ฅํ๋ ์ฝ๋
- ์ด๋ ๊ฒ ์ ์ฅ๋ ๋ชจ๋ธ ํ์ผ์ API ์๋ฒ์์ ๋ถ๋ฌ์ ์๋นํ๋ฉด, ์ ๋ ฅ๊ฐ(ํน์ฑ 8๊ฐ)์ ๋ฐ์ ์ง๊ฐ์ ์์ธก ๊ฐ๋ฅ
import pickle
import numpy as np
from fastapi import FastAPI
from pydantic import BaseModel
from fastapi.middleware.cors import CORSMiddleware
app = FastAPI()
'''
HouseInput: API๋ก ๋ฐ์ ์
๋ ฅ๊ฐ์ ๊ตฌ์กฐ๋ฅผ ์ ์
๊ฐ ํ๋๋ ์บ๋ฆฌํฌ๋์ ์ง๊ฐ ๋ฐ์ดํฐ์
์ feature์ ์ ํํ ์ผ์นํด์ผ ํ๋ค.
'''
# ์
๋ ฅ ๋ฐ์ดํฐ ๊ตฌ์กฐ ์ ์
class HouseInput(BaseModel):
MedInc: float # ์ค๊ฐ ์๋
HouseAge: float # ์ฃผํ ์ฐ์
AveRooms: float # ํ๊ท ๋ฐฉ ๊ฐ์
AveBedrms: float # ํ๊ท ์นจ์ค ๊ฐ์
Population: float # ์ธ๊ตฌ ์
AveOccup: float # ํ๊ท ๊ฐ๊ตฌ์ ์
Latitude: float # ์๋
Longitude: float # ๊ฒฝ๋
'''
FastAPI ์ต์ด ์คํ ์ ์คํ๋๋ ํจ์
with open("app/california_model.pkl", "rb") as f: ์ ์ฅ๋ pkl ํ์ผ์ ์ฝ๊ธฐ ๋ชจ๋๋ก ์ด๊ณ ,
pickle.load(f): ํ์ผ์์ ํ์ต๋ ๋ชจ๋ธ ๊ฐ์ฒด๋ฅผ ๋ณต์(์ญ์ง๋ ฌํ)
์ด์ ์๋ฒ๊ฐ ์ผ์ง ํ์๋, API ์์ฒญ๋ง๋ค ๋ชจ๋ธ์ ์๋ก ๋ถ๋ฌ์ฌ ํ์ ์์ด, ๋ฉ๋ชจ๋ฆฌ์ ์ฌ๋ ค๋ ๋ชจ๋ธ์ ๋ฐ๋ก ์ฌ์ฉํ ์ ์๋ค.
'''
@app.on_event("startup")
def load_model():
global model
with open("app/california_model.pkl", "rb") as f:
model = pickle.load(f)
'''
input: HouseInput: ์
๋ ฅ๊ฐ์ด HouseInput ๊ตฌ์กฐ๋ฅผ ๋ฐ๋ผ์ผ ํจ์ ๋ช
์
X = np.array([[...]]): ์
๋ ฅ๊ฐ์ 2์ฐจ์ ๋ฐฐ์ด๋ก ๋ณํ(scikit-learn ๋ชจ๋ธ์ ํญ์ 2์ฐจ์ ๋ฐฐ์ด์ ์
๋ ฅ์ผ๋ก ๋ฐ์)
model.predict(X): ์
๋ ฅ๊ฐ์ ๋ํด ๋ชจ๋ธ์ด ์ง๊ฐ์ ์์ธก
'''
@app.post("/predict")
def predict(input: HouseInput):
X = np.array([[input.MedInc, input.HouseAge, input.AveRooms, input.AveBedrms,
input.Population, input.AveOccup, input.Latitude, input.Longitude]])
y_pred = model.predict(X)
return {"predicted_house_value($100,000)": float(y_pred[0])}
์ค์จ๊ฑฐ๋ก ํ ์คํธ
{
"predicted_house_value($100,000)": 4.400230700000003
}
'๐ผ ๋ฐฑ์ค๋ > Fast API' ์นดํ ๊ณ ๋ฆฌ์ ๋ค๋ฅธ ๊ธ
Fast API - ORM (0) | 2025.06.24 |
---|---|
Fast API - ์ฑ๋ฅ ๊ฐ์ (0) | 2025.06.23 |
Fast API - ๊ธฐ๋ฅ (3) | 2025.06.23 |
Fast API - ๊ธฐ์ด (3) | 2025.06.18 |