Optuna hiperparaméter hangolás Pythonban: Teljes útmutató 2026

Gyakorlati útmutató az Optuna 4.x hiperparaméter optimalizáló könyvtárhoz Pythonban: TPE sampler, pruning, scikit-learn és XGBoost integráció, Dashboard és többcélú optimalizáció 2026-ban.

Optuna hiperparaméter hangolás 2026

Frissítve: 2026. június 15.

Az Optuna egy nyílt forráskódú, automatikus hiperparaméter-optimalizáló keretrendszer Pythonhoz, amely Bayes-i mintavételezést (TPE), korai leállítást (pruning) és párhuzamos kereséseket használ a legjobb modellbeállítások megtalálásához. A 2026-os Optuna 4.x verzió kompatibilis a scikit-learn, XGBoost, LightGBM, PyTorch és TensorFlow ökoszisztémákkal, és nagyságrendekkel gyorsabban talál jó hiperparamétereket, mint a klasszikus GridSearchCV. Ebben az útmutatóban végigvesszük az Optuna teljes munkafolyamatát a Study és Trial objektumoktól a samplereken és prunereken át a Dashboardig.

  • Az Optuna 4.x (2026) alapértelmezett samplere a TPE (Tree-structured Parzen Estimator), amely lényegesen hatékonyabb a véletlenszerű vagy rácsos keresésnél magas dimenziójú terekben.
  • A MedianPruner és HyperbandPruner a gyengén teljesítő trialeket korán leállítja, így a számítási idő 30–70%-kal csökkenthető.
  • Az Optuna integrálható a scikit-learn, XGBoost, LightGBM, PyTorch Lightning és Keras keretrendszerekkel egy callback vagy OptunaSearchCV wrapperrel.
  • Az optuna-dashboard valós idejű webes felületet ad a trial-ek vizualizálásához, paraméterfontosság-elemzéshez és párhuzamos koordináta-diagramokhoz.
  • Több cél (multi-objective) optimalizálás támogatott NSGA-II és NSGA-III samplerekkel, ami például pontosság és inferencia-idő egyidejű optimalizálását teszi lehetővé.
  • Az RDB storage (SQLite/PostgreSQL) lehetővé teszi az elosztott, párhuzamos hangolást több gépen ugyanazon Study-ban.

Mire használjuk az Optunát?

Az Optuna egy Python nyelvű hiperparaméter-optimalizáló (HPO) keretrendszer, amelyet eredetileg a Preferred Networks fejlesztett ki, és ma de facto szabvány a gépi tanulási projektekben. A fő használati esetek: gépi tanulási modellek tanulási rátájának, regularizációs együtthatóinak, fa-mélységének, batch méretének és további több tíz paraméterének automatikus megkeresése, hogy maximalizáljunk egy validációs metrikát (pl. ROC AUC, F1, RMSE).

Őszintén szólva, a klasszikus alternatívák (a sklearn.model_selection.GridSearchCV és a RandomizedSearchCV) két nyilvánvaló problémával küzdenek. A rácsos keresés exponenciálisan robban a paraméterek számával, a véletlenszerű keresés pedig nem tanul az előző trialekből. Az Optuna ezzel szemben szekvenciális modell-alapú optimalizálást (SMBO) végez: minden befejezett trial alapján frissíti a valószínűségi modelljét arról, hogy mely paramétertér-régiók ígéretesek, és a következő trialhez ezeket választja.

Egy tipikus tanulmány azt mutatja, hogy egy 100 trial-es Optuna futás ugyanazt vagy jobb eredményt ér el, mint egy 1000+ pontos rácsos keresés, különösen akkor, ha 5-nél több hiperparamétert hangolunk egyszerre. A 2026-os 4.x sorozat bevezette a továbbfejlesztett GPSampler-t (Gaussian Process-alapú), amely különösen kis trial-budget esetén (≤50) hatékony.

Egy korábbi ügyfél-projektünkben (egy közepes méretű LightGBM ranker modell, kb. 18 hiperparaméter) egyetlen hétvége alatt 30 órás GridSearchCV futás után álltunk át Optunára. Két óra elteltével az új best score 1,4 NDCG@10 ponttal lett magasabb, mint az egész éjszakás rács. Azóta nem nyúltam újra grid search-höz, hacsak nem két-három paraméterről van szó.

Telepítés és az első Study

Az Optuna telepítése egyszerű pip-pel vagy conda-val. 2026 júniusában a legújabb stabil verzió a 4.2.x. A vizualizációkhoz a plotly opcionális, de erősen ajánlott.

pip install optuna optuna-dashboard plotly scikit-learn

A legkisebb működő példa egy egyszerű kvadratikus függvény minimalizálása. Az Optuna két kulcsfogalmat használ: a Study az egész optimalizálási kísérlet, a Trial pedig egy konkrét paraméterbeállítással történt egyetlen futás.

import optuna

def objective(trial: optuna.Trial) -> float:
    # Egy lebegopontos parametert javaslunk -10 es 10 kozott
    x = trial.suggest_float("x", -10.0, 10.0)
    # A celfuggveny: (x-2)^2, minimuma x=2-nel van
    return (x - 2) ** 2

# A study iranya: minimalizalas (alapertelmezett) vagy maximalizalas
study = optuna.create_study(direction="minimize")
study.optimize(objective, n_trials=50, show_progress_bar=True)

print("Legjobb x:", study.best_params)
print("Legjobb ertek:", study.best_value)

50 trial után az x értéke 2.0 közelébe konvergál. A study.trials_dataframe() hívással az összes trial-t Pandas DataFrame-ként kapjuk meg, ami remek belépési pont a következő lépéshez: az adatvizualizációs eszközökkel történő utólagos elemzéshez.

Suggest függvények és a paramétertér definiálása

Az Optuna define-by-run API-t használ. Ez azt jelenti, hogy a paramétertér nem előre, statikusan megadott, hanem a trial.suggest_* függvényeken keresztül dinamikusan jön létre a célfüggvény futása során. Pont ez teszi lehetővé a feltételes paramétereket (pl. ha az algoritmus „SVM", akkor van kernel paraméter, ha „RandomForest", akkor n_estimators).

A legfontosabb suggest függvények:

  • trial.suggest_float(name, low, high, log=False, step=None): folytonos paraméter; log=True ajánlott tanulási rátához (1e-5 → 1e-1).
  • trial.suggest_int(name, low, high, log=False, step=1): egész paraméter, pl. n_estimators, max_depth.
  • trial.suggest_categorical(name, choices): diszkrét lista, pl. optimalizáló neve vagy aktivációs függvény.
def objective(trial):
    classifier_name = trial.suggest_categorical("classifier", ["SVC", "RandomForest"])
    if classifier_name == "SVC":
        svc_c = trial.suggest_float("svc_c", 1e-3, 1e3, log=True)
        kernel = trial.suggest_categorical("svc_kernel", ["linear", "rbf"])
        # ... modell betanitas
    else:
        n_est = trial.suggest_int("rf_n_estimators", 50, 500, step=50)
        max_depth = trial.suggest_int("rf_max_depth", 3, 20)
        # ... modell betanitas
    return validation_score

A log=True kapcsoló kritikus a több nagyságrendet átfedő paramétereknél (tanulási ráta, regularizációs együttható), enélkül a sampler aránytalanul sok időt tölt a felső intervallumban. A step paraméter pedig diszkretizál, és hasznos a batch_size vagy n_estimators hangolásánál.

Samplerek: TPE, CMA-ES és NSGA-II

A sampler az Optuna „agya": ő dönti el, milyen paraméterértékeket javasoljon a következő trial-hez. 2026-ban öt elsődleges sampler érhető el:

SamplerMikor használdTrial számParam. típus
TPESampler (alapért.)Általános HPO, jó alapérték50–1000Vegyes
RandomSamplerBaseline összehasonlításBármiVegyes
CmaEsSamplerFolytonos terek, sima célfügg.100+Csak float
GPSampler (Optuna 4.x)Drága célfügg., kevés trial≤50Vegyes
NSGAIISamplerTöbb cél optimalizálása200+Vegyes

Az alapértelmezett TPESampler a legtöbb feladatban kiváló választás. Algoritmusa: az eddigi trialeket két csoportra osztja (jó és rossz), két Parzen-becslőt illeszt rájuk, majd onnan mintavételez, ahol a jó/rossz arány a legnagyobb. A részletes matematikai háttér megtalálható az Optuna hivatalos dokumentációjában.

from optuna.samplers import TPESampler, GPSampler

# TPE explicit konfiguracio: elso 10 trial veletlenszeru (cold start)
sampler = TPESampler(n_startup_trials=10, multivariate=True, seed=42)
study = optuna.create_study(sampler=sampler, direction="maximize")

# Draga deep learning futashoz GP sampler keves trial-lel
sampler_gp = GPSampler(n_startup_trials=5, seed=42)

Pruning: gyenge trialek korai leállítása

A pruning (vagy korai leállítás) a gyengén teljesítő trialeket még a tanítás vége előtt megszakítja, így spórolva drága GPU/CPU-időt. Az Optuna ehhez a trial.report(value, step) és trial.should_prune() hívásokat használja: az iterációs tanulási ciklus minden epoch-ja után jelented az aktuális validációs metrikát, és az Optuna eldönti, érdemes-e folytatni.

import optuna
from optuna.pruners import MedianPruner, HyperbandPruner

def objective(trial):
    lr = trial.suggest_float("lr", 1e-5, 1e-1, log=True)
    n_layers = trial.suggest_int("n_layers", 1, 5)

    model = build_model(lr, n_layers)
    for epoch in range(50):
        val_score = model.train_one_epoch()
        # Jelentjuk a koztes eredmenyt
        trial.report(val_score, epoch)
        # Ha a pruner ugy donti, megszakitjuk
        if trial.should_prune():
            raise optuna.TrialPruned()
    return val_score

# MedianPruner: leallit, ha az adott step-nel a trial gyengebb,
# mint a korabbi trial-ek medianja
pruner = MedianPruner(n_startup_trials=5, n_warmup_steps=10)
study = optuna.create_study(direction="maximize", pruner=pruner)
study.optimize(objective, n_trials=100)

A két leggyakoribb pruner:

  • MedianPruner: egyszerű, megbízható, jó alapérték.
  • HyperbandPruner: bracketing alapú, agresszívabb leállítás, ideális mély tanuláshoz (PyTorch, Keras).

Gyakorlati tapasztalat: egy 100 trial-es deep learning HPO-nál a HyperbandPruner az össz futási időt 60–70%-kal csökkentheti. A hasznos trialek továbbra is teljesen lefutnak, csak a reménytelenek halnak el korán.

Optuna és scikit-learn integráció

Az scikit-learn ökoszisztémával az Optuna kétféleképp dolgozhat: vagy manuálisan írod a cross_val_score hívást a célfüggvénybe, vagy használod a kényelmes optuna.integration.OptunaSearchCV wrappert, amely API-kompatibilis a GridSearchCV-vel.

import optuna
from sklearn.datasets import load_iris
from sklearn.ensemble import RandomForestClassifier
from sklearn.model_selection import cross_val_score

X, y = load_iris(return_X_y=True)

def objective(trial):
    params = {
        "n_estimators": trial.suggest_int("n_estimators", 50, 500, step=50),
        "max_depth": trial.suggest_int("max_depth", 3, 20),
        "min_samples_split": trial.suggest_int("min_samples_split", 2, 20),
        "max_features": trial.suggest_categorical("max_features", ["sqrt", "log2"]),
    }
    clf = RandomForestClassifier(**params, random_state=42, n_jobs=-1)
    return cross_val_score(clf, X, y, cv=5, scoring="accuracy").mean()

study = optuna.create_study(direction="maximize")
study.optimize(objective, n_trials=100, n_jobs=4)
print(study.best_params)

Ha már Pipeline-okat és ColumnTransformer-eket használsz a feldolgozásban (lásd a scikit-learn Pipeline és ColumnTransformer útmutatót), egyszerűen a teljes pipeline-t add át a cross_val_score-nak, és Optunával hangold a transformerek és a végső becslő paramétereit egyszerre (pl. imputer__strategy és classifier__C).

XGBoost és LightGBM hangolása Optunával

A gradient boosting modellek hangolása az Optuna egyik legértékesebb használati esete, mert ezekben a könyvtárakban 10+ hiperparaméter van, és a num_boost_round + learning_rate kombináció miatt a pruning különösen hatékony. Az alábbi példa XGBoost-tal:

import optuna
import xgboost as xgb
from sklearn.datasets import load_breast_cancer
from sklearn.model_selection import train_test_split

X, y = load_breast_cancer(return_X_y=True)
X_tr, X_va, y_tr, y_va = train_test_split(X, y, test_size=0.2, random_state=42)
dtrain = xgb.DMatrix(X_tr, label=y_tr)
dvalid = xgb.DMatrix(X_va, label=y_va)

def objective(trial):
    params = {
        "objective": "binary:logistic",
        "eval_metric": "auc",
        "tree_method": "hist",  # GPU-ra: "gpu_hist"
        "learning_rate": trial.suggest_float("learning_rate", 1e-3, 0.3, log=True),
        "max_depth": trial.suggest_int("max_depth", 3, 12),
        "subsample": trial.suggest_float("subsample", 0.5, 1.0),
        "colsample_bytree": trial.suggest_float("colsample_bytree", 0.5, 1.0),
        "min_child_weight": trial.suggest_int("min_child_weight", 1, 10),
        "reg_lambda": trial.suggest_float("reg_lambda", 1e-3, 10.0, log=True),
    }
    pruning_cb = optuna.integration.XGBoostPruningCallback(trial, "validation-auc")
    booster = xgb.train(params, dtrain, num_boost_round=1000,
                        evals=[(dvalid, "validation")],
                        callbacks=[pruning_cb], early_stopping_rounds=50,
                        verbose_eval=False)
    return booster.best_score

study = optuna.create_study(direction="maximize",
                            pruner=optuna.pruners.MedianPruner())
study.optimize(objective, n_trials=200, timeout=600)

Az XGBoostPruningCallback minden boosting iteráció után jelenti az AUC-t az Optunának, így a gyenge trialek a 20-30. iteráció környékén leállnak ahelyett, hogy mind az 1000-et lefuttatnák. LightGBM-hez ugyanez a minta LightGBMPruningCallback-kel működik. Ha még nem választottál a fő gradient boosting könyvtárak között, érdemes elolvasni az XGBoost vs LightGBM vs CatBoost összehasonlítást.

Optuna Dashboard és vizualizációk

Az optuna-dashboard egy önálló webalkalmazás, amely valós időben mutatja a futó Study haladását: optimalizációs történet, paraméterfontosság, kontúrdiagramok, párhuzamos koordináta-ábrák. Indítása triviális, ha RDB storage-ot használsz:

# A Study-t SQLite fajlba mentjuk
study = optuna.create_study(
    study_name="xgb_breast_cancer",
    storage="sqlite:///optuna_studies.db",
    direction="maximize",
    load_if_exists=True,
)
study.optimize(objective, n_trials=200)

# Kulon terminalban:
# optuna-dashboard sqlite:///optuna_studies.db

A dashboard a http://localhost:8080 címen elérhető, és az alábbi nézeteket adja:

  • Optimization History: trialek értékei az időben.
  • Parameter Importances: fANOVA alapú fontosság-elemzés, hogy melyik paraméter számít a legtöbbet.
  • Slice Plot: egy paraméter hatása a célfüggvényre.
  • Parallel Coordinate Plot: minden paraméter és a célérték egy ábrán.

Programatikusan ugyanezeket a optuna.visualization modullal (Plotly-alapú) érheted el:

import optuna.visualization as vis
fig = vis.plot_param_importances(study)
fig.show()

Több cél optimalizálása NSGA-II-vel

A gyakorlatban gyakran nemcsak pontosság, hanem inferencia-idő, modellméret vagy memóriaigény is számít. Az Optuna 3.x óta natívan támogatja a többcélú optimalizálást: a célfüggvény nem egy számot, hanem egy tuple-t ad vissza, és az Optuna Pareto-frontot keres.

import optuna
from optuna.samplers import NSGAIISampler

def objective(trial):
    # ... modell betanitas
    accuracy = compute_accuracy(model)
    inference_ms = measure_inference_time(model)
    return accuracy, inference_ms  # max accuracy, min latency

study = optuna.create_study(
    directions=["maximize", "minimize"],
    sampler=NSGAIISampler(population_size=50, seed=42),
)
study.optimize(objective, n_trials=200)

# Pareto-optimalis trial-ek
for t in study.best_trials:
    print(t.params, t.values)

A study.best_trials a Pareto-front pontjait adja vissza. Ezek között a felhasználói preferencia (pl. „90% pontosság feletti leggyorsabb modell") alapján választhatsz. A módszer matematikai hátteréhez ajánlott olvasmány a eredeti Optuna kutatási publikáció.

Elosztott hangolás RDB storage-dzsal

Több gépen vagy több folyamatban párhuzamosan futtathatod ugyanazt a Study-t, ha közös storage backend-et használsz. A trialeket az Optuna automatikusan koordinálja:

# Gep 1, 2, 3 ... ugyanezt a kodot futtatja
study = optuna.create_study(
    study_name="distributed_hpo",
    storage="postgresql://user:pass@db-host:5432/optuna_db",
    load_if_exists=True,
    direction="maximize",
)
study.optimize(objective, n_trials=100)  # gepenkent 100, ossz: 300

SQLite is működik kis projekteknél, de éles, sok-workeres elosztott futáshoz PostgreSQL vagy MySQL ajánlott a tranzakciók és a sorzárak miatt. A storage opcionális; az in-memory None alapértelmezetten gyorsabb, de a Study a futás végén elveszik. Az RDB lehetővé teszi a resume-ot is: ha leállítod a futást, később onnan folytatódhat.

Gyakran ismételt kérdések

Mi a különbség az Optuna és a GridSearchCV között?

A GridSearchCV minden paraméterkombinációt kipróbál (exhaustive), míg az Optuna Bayes-i mintavételezéssel (TPE) tanul az előző trialek eredményeiből, és csak az ígéretes régiókat tárja fel. Tipikusan 5-10x kevesebb trial-lel ér el ugyanolyan vagy jobb eredményt, és támogatja a pruningot is.

Hány trial szükséges egy jó Optuna optimalizáláshoz?

Általános szabály: a paraméterek számának 20-50-szerese. 5 hiperparaméternél 100-200 trial elegendő. Mély tanulási modelleknél pruninggal 50-100 trial is jó eredményt ad, mert a rossz trial-ek korán leállnak.

Hogyan reprodukálhatóak az Optuna eredmények?

Add meg a sampler-nek a seed paramétert (pl. TPESampler(seed=42)) és rögzítsd a numpy/torch/random seedjeit is a célfüggvényben. Az RDB storage-ben tárolt Study load_if_exists=True-val pontosan onnan folytatódik, ahol abbahagytad.

Használhatom az Optunát PyTorch és Keras modellekhez?

Igen. Az optuna.integration modul tartalmaz callback-eket PyTorch Lightninghez, Keras-hoz, FastAI-hez, MLflow-hoz és Weights & Biases-hez. A trial.report() + trial.should_prune() mintával bármilyen iteratív tanulási hurokba integrálható.

Mikor érdemes a GPSampler-t használni a TPE helyett?

Ha egy trial nagyon drága (pl. nagy nyelvi modell finomhangolás, ahol egy futás 1+ óra), és a teljes budgeted ≤50 trial, a GPSampler jobb mintaháztartású, mint a TPE. 100+ trial felett a TPE általában gyorsabb és jobban skálázódik.

Editorial Team
A Szerzőről Editorial Team

Our team of expert writers and editors.