Skip to learning content

DATA SCIENCE PYTHON PLAYGROUND

Machine Learning · Learn / Refresh

← Regression lessons
Curves and trees · ML-R-K1 · 25–35 MIN

Regression checkpoint

  1. Retrieval 1Retrieve and applyCurrent exercise

Outputs you create

cv_results
  1. Dataframe indexed by the requested model IDs, with initial_score, selected_score and settings columns.
  2. Scores are observed mean training-fold scores; settings describes the chosen recipe.
reference_results
  1. cross_validate result for the dummy reference; test_score contains five scores.
chosen_name
  1. Model ID nominated from training evidence.
residuals
  1. Training-only actual, predicted and actual-minus-predicted residual evidence.
final_rmse
  1. Root mean squared error in original target units.
candy · first 8 rows
competitornamechocolatefruitycaramelpeanutyalmondynougatcrispedricewaferhardbarpluribussugarpercentpricepercentwinpercent
100 Grand1010010100.7320.8666.9717
3 Musketeers1000100100.6040.51167.6029
One dime0000000000.0110.11632.2611
One quarter0000000000.0110.51146.1165
Air Heads0100000000.9060.51152.3415
Almond Joy1001000100.4650.76750.3475
Baby Ruth1011100100.6040.76756.9145
Boston Baked Beans0001000010.3130.51123.4178
Your task
  1. Compare mixed-input linear regression and a tree on Candy with common training folds, a reference, diagnosis and final evidence.
cv_resultsreference_resultschosen_nameresidualsfinal_rmse
Hints

Think: Reconstruct a fair comparison of two different flexibility assumptions.

Tools: Common KFold, mixed pipelines, tree-depth search, OOF residuals and final RMSE.

Approach: Evaluate both candidates and the reference, tune only the declared tree grid, nominate from training evidence, diagnose and finish.

Explained solution
from sklearn.base import clone
from sklearn.model_selection import train_test_split, KFold, cross_validate, cross_val_predict, GridSearchCV
from sklearn.dummy import DummyRegressor
from sklearn.metrics import root_mean_squared_error

import matplotlib.pyplot as plt
import seaborn as sns
X=df[['sugarpercent', 'pricepercent', 'chocolate', 'fruity', 'caramel', 'peanutyalmondy', 'nougat', 'crispedricewafer', 'hard', 'bar', 'pluribus']]
y=df['winpercent']
X_train,X_test,y_train,y_test=train_test_split(X,y,test_size=.2,random_state=42)
folds=KFold(n_splits=5,shuffle=True,random_state=42)
candidates={}
grids={}
# Prepare inputs and construct the candidate pipeline.
preprocessor = 'passthrough'
from sklearn.pipeline import Pipeline
from sklearn.linear_model import LinearRegression
model = LinearRegression()
pipeline = Pipeline([('prepare', preprocessor), ('model', model)])
model = pipeline
candidates['multiple_linear']=model
grids['multiple_linear']=None
# Prepare inputs and construct the candidate pipeline.
preprocessor = 'passthrough'
from sklearn.pipeline import Pipeline
from sklearn.tree import DecisionTreeRegressor
model = DecisionTreeRegressor(random_state=42)
pipeline = Pipeline([('prepare', preprocessor), ('model', model)])
model = pipeline
candidates['regression_tree']=model
grids['regression_tree']={'model__max_depth': [3, 5, None]}
# Validate initial candidates on matching training folds.
initial_results={name:cross_validate(candidate,X_train,y_train,cv=folds,scoring='neg_root_mean_squared_error') for name,candidate in candidates.items()}
# Compare with a simple reference before tuning.
reference_results=cross_validate(DummyRegressor(strategy='mean'),X_train,y_train,cv=folds,scoring='neg_root_mean_squared_error')
rows=[]
selected={}
for name,candidate in candidates.items():
    initial=initial_results[name]
    grid=grids[name]
    if grid:
        search=GridSearchCV(candidate,grid,cv=folds,scoring='neg_root_mean_squared_error',n_jobs=1)
        search.fit(X_train,y_train)
        selected[name]=search.best_estimator_
        validation_score=float(search.best_score_)
        settings=search.best_params_
    else:
        selected[name]=candidate
        validation_score=float(np.mean(initial['test_score']))
        settings='Keep defaults: no production search'
    rows.append({'model':name,'initial_score':float(np.mean(initial['test_score'])),'selected_score':validation_score,'settings':str(settings)})
cv_results=pd.DataFrame(rows).set_index('model')
# This solution nominates by mean training-fold score. Other evidence-based choices can be defensible.
chosen_name=cv_results.selected_score.idxmax()
chosen=selected[chosen_name]
oof_predictions=cross_val_predict(chosen,X_train,y_train,cv=folds)
diagnostic_y=y_train
residuals=pd.DataFrame({'actual':diagnostic_y,'predicted':oof_predictions,'residual':diagnostic_y-oof_predictions})
fig,ax=plt.subplots(figsize=(6,4))
sns.scatterplot(x=residuals.predicted,y=residuals.residual,s=12,ax=ax)
ax.axhline(0,color='black')
ax.set(xlabel='Training-validation prediction',ylabel='Residual',title='Training-only residuals')
fig.tight_layout()
fig.savefig('diagnostic.png',dpi=150,bbox_inches='tight')
final_model=clone(chosen).fit(X_train,y_train)
final_predictions=final_model.predict(X_test)
final_rmse=root_mean_squared_error(y_test,final_predictions)
print('Final RMSE:',final_rmse)

The matched design isolates candidate differences; original-unit residuals qualify the nomination before a single final evaluation of the selected workflow.

Ctrl/⌘+Enter: Run · Tab: indent · Esc then Tab: leave editor

Python loads when you run. Code and results stay in this activity only.

Run your code to inspect its output. Check uses that same run.