Classical machine learning
Encoding categories and text
Categories and words become numbers through one-hot columns, hashing and bag-of-words counts. Each method has a cost that shows up with many levels or a large vocabulary.
Models need numbers, but a country or a plan is a label. Encoding turns each label into numeric columns. Text can be handled the same way, by counting the words it contains. This page covers the common encodings, what each one costs, and where each one breaks.
Common encodings
| Method | Idea | Watch out for |
|---|---|---|
| One-hot | One binary column per level | Width grows with the number of levels. For linear models, drop one reference level |
| Ordinal | Map levels to integers | Implies an order and spacing that may not exist |
| Hashing | Hash each level into a fixed number of buckets | Collisions between levels. Good for huge vocabularies under a memory limit |
| Target encoding | Replace each level with its average label | Leaks badly unless computed out of fold. See the next topic page |
| Embeddings | Learn a vector for each level | Natural inside neural nets. Overkill for small tabular models |
Trade-off
One-hot or target encoding. One-hot, or hashing, is the safe default for linear models and for trees when the number of levels is moderate, below about 100 to 200. Target encoding helps with high-cardinality fields such as city or merchant, but you must compute it with out-of-fold statistics.
One-hot in practice
Take plan with three levels: free, pro and team. One-hot gives three columns:
free → [1, 0, 0]
pro → [0, 1, 0]
team → [0, 0, 1]A linear model can drop one column, because the other two imply it. A tree does not need that. A city column with 10,000 levels would add 10,000 columns, which is why hashing or target encoding is used there instead.
Example
Sketch, not run here: a scikit-learn ColumnTransformer applies one-hot encoding to the categorical columns and passes the numeric ones through. The handle_unknown="ignore" option matters, because new categories will appear in production.
from sklearn.preprocessing import OneHotEncoder
from sklearn.compose import ColumnTransformer
cat = ["plan", "country"]
num = ["logins_14d", "log_spend"]
pre = ColumnTransformer([
("num", "passthrough", num),
("cat", OneHotEncoder(handle_unknown="ignore", sparse_output=False), cat),
])Text as word counts
The simplest text representation is a bag of words: one column per word, and each value is the count of that word in the document. Word order is lost, but for many tasks, such as routing tickets or flagging spam, the words are enough.
docs = ["refund my order", "order not received", "refund refund"]
vocab = sorted({w for d in docs for w in d.split()})
counts = [[d.split().count(w) for w in vocab] for d in docs]
print(vocab)
for row in counts:
print(row)Output:
['my', 'not', 'order', 'received', 'refund']
[1, 0, 1, 0, 1]
[0, 1, 1, 1, 0]
[0, 0, 0, 0, 2]Common words such as "the" get large counts in every document and carry little signal. TF-IDF fixes this by multiplying each count by an inverse document frequency, which is lower for words that appear in many documents. TF-IDF with a linear model is a strong baseline for ticket routing and spam. Keep it in your evaluation sheet before you try embeddings.
Common mistakes
- One-hot on a column with thousands of levels. The matrix becomes very wide and sparse. Hash it, or target-encode it with care.
- Using ordinal codes for unordered categories. A linear model will treat the distance between codes as meaningful.
- Crashing on unseen categories in production. Set the encoder to ignore unknown levels, or map them to an "other" bucket.
Check yourself
- How many columns does one-hot give for a three-level category, for a linear model with a reference level dropped? Two. The third is implied by the others.
- Why does ordinal encoding mislead a linear model on
country? It implies that countries have an order and equal spacing, which they do not.
Key takeaways
- One-hot encoding is the safe default for moderate numbers of levels.
- Hashing bounds the width for huge vocabularies, at the cost of collisions.
- Bag-of-words and TF-IDF turn text into sparse counts, and they are strong baselines.
- Plan for unseen categories at serving time.
Further learning
Missing values are the next problem, and they often carry information of their own: missing values and pipelines.
Related
Features and data preparation
Turning raw data into model inputs without leaking the future. Covers scaling, encoding, missing values, time windows, target encoding and class imbalance, and keeping training and serving identical.
Linear and logistic regression
The two models under almost everything in ML. They fit lines, predict probabilities and stay honest through regularization.
Embeddings and similarity
Turning text into vectors, measuring similarity, and choosing an embedding model.