Data Scaling with MinMaxScaler
The Boston Housing workflow loads the data, splits it into training and test sets, scales the training data with MinMaxScaler, and applies the same fitted scaler to the test data.
Why a Model Needs a Prepared Table
A linear model is only as useful as the table of numbers it receives. Before a model can learn anything from the Boston Housing data, the data has to be loaded, divided into parts, rescaled, and expanded into a richer set of columns. This article follows that preparation from start to finish. You will trace each step, predict what it should produce, and then check the result against what the program reports.
The goal is not only to run the code. The goal is to learn how to read each stage, so that when something goes wrong you can tell which step produced the surprising result. Preparation errors often do not crash the program. The table can have the right shape and still contain the wrong values, so knowing where each number came from is the most useful skill here.
Tracing the Load and Split
The first stage imports three tools from scikit-learn, loads the dataset, and divides it into a training portion and a test portion. Read the code from top to bottom. Every name on the left of an equals sign is a new object created by the step on the right. The split is performed by train_test_split, which receives the input data and the target values together and returns four objects: a training input matrix, a test input matrix, a training target vector, and a test target vector.
- The three imports bring in the split function, the scaler, and the polynomial transformer.
boston.dataholds the inputs; boston.target holds the values to predict.random_statefixes the random choices so the same split is produced each run. The value 0 is illustrative; any fixed integer behaves the same way.
The rows of boston.data are the samples and its columns are the features. The split keeps inputs and targets aligned, so every row of X_train still belongs with the matching entry of y_train. Splitting the rows this way is what allows the test portion to play the role of data the model has not seen during preparation.
Before reading the scaling steps, it helps to have a concrete expectation. The training matrix starts with 379 rows and 13 columns. The scaling and expansion steps that follow will change the values and then the number of columns, but the number of rows will stay the same at each stage that transforms the features.
Read the diagram as a sequence of states. Loading produces the full table of samples and features. Splitting divides the rows into two groups and leaves the number of columns alone. Scaling changes the values inside the columns but not their count. Expansion changes the count of columns, which is the stage where the matrix becomes wider.
Scaling Before Expansion
The source uses MinMaxScaler to rescale the data so that its values lie within a common range. The default range in scikit-learn is 0 to 1, where each feature's smallest training value maps to 0 and its largest training value maps to 1, with other values placed proportionally between them. This matters because the polynomial step multiplies features together. If one feature has values far larger than the others, its products would dominate the new columns. Scaling first puts the original features on comparable footing before they are combined.
Following the Scaled Values
The fitted scaler is a single object that carries information from the training data into every later step. The diagram below traces which data is used to compute the minimum and maximum, and how the same fitted object then transforms the test set.
Expanding to Degree-2 Features
The next stage asks the transformer to create new columns from the existing ones. The degree argument sets the largest number of original features that may be multiplied together in one new column. With degree=2, each output column is either an original feature, a constant, a square of one original feature, or a product of two different original features. The transformer is fitted on the scaled training data, and that same fitted object is then used to transform both the scaled training data and the scaled test data.
(379, 13)
(379, 105)- The expansion is fitted on the scaled training data and reused for the scaled test data.
- The printed shapes show the change in width: 13 columns become 105, and the row count stays at 379.
What do you think happens?
After degree-2 expansion of the 13 scaled features, how many columns does X_train_poly have?
Reveal answer
105
The expanded matrix keeps the 379 rows and has 105 columns: one constant column, the 13 original columns, and 91 squares and pairwise products.
The printed shapes show the change in width. The original training matrix has 13 columns and the expanded one has 105. The number of rows stays at 379 because each sample still produces exactly one row; only the description of each sample becomes longer. Each of the 13 original features contributes a square term, and each pair of different features contributes one interaction term. Those interaction terms are the pairwise products of the data.
Counting the Expanded Columns
You can predict the column count before running the code. Let n stand for the number of original features. The count has three parts: one constant column, then the n original columns, then the squares and the distinct pairwise products. The squares contribute n terms, and the distinct pairs contribute $\frac{n(n-1)}{2}$ terms, which together give $\frac{n(n+1)}{2}$.
This expression is a way of checking the count, not a formula printed in the source. Written in full, the total is $1 + n + \frac{n(n+1)}{2}$. Using it as a check protects you from trusting a printed shape you did not understand.
Predicting the width for 13 features
How many columns should a degree-2 expansion of 13 original features produce, and does that match the printed shape?
- 1Identify n
There are 13 original features, so n = 13.
- 2Count the constant
One column is the constant '1'. That contributes 1.
- 3Count the originals
The 13 original features each keep a column. That contributes 13.
- 4Count the squares and products
The 13 squares plus the $\frac{13 \cdot 12}{2} = 78$ distinct pairs give 91 terms.
- 5Add the parts
$1 + 13 + 91 = 105$, which matches the printed shape of 105 columns.
The expanded matrix has 105 columns and still 379 rows.
Reading the Feature Names
A table of 105 unlabeled numbers is hard to interpret, so the transformer can report which input produced each output. The get_feature_names method returns those labels. The labels are not arbitrary. The first is the constant '1', the next thirteen are the original features named x0 through x12, and the names after those show the squares and products. In the printed output, a caret indicates a square, and a space indicates a product of two features.
['1', 'x0', 'x1', 'x2', 'x3', 'x4', 'x5', 'x6', 'x7', 'x8', 'x9', 'x10', 'x11', 'x12', 'x0^2', 'x0 x1']- Position 0 is the constant. Positions 1 through 13 are the original features x0 through x12.
- Position 14 is the square of x0, and position 15 is the product of x0 and x1.
The full list follows a regular order. Names beginning with x0 come first, then x1, and so on. For each starting feature, the square comes first and is followed by the products with each later feature. So after x02 come x0 x1, x0 x2, and continuing through x0 x12. Then the names switch to x12, followed by x1 x2 and onward. The printed list in the source wraps across several lines, but this regular pattern lets you predict any name from its position.
Read the diagram as a lookup table. Position 0 is the constant. Positions 1 through 13 are the original features. Position 14 begins the squared and product terms built from the first feature. Because the names record the origin of each column, you can check any coefficient or diagnostic later against the input it came from. The position of a column is enough to find its name, and the name is enough to find its origin.
Mistakes in the Preparation Order
Preparation errors are easy to make because the shapes often look correct. Consider a variant of the code in which the expansion is applied to the unscaled training data instead of the scaled data. The column count is still 105, so a shape check would pass, but the products would be built from raw values on different scales.
Common mistake Fitting the scaler on the test data
What it looks likescaler.fit_transform(X_test) followed by a separate scaler for the training set
Why it failsThe minimum and maximum are then learned from test data, and the two sets are scaled by different rules.
Do this insteadCall fit_transform only on X_train and transform on X_test with that same fitted scaler.
Common mistake Expanding before scaling
What it looks likePolynomialFeatures applied to the raw training matrix, then MinMaxScaler applied to the widened result
Why it failsA feature with much larger values would dominate the products, and the scaling would then act on columns that were already distorted.
Do this insteadScale the original features first, then build the polynomial columns from the scaled values.
Common mistake Trusting matching shapes as proof of correct values
Why it failsShape checks confirm the column count but not the values. The output can be the right width and still be built from the wrong stage.
Do this insteadTrace each stage in the order the data passes through it, and check the values produced at each step.
Common mistake Reading column numbers without the feature names
Why it failsPosition 15 means nothing by itself, so a surprising coefficient cannot be traced back to its input.
Do this insteadUse the labels from get_feature_names to map each position to its original feature or pair.
Practice: Trace and Predict
Without running the code, predict the shape of X_test_poly if the test portion has 127 rows and the expansion is degree 2 applied to 13 scaled features. Then predict which feature name sits at position 27 of the expanded columns, and explain which input or pair it comes from. Finally, state which stage would produce a wrong result if the scaler were fitted on the test data.
Hints
- Rows are preserved by expansion, so the row count of the test set carries through unchanged.
- The columns are the same 105 as the training expansion, because the same degree and the same 13 inputs are used.
- Position 27 falls in the block that begins with x12, so look at the regular ordering of the names.
- The scaler is the stage that learns parameters, so fitting it on test data changes the learned minimum and maximum.
Key Takeaways
- The workflow loads the data, splits it into training and test sets, fits MinMaxScaler on the training data only, and reuses that fitted scaler on the test data.
- Degree-2 PolynomialFeatures turns 13 original features into 105 columns, made of one constant, 13 originals, 13 squares, and 78 pairwise products, while the 379 training rows stay unchanged.
- The feature names map each output column to its origin: '1' is the constant, x0 through x12 are the originals, a caret marks a square, and a space marks a product.
- Scaling should come before expansion so that large-valued features do not dominate the products, and shape checks alone cannot confirm that the values are correct.