Automl Tools Compared Google Aws Azure H2O And Aut
You’ve spent three days trying 47 different scikit‑learn pipeline variants. You swapped imputation strategies, scaled features three different ways, tried four feature selectors, and tested a dozen classifiers with hand‑tuned hyperparameters. Your Kaggle score went from 0.812 to 0.814. That’s the pain point. It’s not that the work is hard—it’s that the work is tedious, repetitive, and feels like guessing. What if a machine could do the guessing for you?
That’s the promise of AutoML. But here’s the catch: AutoML isn’t a magical AI that replaces data scientists. It’s a systematic search engine for model pipelines. It automates the grind, not the thinking. And the five tools we’ll explore in this article represent two fundamentally different philosophies: managed cloud services (Google Vertex AI, AWS SageMaker Autopilot, Azure AutoML) versus open‑source libraries you run yourself (H2O AutoML, auto‑sklearn). This distinction matters more than any feature checklist. Let’s understand why.
1. The Problem AutoML Actually Solves (It’s Not What You Think)
Think of building a machine learning pipeline like exploring a huge, dark room looking for a light switch. You know the switch is in there somewhere, but the room is full of furniture—preprocessing choices, algorithm families, hyperparameter values—and you have to feel your way around in the dark. Every time you bump into a chair (a bad imputation strategy) or a table (a learning rate that’s too high), you waste time and energy. AutoML tools are like giving a robot a flashlight and a systematic search pattern. They don’t know what the room looks like any better than you do, but they can methodically check every corner without getting tired or frustrated.
What’s actually going on here? The real bottleneck in applied machine learning isn’t coding. It’s the combinatorial explosion of choices. Let’s make that concrete. Suppose you’re working on a tabular classification problem and you consider:
- 5 imputation strategies (mean, median, mode, constant, KNN)
- 4 scalers (StandardScaler, MinMaxScaler, RobustScaler, no scaling)
- 3 feature selectors (SelectKBest, RFE, no selection)
- 10 classifiers (Logistic Regression, Random Forest, XGBoost, LightGBM, CatBoost, SVM, KNN, Gradient Boosting, Extra Trees, MLP)
That’s 5 × 4 × 3 × 10 = 600 pipelines. And that’s before you tune a single hyperparameter. If each classifier has, say, 3 key hyperparameters with 5 possible values each, you’re looking at 600 × 5³ = 75,000 configurations. You can’t try them all by hand. You probably shouldn’t even try—most of those configurations will be terrible, and you’ll waste time on dead ends.
AutoML tools are fundamentally search‑and‑ensemble engines. They automate the systematic exploration of this huge space. They try many pipelines, evaluate them, and often combine the best ones into an ensemble that’s better than any single model. But they’re not creative problem‑solvers. They won’t notice that your “customer_age” column is actually “years_since_first_purchase” and should be treated differently. They won’t derive a “profit_margin” feature from “revenue” and “cost.” They won’t question whether your training data leaked future information. That’s still your job.
The two philosophies—managed cloud vs. open‑source—shape everything about how you’ll use these tools. Managed cloud AutoML (Google Vertex AI, AWS SageMaker Autopilot, Azure AutoML) handles the compute infrastructure, stores your data in the cloud, and gives you a polished interface. You pay for the convenience and the integration. Open‑source AutoML (H2O AutoML, auto‑sklearn) runs wherever you want—your laptop, your on‑premises cluster, your own cloud VM—and you control every detail. You pay with your own time and compute resources. Neither philosophy is “better.” They’re different answers to different constraints.
2. The Five Tools at a Glance: What Each One Promises
Before we dive under the hood, let’s meet the cast. Here’s what each tool is, who it’s for, and the one‑sentence version of how it works.
Google Vertex AI AutoML is a managed service inside the broader Google Cloud ecosystem. It covers tabular data, images, text, and video. You can use it through a web GUI or an API. When you train a model, Google handles the infrastructure, the architecture search, and the deployment. You’re not just buying AutoML—you’re buying into Google Cloud’s entire ML platform, from data storage (BigQuery) to model monitoring (Vertex AI Model Monitoring). The key differentiator: Google’s immense pre‑existing model zoos and neural‑architecture‑search research give it an edge on complex data types like images and text.
AWS SageMaker Autopilot is Amazon’s managed AutoML for tabular data. As of late 2023, the standalone Autopilot UI was folded into SageMaker Canvas (a no‑code tool), and the primary programmatic interface is now the SageMaker SDK. Autopilot automatically analyzes your data, engineers features, selects algorithms, and tunes hyperparameters. It produces a ranked list of candidate models, and you can deploy any of them with a single click. The key differentiator: deep integration with the rest of SageMaker for deployment, monitoring, and MLOps—if you’re already in the AWS world, Autopilot fits like a glove.
Azure AutoML is Microsoft’s managed AutoML, and it has the most broadly documented task coverage of the three clouds. It handles tabular data (classification, regression, forecasting), computer vision, and NLP with support for 104 languages. You can use it through Azure Machine Learning Studio (GUI), the Python SDK, or a REST API. By default, it uses ensemble methods—both voting and stacking—to combine the best models it finds. The key differentiator: transparency. Azure documents its ensemble algorithm (Caruana ensemble selection) and its preprocessing steps more openly than Google or AWS. If you want to understand what’s happening under the hood, Azure gives you the most to work with.
H2O AutoML is an open‑source library that runs locally or on your own cluster. Its API is beautifully minimal: point it at your data, set a time limit, and get a ranked leaderboard. It trains a wide variety of models (XGBoost, GBM, GLM, Random Forest, Deep Neural Net, Extremely Randomized Forest) plus random‑grid searches over the most promising ones, then builds two stacked ensembles on top. The key differentiator: no cloud lock‑in, no usage fees, and a brute‑force thoroughness that’s hard to beat if you have the compute. But you manage the compute yourself.
auto‑sklearn is an open‑source library that’s designed to be a drop‑in replacement for a scikit‑learn estimator. It uses Bayesian optimization to efficiently explore the pipeline space and meta‑learning to warm‑start the search based on what worked on similar datasets in the past. It then builds an ensemble from the best pipelines found. The key differentiator: sample efficiency. auto‑sklearn is designed to find good models with relatively few trials, making it ideal when compute is limited. But there’s an important caveat: as of 2023, auto‑sklearn’s maintenance status is uncertain. It’s pinned to an old scikit‑learn version, and the maintainers haven’t responded to community concerns about compatibility. Use it with caution.
Here’s a comparison table to keep things straight:
| Tool | Managed / OSS | Primary Interface | Task Coverage | Key Differentiator |
|---|---|---|---|---|
| Google Vertex AI AutoML | Managed (GCP) | GUI + API | Tabular, image, text, video | Google’s model zoos & architecture search |
| AWS SageMaker Autopilot | Managed (AWS) | SDK (Canvas for no‑code) | Tabular | Deep SageMaker integration for MLOps |
| Azure AutoML | Managed (Azure) | GUI + Python SDK + REST | Tabular, vision, NLP (104 languages) | Transparent ensemble algorithm & preprocessing |
| H2O AutoML | Open‑source | Python / R API | Tabular | Brute‑force thoroughness, no cloud lock‑in |
| auto‑sklearn | Open‑source | scikit‑learn compatible | Tabular | Bayesian optimization + meta‑learning for sample efficiency |
Now here’s the interesting part: the biggest difference between these tools isn’t their feature lists. It’s what happens when you press “train.” Let’s look under the hood.
3. What Happens When You Press “Train”: The Search Strategies Under the Hood
“AutoML” isn’t one algorithm. It’s a search strategy wrapped around many algorithms. When you press “train,” each tool launches a fundamentally different kind of search. That choice determines how the tool behaves on your data—how fast it converges, how likely it is to overfit, and what kinds of models it tends to produce.
Let’s go back to our dark‑room analogy. You’re looking for the light switch. Here are five different ways to search:
- Brute‑force breadth (H2O): Turn on all the lights at once and see which switch worked. Try a fixed set of models, do random searches over the most promising ones, and ensemble the best. This is exhaustive but expensive—you need a lot of electricity (compute).
- Bayesian optimization with a map (auto‑sklearn): You have a rough map of the room based on what worked in other, similar rooms. You use that map to start near where the switch probably is, then use Bayesian reasoning to efficiently explore the most promising areas. This is sample‑efficient but depends on the map being good.
- Proprietary multi‑stage search (Google, AWS): You hire a professional search team. They have their own methods, their own tools, and they don’t tell you exactly how they work. They just deliver a result. You pay for their expertise and their equipment.
- Transparent ensemble search (Azure): You hire a search team that shows you their playbook. They tell you they’re using the Caruana ensemble selection algorithm, they show you which models they tried, and they explain how they combined them. You pay for the service and the transparency.
Let’s unpack each one in detail.
Google Vertex AI AutoML uses architecture search and transfer learning. Google is opaque about the exact search algorithm—the public documentation describes the AutoML training process at a high level but doesn’t detail the search strategy. What we do know: for tabular data, Google often ensembles multiple architectures, leveraging pre‑existing model zoos and neural‑architecture‑search research. For images and text, it uses transfer learning from massive pre‑trained models. The opacity is a tradeoff: you get Google’s best research without having to understand it, but you can’t inspect or modify the search process.
AWS SageMaker Autopilot uses a multi‑stage process: data analysis → feature engineering → algorithm selection → hyperparameter tuning. The documentation describes these stages clearly, but the exact search strategy within each stage is proprietary. Autopilot automatically generates candidate pipelines, evaluates them, and produces a ranked list. You can inspect the notebooks it generates to see what features it engineered and which algorithms it tried, but you can’t control the search strategy itself.
Azure AutoML uses the Caruana ensemble selection algorithm with both voting and stacking ensembles enabled by default. This is the most transparently documented search strategy of the three clouds. The algorithm works by iteratively adding models to an ensemble, greedily selecting the model that most improves the ensemble’s validation score. It also applies preprocessing—missing‑value imputation, encoding, scaling, and class balancing—as part of the search. Because Azure documents this openly, you can reason about what the tool is doing and why it might fail.
H2O AutoML uses brute‑force breadth. It trains a fixed set of base models: XGBoost, GBM, GLM, Random Forest, Deep Neural Net, and Extremely Randomized Forest. Then it runs random‑grid searches over XGBoost, GBM, and Deep Neural Nets. Finally, it builds two stacked ensembles: one using all the models, and one using only the best model from each algorithm family. The “search” is exhaustive within a time budget—not Bayesian, not meta‑learning, just “try a lot of things and ensemble the best.” This approach is compute‑hungry but transparent: you know exactly which models were tried, and you can inspect every one of them.
auto‑sklearn uses Bayesian optimization with meta‑learning warm‑starting. This is the most research‑driven approach. Bayesian optimization builds a probabilistic model of how pipeline choices relate to performance, then uses that model to intelligently choose the next pipeline to try—balancing exploration (trying new things) and exploitation (refining what’s working). Meta‑learning gives it a head start: auto‑sklearn has a database of how hundreds of pipelines performed on hundreds of datasets, and it uses that knowledge to start the search in a promising region of the pipeline space. Finally, it builds an ensemble from the best pipelines found. This is fundamentally different from H2O’s brute‑force approach—it’s designed to be sample‑efficient, not compute‑intensive.
So what does that mean for us? If you have a small compute budget and a dataset that resembles common benchmarks, auto‑sklearn’s meta‑learning might give you a good result fast. If you have a big cluster and want to throw compute at the problem, H2O’s brute‑force approach might find something the Bayesian search missed. The cloud tools abstract this choice away—you’re paying for Google, Amazon, or Microsoft to make these decisions for you, and you’re trusting their proprietary search strategies.
4. Let’s See What Happens: A Hands‑On Comparison on a Single Dataset
Enough theory. Let’s run all five tools on the same dataset and see what happens. We’ll use the Adult/Census Income dataset from the UCI repository—a tabular classification problem with a mix of numeric and categorical features, some missing values, and a binary target (whether income exceeds $50K/year). This exercises each tool’s preprocessing pipeline and gives us a fair comparison.
Important caveat before we start: This is an illustration, not a definitive benchmark. One dataset, one random seed, one time budget. The goal is to show you the workflow and the output format, not to crown a winner. Also, the cloud tools require billing accounts and may incur costs even for this small experiment. auto‑sklearn may fail to install in a modern Python environment due to its scikit‑learn version pin. H2O requires a Java runtime. These are real‑world friction points, and we’ll call them out as we go.
Let’s start with the data.
# Load and prepare the Adult dataset for all our AutoML experiments.
# Every code block in this article is self-contained, so we'll reload the data
# in each block. In practice, you'd do this once.
import pandas as pd
import numpy as np
from sklearn.model_selection import train_test_split
# Load the Adult dataset from OpenML
from sklearn.datasets import fetch_openml
adult = fetch_openml(data_id=1590, as_frame=True, parser="auto")
X = adult.data
y = adult.target
# The target is categorical strings; convert to binary 0/1
# In this dataset, the positive class is ">50K"
y_binary = (y == ">50K").astype(int)
# Hold out a truly untouched test set that NO AutoML tool will see during training
X_train_full, X_test, y_train_full, y_test = train_test_split(
X, y_binary, test_size=0.2, random_state=42, stratify=y_binary
)
print(f"Training set: {X_train_full.shape[0]} rows, {X_train_full.shape[1]} columns")
print(f"Test set (untouched): {X_test.shape[0]} rows")
print(f"Positive class rate: {y_train_full.mean():.3f}")
This gives us a training set of about 39,000 rows and a held‑out test set of about 9,800 rows. The positive class (income > $50K) is about 24.8% of the data—a moderate class imbalance that AutoML tools should handle. We’ll give each tool a 5‑minute time budget (or equivalent trial budget) and compare the AUC on the untouched test set.
4.1 H2O AutoML
H2O AutoML is the easiest open‑source tool to get started with—if you have Java installed. It runs a local H2O cluster and provides a scikit‑learn‑like API.
# H2O AutoML on the Adult dataset
# This block is fully self-contained: it reloads the data, starts H2O, trains, and evaluates.
import pandas as pd
import numpy as np
from sklearn.model_selection import train_test_split
from sklearn.datasets import fetch_openml
from sklearn.metrics import roc_auc_score
import h2o
from h2o.automl import H2OAutoML
# ---- Reload and prepare data (self-contained block) ----
adult = fetch_openml(data_id=1590, as_frame=True, parser="auto")
X = adult.data
y = adult.target
y_binary = (y == ">50K").astype(int)
X_train_full, X_test, y_train_full, y_test = train_test_split(
X, y_binary, test_size=0.2, random_state=42, stratify=y_binary
)
# H2O needs the target as a factor (categorical) for classification
# We'll convert it and combine into a single H2O frame
train_df = X_train_full.copy()
train_df["target"] = y_train_full.astype(str) # H2O AutoML expects categorical target as string/factor
test_df = X_test.copy()
test_df["target"] = y_test.astype(str)
# ---- Start H2O cluster and train AutoML ----
h2o.init() # Starts a local H2O cluster (requires Java)
# Convert pandas DataFrames to H2O frames
h2o_train = h2o.H2OFrame(train_df)
h2o_test = h2o.H2OFrame(test_df)
# Identify predictors and target
x_cols = h2o_train.columns[:-1] # all columns except the last
y_col = "target"
# Train AutoML with a 5-minute time budget
# max_models=0 means "no limit on number of models, just use the time budget"
aml = H2OAutoML(max_runtime_secs=300, seed=42, max_models=0,
# Exclude Deep Learning to keep runtime manageable on CPU
exclude_algos=["DeepLearning"])
aml.train(x=x_cols, y=y_col, training_frame=h2o_train)
# ---- Leaderboard ----
lb = aml.leaderboard
print("\nH2O AutoML Leaderboard (top 5):")
print(lb.head(rows=5))
# ---- Evaluate on untouched test set ----
# The leader model is aml.leader
preds = aml.leader.predict(h2o_test)
# For binary classification, H2O returns probabilities for each class
# We want the probability of the positive class (the second column, typically)
y_pred_proba = preds.as_data_frame().iloc[:, 1].values
y_true = y_test.values # numpy array of 0/1
auc = roc_auc_score(y_true, y_pred_proba)
print(f"\nH2O AutoML leader AUC on untouched test set: {auc:.4f}")
h2o.shutdown(prompt=False) # Clean shutdown
What this output tells us: H2O tried a wide variety of models—XGBoost, GBM, GLM, Random Forest, Extremely Randomized Forest—plus random‑grid searches and two stacked ensembles, all within 5 minutes. The leaderboard ranks them by a cross‑validated metric. The untouched test set AUC gives us an honest estimate of how well the best model generalizes. A typical result on this dataset is around 0.91–0.93 AUC. The difference between the leaderboard’s CV score and the test score is the generalization gap—we’ll come back to that in Section 5.
4.2 auto‑sklearn
auto‑sklearn is a drop‑in replacement for a scikit‑learn classifier. It uses Bayesian optimization with meta‑learning to efficiently search the pipeline space. But first, you have to install it—and this is where things get tricky.
# auto-sklearn on the Adult dataset
# This block is fully self-contained.
# NOTE: auto-sklearn requires Python 3.8–3.10 and an older scikit-learn (<1.3).
# If installation fails, see the maintenance caveat in Section 2.
import pandas as pd
import numpy as np
from sklearn.model_selection import train_test_split
from sklearn.datasets import fetch_openml
from sklearn.metrics import roc_auc_score
# ---- Reload and prepare data (self-contained block) ----
adult = fetch_openml(data_id=1590, as_frame=True, parser="auto")
X = adult.data
y = adult.target
y_binary = (y == ">50K").astype(int)
X_train_full, X_test, y_train_full, y_test = train_test_split(
X, y_binary, test_size=0.2, random_state=42, stratify=y_binary
)
# auto-sklearn can handle categorical features if we specify their column indices
# Let's identify categorical columns (those with dtype 'category' or 'object')
categorical_cols = [i for i, dtype in enumerate(X_train_full.dtypes) if dtype.name in ("category", "object")]
# ---- Train auto-sklearn ----
import autosklearn.classification
# Create the classifier with a time budget for the entire search (5 minutes)
# and a per-model runtime limit of 30 seconds
automl = autosklearn.classification.AutoSklearnClassifier(
time_left_for_this_task=300, # total search time in seconds
per_run_time_limit=30, # max time per model trial
seed=42,
# We'll disable ensemble building to keep within the time budget,
# but in practice you'd want it on for better performance
ensemble_size=1,
# Tell auto-sklearn which features are categorical
feat_type=["Categorical" if i in categorical_cols else "Numerical"
for i in range(X_train_full.shape[1])]
)
# Fit the model
# auto-sklearn expects numpy arrays, not DataFrames
# But we can pass DataFrames and it handles the conversion
# However, to be safe with categorical feature types, we'll convert to numpy
# and let auto-sklearn handle the encoding based on feat_type
X_train_np = X_train_full.to_numpy()
y_train_np = y_train_full.to_numpy()
X_test_np = X_test.to_numpy()
y_test_np = y_test.to_numpy()
automl.fit(X_train_np, y_train_np)
# ---- Leaderboard (auto-sklearn stores the best models internally) ----
print("\nauto-sklearn results:")
print(automl.sprint_statistics())
# ---- Evaluate on untouched test set ----
y_pred_proba = automl.predict_proba(X_test_np)[:, 1] # probability of positive class
auc = roc_auc_score(y_test_np, y_pred_proba)
print(f"\nauto-sklearn AUC on untouched test set: {auc:.4f}")
auto‑sklearn’s output shows you which models it tried, which pipeline won, and the cross‑validation performance. The Bayesian optimization with meta‑learning means it’s making smart choices about which pipelines to try next, rather than randomly sampling the space. On this dataset, auto‑sklearn often achieves AUC in the 0.91–0.93 range, comparable to H2O. The arXiv benchmark (2212.02704v3) found that H2O and auto‑sklearn tend to converge to similar performance on tabular benchmarks, though H2O sometimes edges ahead when given enough compute, while auto‑sklearn is more sample‑efficient.
4.3 Google Vertex AI AutoML
Google Vertex AI AutoML requires a Google Cloud project with billing enabled. The workflow is: upload your data to a Google Cloud Storage bucket, create a dataset in Vertex AI, and launch a training job. The code below shows the Python SDK approach. You’ll need to replace the placeholder values with your actual project ID, bucket name, and region.
# Google Vertex AI AutoML on the Adult dataset
# This block is self-contained but requires a GCP project with billing enabled.
# Replace PLACEHOLDER values with your actual GCP details.
import pandas as pd
import numpy as np
from sklearn.model_selection import train_test_split
from sklearn.datasets import fetch_openml
from sklearn.metrics import roc_auc_score
from google.cloud import aiplatform, storage
# ---- Reload and prepare data (self-contained block) ----
adult = fetch_openml(data_id=1590, as_frame=True, parser="auto")
X = adult.data
y = adult.target
y_binary = (y == ">50K").astype(int)
X_train_full, X_test, y_train_full, y_test = train_test_split(
X, y_binary, test_size=0.2, random_state=42, stratify=y_binary
)
# Vertex AI AutoML expects the target column to be in the training data
# and the column names must be alphanumeric (no special characters)
train_df = X_train_full.copy()
train_df["target"] = y_train_full
test_df = X_test.copy()
test_df["target"] = y_test
# ---- Upload data to GCS (requires gcloud authentication) ----
# In practice, you'd authenticate via `gcloud auth application-default login`
# or by setting GOOGLE_APPLICATION_CREDENTIALS environment variable.
PROJECT_ID = "YOUR_PROJECT_ID" # Replace with your GCP project ID
BUCKET_NAME = "YOUR_BUCKET_NAME" # Replace with your GCS bucket name
REGION = "us-central1" # Replace with your preferred region
# Save to CSV and upload
train_df.to_csv("adult_train.csv", index=False)
test_df.to_csv("adult_test.csv", index=False)
storage_client = storage.Client(project=PROJECT_ID)
bucket = storage_client.bucket(BUCKET_NAME)
bucket.blob("adult_train.csv").upload_from_filename("adult_train.csv")
bucket.blob("adult_test.csv").upload_from_filename("adult_test.csv")
print(f"Data uploaded to gs://{BUCKET_NAME}/")
# ---- Create Vertex AI Tabular Dataset and train AutoML ----
aiplatform.init(project=PROJECT_ID, location=REGION)
dataset = aiplatform.TabularDataset.create(
display_name="adult_dataset",
gcs_source=f"gs://{BUCKET_NAME}/adult_train.csv"
)
# Launch AutoML training job
# The target column is "target", and we want binary classification
job = aiplatform.AutoMLTabularTrainingJob(
display_name="adult_automl",
optimization_prediction_type="classification",
column_transformations=[
{"categorical": {"column_name": col}}
if train_df[col].dtype == "object" or train_df[col].dtype.name == "category"
else {"numeric": {"column_name": col}}
for col in train_df.columns if col != "target"
]
)
model = job.run(
dataset=dataset,
target_column="target",
budget_milli_node_hours=1000, # 1 node-hour budget (adjust as needed)
model_display_name="adult_automl_model",
disable_early_stopping=False,
)
print(f"Model trained: {model.resource_name}")
# ---- Evaluate on untouched test set ----
# Vertex AI stores model evaluation metrics; we can also batch-predict on the test set
batch_prediction_job = model.batch_predict(
job_display_name="adult_test_prediction",
gcs_source=f"gs://{BUCKET_NAME}/adult_test.csv",
gcs_destination_prefix=f"gs://{BUCKET_NAME}/predictions/",
instances_format="csv",
)
batch_prediction_job.wait()
print("Batch prediction complete. Results in GCS bucket.")
# In practice, you'd download the predictions and compute AUC:
# from google.cloud import storage
# blobs = storage_client.list_blobs(BUCKET_NAME, prefix="predictions/")
# for blob in blobs:
# if "prediction" in blob.name:
# blob.download_to_filename("predictions.csv")
# preds = pd.read_csv("predictions.csv")
# auc = roc_auc_score(y_test, preds["target_1"]) # adjust column name as needed
# print(f"Vertex AI AutoML AUC on untouched test set: {auc:.4f}")
This code is more involved than the open‑source tools because it requires cloud infrastructure setup. The key steps: upload data to Google Cloud Storage, create a Vertex AI dataset, launch an AutoML training job with a node‑hour budget, and batch‑predict on the test set. Google handles the architecture search, preprocessing, and ensembling automatically. The AUC you get will depend on the node‑hour budget—more budget means more search, but also more cost.
4.4 AWS SageMaker Autopilot
AWS SageMaker Autopilot also requires an AWS account with appropriate permissions. The workflow is similar to Google’s: upload data to S3, launch an Autopilot job, and deploy or batch‑predict.
# AWS SageMaker Autopilot on the Adult dataset
# This block is self-contained but requires an AWS account with SageMaker permissions.
# Replace PLACEHOLDER values with your actual AWS details.
import pandas as pd
import numpy as np
from sklearn.model_selection import train_test_split
from sklearn.datasets import fetch_openml
from sklearn.metrics import roc_auc_score
import sagemaker
import boto3
# ---- Reload and prepare data (self-contained block) ----
adult = fetch_openml(data_id=1590, as_frame=True, parser="auto")
X = adult.data
y = adult.target
y_binary = (y == ">50K").astype(int)
X_train_full, X_test, y_train_full, y_test = train_test_split(
X, y_binary, test_size=0.2, random_state=42, stratify=y_binary
)
# SageMaker Autopilot expects the target column in the training data
# and the data must be in CSV format without a header row (by default)
train_df = X_train_full.copy()
train_df["target"] = y_train_full
test_df = X_test.copy()
test_df["target"] = y_test
# ---- Upload data to S3 ----
BUCKET_NAME = "YOUR_S3_BUCKET" # Replace with your S3 bucket name
ROLE_ARN = "YOUR_SAGEMAKER_ROLE_ARN" # Replace with your SageMaker execution role ARN
REGION = "us-east-1" # Replace with your preferred region
s3_client = boto3.client("s3", region_name=REGION)
# Save without header for Autopilot
train_df.to_csv("adult_train_noheader.csv", index=False, header=False)
test_df.to_csv("adult_test_noheader.csv", index=False, header=False)
s3_client.upload_file("adult_train_noheader.csv", BUCKET_NAME, "adult_train_noheader.csv")
s3_client.upload_file("adult_test_noheader.csv", BUCKET_NAME, "adult_test_noheader.csv")
print(f"Data uploaded to s3://{BUCKET_NAME}/")
# ---- Launch Autopilot job ----
session = sagemaker.Session(boto3.session.Session(region_name=REGION))
# Autopilot requires specifying the target attribute name and the S3 input
input_data = f"s3://{BUCKET_NAME}/adult_train_noheader.csv"
output_path = f"s3://{BUCKET_NAME}/autopilot_output/"
# Create an AutoML job
# We need to specify the column names and target column
# Since we saved without header, we provide the column names here
column_names = list(train_df.columns)
target_column = "target"
autopilot = sagemaker.automl.automl.AutoML(
role=ROLE_ARN,
target_attribute_name=target_column,
output_path=output_path,
problem_type="BinaryClassification",
max_candidates=10, # Limit to 10 candidate models to control cost
max_runtime_per_training_job_in_seconds=600, # 10 min per candidate
total_job_runtime_in_seconds=3600, # 1 hour total
sagemaker_session=session,
)
# Set the input data with column names
autopilot.fit(
inputs=input_data,
column_names=column_names,
wait=True, # Wait for the job to complete
logs=True,
)
print("Autopilot job complete.")
# ---- Evaluate on untouched test set ----
# Deploy the best model and predict, or use batch transform
# The best model is available at autopilot.best_candidate()
best_candidate = autopilot.best_candidate()
print(f"Best candidate: {best_candidate}")
# For batch prediction, we'd create a batch transform job:
# transformer = autopilot.transformer(
# instance_count=1,
# instance_type="ml.m5.large",
# strategy="MultiRecord",
# output_path=f"s3://{BUCKET_NAME}/predictions/"
# )
# transformer.transform(
# data=f"s3://{BUCKET_NAME}/adult_test_noheader.csv",
# content_type="text/csv",
# split_type="Line"
# )
# transformer.wait()
# Then download predictions and compute AUC...
AWS Autopilot’s workflow is similar to Google’s in complexity. The key difference: Autopilot produces a ranked list of candidate models, and you can inspect the notebooks it generates to see exactly what features it engineered and which algorithms it tried. This gives you more transparency than Google’s approach, though less than Azure’s.
4.5 Azure AutoML
Azure AutoML can be used through the Azure Machine Learning Studio GUI or the Python SDK. The SDK approach is shown below. You’ll need an Azure subscription and an Azure ML workspace.
# Azure AutoML on the Adult dataset
# This block is self-contained but requires an Azure subscription and ML workspace.
# Replace PLACEHOLDER values with your actual Azure details.
import pandas as pd
import numpy as np
from sklearn.model_selection import train_test_split
from sklearn.datasets import fetch_openml
from sklearn.metrics import roc_auc_score
from azureml.core import Workspace, Dataset, Experiment
from azureml.train.automl import AutoMLConfig
from azureml.train.automl.run import AutoMLRun
# ---- Reload and prepare data (self-contained block) ----
adult = fetch_openml(data_id=1590, as_frame=True, parser="auto")
X = adult.data
y = adult.target
y_binary = (y == ">50K").astype(int)
X_train_full, X_test, y_train_full, y_test = train_test_split(
X, y_binary, test_size=0.2, random_state=42, stratify=y_binary
)
# Azure AutoML expects the target column in the training data
train_df = X_train_full.copy()
train_df["target"] = y_train_full
test_df = X_test.copy()
test_df["target"] = y_test
# ---- Connect to Azure ML Workspace ----
SUBSCRIPTION_ID = "YOUR_SUBSCRIPTION_ID" # Replace
RESOURCE_GROUP = "YOUR_RESOURCE_GROUP" # Replace
WORKSPACE_NAME = "YOUR_WORKSPACE_NAME" # Replace
ws = Workspace(subscription_id=SUBSCRIPTION_ID,
resource_group=RESOURCE_GROUP,
workspace_name=WORKSPACE_NAME)
# Register the training data as an Azure ML Dataset
# First, save to CSV and upload (or use from_pandas_dataframe)
from azureml.core import Dataset
dataset = Dataset.Tabular.register_pandas_dataframe(
train_df,
target=(ws, "adult_train_dataset"),
name="adult_train"
)
# ---- Configure and run AutoML ----
automl_config = AutoMLConfig(
task="classification",
training_data=dataset,
label_column_name="target",
primary_metric="AUC_weighted",
experiment_timeout_minutes=10, # 10-minute total timeout
max_concurrent_iterations=4,
iterations=20, # Try 20 different pipelines
# Azure AutoML enables ensembling by default (voting + stacking)
enable_ensembling=True,
# We can also enable model explainability
model_explainability=True,
)
experiment = Experiment(ws, "adult_automl_experiment")
run = experiment.submit(automl_config, show_output=True)
run.wait_for_completion()
# ---- Leaderboard ----
best_run, fitted_model = run.get_output()
print(f"\nBest model: {best_run.properties['run_algorithm']}")
print(f"Best AUC: {best_run.get_metrics()['AUC_weighted']:.4f}")
# Get all runs sorted by performance
children = list(run.get_children())
children_sorted = sorted(children, key=lambda r: r.get_metrics().get("AUC_weighted", 0), reverse=True)
print("\nTop 5 models:")
for i, child in enumerate(children_sorted[:5]):
metrics = child.get_metrics()
algo = child.properties.get("run_algorithm", "unknown")
print(f" {i+1}. {algo}: AUC = {metrics.get('AUC_weighted', 'N/A'):.4f}")
# ---- Evaluate on untouched test set ----
# Register test data and run batch prediction
test_dataset = Dataset.Tabular.register_pandas_dataframe(
test_df,
target=(ws, "adult_test_dataset"),
name="adult_test"
)
# Batch-predict using the best model
# (Simplified; in practice you'd use Model.predict() or a batch inference pipeline)
# y_pred_proba = fitted_model.predict(test_df.drop(columns=["target"]))
# auc = roc_auc_score(y_test, y_pred_proba[:, 1])
# print(f"Azure AutoML AUC on untouched test set: {auc:.4f}")
Azure AutoML’s output is the most transparent of the three clouds. You can see exactly which algorithms were tried, their hyperparameters, and their individual performance. The ensemble is built using the Caruana algorithm, and you can inspect which models were included. The model explainability feature gives you SHAP values and feature importance out of the box.
4.6 Interpreting the Results
What did we learn from this hands‑on comparison? First, all five tools can produce strong models on a well‑structured tabular dataset like Adult. The AUC values typically cluster in the 0.91–0.93 range, with differences of 0.01–0.02 between tools—small enough that the “best” tool might change if you use a different random seed or time budget. This convergence is consistent with the arXiv benchmark (2212.02704v3), which found that H2O and auto‑sklearn produce statistically indistinguishable performance on many tabular benchmarks.
Second, the workflow friction varies dramatically. H2O and auto‑sklearn let you start training in minutes (if you can install them). The cloud tools require account setup, data upload, and configuration—but they handle scaling, deployment, and monitoring automatically. The right choice depends on your constraints, not on which tool squeezes out an extra 0.005 AUC.
Third, the leaderboard scores are not the final truth. Every AutoML tool reports a cross‑validation score that is optimistically biased—especially when the tool tries many models. Let’s talk about that.
5. The Hardest Part: When AutoML Fails (and What to Do About It)
AutoML tools are not magic. They fail in predictable ways, and experienced practitioners watch for these failure modes. Here’s what can go wrong and how to catch it.
Leakage: The Silent Killer
AutoML tools automatically preprocess your data—imputing missing values, encoding categoricals, scaling numerics. But they don’t understand your data’s causal structure. If you give them a dataset with a leaky feature, they’ll happily exploit it and produce a misleadingly high validation score.
What’s a leaky feature? Imagine you’re predicting customer churn, and your dataset includes a column called “cancellation_date.” That column is only non‑null for customers who churned—it’s a direct proxy for the target. An AutoML tool will latch onto it and report near‑perfect accuracy. But when you deploy the model, “cancellation_date” will be null for all future customers (they haven’t churned yet), and the model will fail. The tool didn’t know the feature was leaky—it just saw a strong signal.
Another common leak: target encoding that used the whole dataset. If you encoded a categorical feature by replacing each category with the mean target value computed on the entire dataset (including the test set), you’ve leaked the target into the features. AutoML tools won’t catch this—they assume your preprocessing is valid.
Overfitting to the Validation Set: The Multiple‑Comparisons Problem
Here’s the hardest part of AutoML. When an AutoML tool tries 100 different models and picks the one with the best validation score, that validation score is optimistically biased. Why? Because of the multiple‑comparisons problem. If you flip a fair coin 100 times, you’ll get some streaks of heads just by chance. If you search 100 models, you’ll find some that look good on the validation set just by chance—even if they’re no better than random on truly new data.
H2O’s brute‑force approach is especially vulnerable to this because it tries so many models. auto‑sklearn’s Bayesian optimization is somewhat more robust (it makes fewer, smarter trials), but it’s not immune. The cloud tools mitigate this with holdout sets and early stopping, but they can’t eliminate it.
Let’s see what this looks like in practice.
# Detecting overfitting: compare leaderboard CV score to holdout score
# This block simulates the gap you might see with an AutoML tool.
# It's self-contained and illustrates the multiple-comparisons problem.
import numpy as np
import pandas as pd
from sklearn.model_selection import cross_val_score, train_test_split
from sklearn.ensemble import RandomForestClassifier, GradientBoostingClassifier
from sklearn.linear_model import LogisticRegression
from sklearn.svm import SVC
from sklearn.neighbors import KNeighborsClassifier
from sklearn.datasets import fetch_openml
from sklearn.metrics import roc_auc_score
# ---- Reload and prepare data (self-contained block) ----
adult = fetch_openml(data_id=1590, as_frame=True, parser="auto")
X = adult.data
y = adult.target
y_binary = (y == ">50K").astype(int)
# For this demonstration, we'll use a smaller sample to make the point clearer
X_sample, _, y_sample, _ = train_test_split(
X, y_binary, train_size=2000, random_state=42, stratify=y_binary
)
# Hold out a test set
X_train, X_test, y_train, y_test = train_test_split(
X_sample, y_sample, test_size=0.3, random_state=42
)
# ---- Simulate an AutoML search: try many models, pick the best CV score ----
# We'll define a pool of models with different hyperparameters
models = []
# Random Forests with different n_estimators
for n in [10, 50, 100, 200]:
models.append((f"RF_{n}", RandomForestClassifier(n_estimators=n, random_state=42)))
# Gradient Boosting with different learning rates
for lr in [0.01, 0.05, 0.1, 0.2]:
models.append((f"GBM_{lr}", GradientBoostingClassifier(learning_rate=lr, random_state=42)))
# Logistic Regression with different C
for C in [0.01, 0.1, 1.0, 10.0]:
models.append((f"LR_{C}", LogisticRegression(C=C, max_iter=1000, random_state=42)))
# SVM with different kernels
for kernel in ["linear", "rbf"]:
models.append((f"SVM_{kernel}", SVC(kernel=kernel, probability=True, random_state=42)))
# KNN with different k
for k in [3, 5, 7, 11]:
models.append((f"KNN_{k}", KNeighborsClassifier(n_neighbors=k)))
print(f"Searching {len(models)} models...")
# Evaluate each model with 5-fold CV and track the best
best_cv_score = 0
best_model_name = ""
leaderboard = []
for name, model in models:
# Handle categorical features: one-hot encode for models that need it
# For simplicity, we'll use a basic one-hot encoding
X_train_encoded = pd.get_dummies(X_train, drop_first=True)
X_test_encoded = pd.get_dummies(X_test, drop_first=True)
# Align test columns to train
X_test_encoded = X_test_encoded.reindex(columns=X_train_encoded.columns, fill_value=0)
cv_scores = cross_val_score(model, X_train_encoded, y_train, cv=5, scoring="roc_auc")
mean_cv = cv_scores.mean()
leaderboard.append((name, mean_cv))
if mean_cv > best_cv_score:
best_cv_score = mean_cv
best_model_name = name
# Sort leaderboard
leaderboard.sort(key=lambda x: x[1], reverse=True)
print("\nLeaderboard (top 5 by CV AUC):")
for i, (name, score) in enumerate(leaderboard[:5]):
print(f" {i+1}. {name}: CV AUC = {score:.4f}")
# ---- Now evaluate the "best" model on the untouched test set ----
# Find and fit the best model
best_model = None
for name, model in models:
if name == best_model_name:
best_model = model
break
X_train_encoded = pd.get_dummies(X_train, drop_first=True)
X_test_encoded = pd.get_dummies(X_test, drop_first=True)
X_test_encoded = X_test_encoded.reindex(columns=X_train_encoded.columns, fill_value=0)
best_model.fit(X_train_encoded, y_train)
y_pred_proba = best_model.predict_proba(X_test_encoded)[:, 1]
holdout_auc = roc_auc_score(y_test, y_pred_proba)
print(f"\nBest model on leaderboard: {best_model_name}")
print(f"Leaderboard CV AUC: {best_cv_score:.4f}")
print(f"Untouched test set AUC: {holdout_auc:.4f}")
print(f"Gap (optimism): {best_cv_score - holdout_auc:.4f}")
if best_cv_score - holdout_auc > 0.02:
print("\n⚠️ The gap is meaningful. Some of that CV score was luck from searching many models.")
else:
print("\n✓ The gap is small. The CV score was a reliable estimate of generalization.")
This code simulates what an AutoML tool does: it searches many models, picks the one with the best cross‑validation score, and declares it the winner. But when we evaluate that “winner” on truly untouched data, the performance often drops. The gap between the leaderboard CV score and the holdout score is the cost of searching—some of that CV performance was just luck. The more models you search, the larger this gap tends to be.
Domain‑Specific Feature Engineering: The Human Edge
AutoML tools can impute, scale, encode, and select features. They cannot derive a “profit margin” from “revenue” and “cost” columns. They cannot create a rolling average of a time series. They cannot merge in external data sources. The hardest, highest‑value feature engineering is still a human job.
Think of it this way: AutoML automates the mechanical parts of ML—the preprocessing, the algorithm selection, the hyperparameter tuning. But the creative parts—understanding the business problem, designing features that capture domain knowledge, spotting data leakage—are still where you add the most value. AutoML is a power tool, not a replacement for thinking.
Model Complexity and Deployability
The winning model from an AutoML run might be a stacked ensemble of 30 base models that takes 2 seconds to score a single row and requires 2 GB of memory. That’s fine for batch scoring, but it won’t work on a mobile device or a real‑time API with a 50ms latency requirement. AutoML optimizes for accuracy, not for inference speed, memory footprint, or explainability.
Most tools let you constrain model complexity. H2O AutoML allows you to exclude certain algorithms (e.g., exclude_algos=["DeepLearning"]). Azure AutoML lets you set a time budget per iteration and enable or disable specific model types. Google Vertex AI and AWS Autopilot offer similar controls. If deployability matters, use these constraints.
What to Do About It: A Diagnostic Checklist
- Always hold out a truly untouched test set. Don’t let the AutoML tool see it during training or validation. Evaluate the final model on it exactly once.
- Use temporal cross‑validation for time‑series data. Don’t let AutoML do random splits on time‑dependent data—it will leak future information into the past.
- Inspect the top models’ feature importances. If the most important feature is something suspicious (like a “customer_id” or a “future_timestamp”), investigate for leakage.
- Compare the leaderboard CV score to the holdout score. A gap larger than 0.02–0.03 AUC (or equivalent for your metric) suggests overfitting from the search process.
- Set model‑complexity constraints if deployability matters. Exclude deep learning, limit ensemble size, or set a maximum model size.
6. How to Choose: A Decision Framework (Not a Winner)
There is no single “best” AutoML tool. The right choice depends on your constraints. Here’s a decision framework to guide you.
If your data is already in AWS, GCP, or Azure and you need a managed, scalable solution with minimal DevOps: Use the cloud vendor’s AutoML. The integration with data storage, model registry, and deployment endpoints is the real value—not the raw model quality. You’re paying for the ecosystem, not just the AutoML.
If you need to run AutoML on‑premises, in an air‑gapped environment, or without sending data to a cloud service: H2O AutoML is the most robust open‑source choice. It’s actively maintained, has a large user community, and handles a wide variety of data types. It runs anywhere Java runs.
If you’re a scikit‑learn user who wants a drop‑in AutoML that respects the scikit‑learn API and you’re willing to manage the maintenance risk: auto‑sklearn is elegant and sample‑efficient. But check the latest commit date before you depend on it. If the repo is stale, consider H2O instead.
If you need NLP or computer vision AutoML: Azure has the most comprehensively documented multimodal support among the three clouds, covering NLP with 104 languages and computer vision. Google Vertex AI also supports image and text (and video). AWS Autopilot is currently tabular‑focused. H2O and auto‑sklearn are tabular‑only.
If you need explainability and model transparency: H2O AutoML provides feature importance, SHAP values, and partial dependence plots out of the box. Azure AutoML provides model explanations via the Responsible AI dashboard. Google Vertex AI offers Vertex Explainable AI, and AWS offers SageMaker Clarify. The cloud vendors generally offer more explainability tooling than the open‑source tools, but H2O’s built‑in model inspection is excellent.
If cost is your primary concern: The cloud tools charge per training hour and per prediction—costs can escalate quickly on large datasets. H2O and auto‑sklearn are free to run, but you pay for the compute (your own hardware or cloud VMs). There’s no free lunch, but the cost structures are fundamentally different. With open‑source tools, you pay upfront for hardware; with cloud tools, you pay as you go.
Here’s a decision flowchart in plain English:
- Where is your data?
- Already in a cloud (AWS/GCP/Azure) → Use that cloud’s AutoML for seamless integration.
- On‑premises or air‑gapped → Use H2O AutoML (or auto‑sklearn if you accept the maintenance risk).
- What kind of data?
- Tabular → All five tools work.
- Images, text, or video → Azure or Google Vertex AI. (AWS Autopilot is tabular‑only; H2O and auto‑sklearn are tabular‑only.)
- Where will the model run?
- Cloud endpoint → Cloud AutoML tools handle deployment natively.
- On‑premises or edge device → H2O (exports MOJO/POJO for low‑latency scoring) or auto‑sklearn (exports a scikit‑learn pipeline).
- How important is explainability?
- Critical (regulated industry, stakeholder trust) → Azure (Responsible AI dashboard) or H2O (built‑in SHAP and PDP).
- Nice to have → Any tool; all provide basic feature importance.
- What’s your budget?
- Tight budget, own hardware → H2O or auto‑sklearn (free software, you provide compute).
- Can pay for convenience → Cloud AutoML (pay‑per‑use, no hardware management).
Recap
- AutoML tools are systematic search engines for model pipelines—they automate the grind, not the thinking.
- The five tools represent two philosophies: managed cloud services (Google Vertex AI, AWS SageMaker Autopilot, Azure AutoML) vs. open‑source libraries (H2O AutoML, auto‑sklearn).
- Under the hood, they use fundamentally different search strategies: brute‑force breadth (H2O), Bayesian optimization with meta‑learning (auto‑sklearn), proprietary multi‑stage search (Google, AWS), and transparent ensemble selection (Azure).
- On a well‑structured tabular dataset, all five tools converge to similar performance—the differences are small and often swamped by random variation.
- AutoML fails in predictable ways: data leakage, overfitting from multiple comparisons, inability to do domain‑specific feature engineering, and producing overly complex models.
- The right tool depends on your constraints: data location, task type, deployment environment, explainability needs, and budget.
Check Your Understanding
Remember: What are the two fundamental philosophies that distinguish the five AutoML tools in this article?
Understand: In your own words, explain why the leaderboard CV score from an AutoML run is often higher than the model’s performance on a truly untouched test set. What statistical phenomenon causes this gap?
Apply: You have a tabular dataset with 100,000 rows and 50 features, stored in an on‑premises PostgreSQL database. Your company policy forbids sending data to external cloud services. Which AutoML tool(s) would you consider, and why?
Analyze: A colleague runs H2O AutoML on a customer‑churn dataset and gets a leaderboard AUC of 0.95. The top feature is “days_since_last_login.” The colleague is thrilled. What questions would you ask before trusting this model for production?
Evaluate: Compare the search strategies of H2O AutoML and auto‑sklearn. Under what circumstances might auto‑sklearn’s Bayesian optimization with meta‑learning outperform H2O’s brute‑force approach? Under what circumstances might the reverse be true?
Create: Design a small experiment to test whether Azure AutoML’s ensemble selection (Caruana algorithm) produces better‑calibrated probabilities than H2O AutoML’s stacked ensembles on an imbalanced dataset. What metrics would you use beyond AUC? How would you ensure a fair comparison?
Apply What You Learned is for Supporter and Insider subscribers.
Subscribe to unlock the exercises on this post.
See plansRelated articles
- Python Engineering Under review
Advances In Financial Machine Learning L Pez De Pr
Before we start picking winners and losers, let’s get oriented. The book has five parts spread across 22 chapters, and each part tackles a different stage of the quant research pipeline.
- Python Engineering Under review
Machine Learning In Manufacturing Predictive Maint
Think about how you maintain your car. You have three options:
- Python Engineering Under review
Auto Sklearn And H2O Automl Open Source Automl You
You know the feeling. You've spent hours tweaking hyperparameters — adjusting the learning rate, changing the number of trees, trying different kernels.
- Python Engineering Under review
Andrew Ng S Machine Learning Courses Which One Sho
Before we talk about what exists today, we need to talk about what doesn't. Because half the confusion around 'Andrew Ng's ML course' comes from a ghost.
Looking for something else?
Search every article by title, summary or topic.