Glossary
Every term defined across the written lessons (3019 terms so far). Each entry links to the lesson that introduced it. The glossary grows as lessons are written.
- __annotations__ Day 69
- The dictionary Python builds on a class or function holding every annotated name in declaration order. It is what makes annotations useful at runtime to tools rather than to the interpreter — and it is precisely what `@dataclass` reads to work out what the fields are.
- __cause__ Day 66
- The attribute set by "raise X from err" — an explicit claim by the author that err caused X. The traceback prints "The above exception was the direct cause of the following exception".
- __context__ Day 66
- The attribute Python sets automatically when a new exception is raised while another is being handled, with no "from". The traceback prints "During handling of the above exception, another exception occurred", which reads as an accident rather than a decision.
- __dict__ Day 67
- The dictionary an object uses to store its attributes. An instance's holds only state; a class's holds its class attributes and every method. `vars(obj)` returns the same object.
- __init__ Day 67
- The initializer. It receives an object that already exists as `self`, sets its attributes, and returns None. It is not a constructor: it cannot choose or replace the object it was given, which is why alternative constructors are classmethods.
- __init__.py Day 59
- The file that marks a directory as a package and, by convention, defines the package's public API by re-exporting names from its submodules, so callers can write `from wordstats import tokenize` without knowing which module tokenize lives in.
- __main__ Day 59
- The value Python assigns to __name__ in the file that was launched directly (via python3 script.py or python3 -m package). Code under `if __name__ == "__main__":` therefore runs only when the file is run, not when it is imported.
- __name__ Day 49
- A built-in variable Python sets for every module: it equals the string `"__main__"` when the file is run directly, and the module's own name when the file is imported by another.
- __name__ Day 59
- A built-in variable every module has. Python sets it to the module's dotted name (such as "wordstats.tokens") when the module is imported, and to the special string "__main__" when the file is run directly — the switch the main guard reads.
- __post_init__ Day 69
- A method the generated `__init__` calls after assigning the fields. It is where validation and derived fields belong, and — unlike an annotation — it actually runs and can raise, making it the only enforcement in a plain dataclass.
- __post_init__ Day 70
- The method a dataclass calls after its generated initializer has assigned the fields. It is the standard place to validate a value object, raising a domain exception before any invalid instance can escape.
- __repr__ Day 67
- The method producing unambiguous text about an object, for you rather than for a user. Lists and debuggers use it exclusively, and `print` falls back to it, which is why every class deserves one. Never put a secret in it — it reaches logs and tracebacks.
- __sklearn_tags__ Day 146
- An internal method, supplied by BaseEstimator, that scikit-learn's own fitted-check reads inside Pipeline and cross_val_score. Its absence is the exact, measured cause of an estimator built without BaseEstimator failing inside both, even though its fit/predict/score work fine directly.
- __str__ Day 67
- The method producing friendly text about an object, for a person reading output. `print`, `str()`, and f-strings use it when it exists and fall back to `__repr__` when it does not.
- .agg() Day 123
- A GroupBy method that reduces each group to a single summary row. Accepts a single function name, a list of function names, a dict mapping columns to functions, or named aggregation (result_name=(column, function)). The list and dict forms on a multi-column selection typically produce a MultiIndex on the result columns; named aggregation always produces flat column names.
- .apply() (GroupBy) Day 123
- A GroupBy method that runs an arbitrary user function once per group, passing the whole group as a DataFrame or Series, and reassembles whatever the function returns. The most general and, for built-in-equivalent computations, the slowest of the three, because it calls a Python function once per group rather than dispatching to a vectorised path.
- .bashrc Day 11
- The configuration file bash reads for interactive non-login shells; a common place to define aliases, functions, and exported variables.
- .between() Day 122
- A Series method testing whether each value falls within a closed range (inclusive of both endpoints by default): series.between(lo, hi) is equivalent to (series >= lo) & (series <= hi), written as one call instead of a parenthesised compound comparison.
- .describe() Day 120
- A DataFrame or Series method that computes count, mean, standard deviation, min, the quartiles, and max for every numeric column at once -- the same summary statistics Day 116 covered computing by hand, including Bessel's correction for the standard deviation.
- .drop_duplicates() Day 122
- A DataFrame method removing rows that repeat according to a chosen subset of columns (every column, by default). subset names which columns define "duplicate"; keep chooses which occurrence of each duplicate group survives ('first', 'last', or False to drop every member of a duplicated group).
- .filter() Day 122
- A DataFrame method selecting LABELS -- column names by default, or row labels with axis=0 -- by exact match (items=), substring (like=), or pattern (regex=). It never evaluates a condition on the data inside a column or row, and passing it row-shaped arguments silently matches nothing rather than raising, making its name one of the more confusing in the library.
- .gitignore Day 30
- A file listing path patterns Git should not track, so build outputs, temp files, and secrets never get staged or committed by accident.
- .iloc Day 120
- A positional indexer, exactly like indexing a Python list or NumPy array by integer position, regardless of the labels present. A slice given to .iloc is exclusive of its stop position, matching ordinary Python slice semantics.
- .isin() Day 122
- A Series method returning True for every row whose value appears in a given collection. Equivalent to chaining `==` and `|` once per value, but scales to any number of values with one call. series.isin([]), an empty collection, returns an all-False mask -- filtering with it gives an empty frame, not the untouched original.
- .isna() Day 120
- A Series or DataFrame method that returns a boolean mask marking which positions hold a missing value, checking the underlying missing-value representation directly rather than relying on equality comparison, which can never succeed against NaN.
- .isna().sum() Day 121
- A DataFrame method chain reporting how many missing values each column holds. The second command in the inspection battery, run immediately after any load whose row counts have not been independently verified.
- .loc Day 120
- A label-based indexer. df.loc[row_label, col_label] selects by the labels present in the index and columns. A slice given to .loc is inclusive of its stop label: df.loc["b":"d"] includes the row labelled "d".
- .loc Day 122
- A label-based indexer. df.loc[mask, 'col'] combines row filtering by a boolean mask with column selection in one call, and is the safe form for assignment through a filter under Copy-on-Write (Day 120).
- .nlargest() / .nsmallest() Day 122
- DataFrame/Series methods returning the n rows with the largest (or smallest) values in a given column, computed without a full sort. Match df.sort_values(col, ascending=False).head(n) exactly when no tie sits at the cutoff; keep='all' can return MORE than n rows, surfacing every row tied at the boundary rather than an arbitrary subset of them.
- .nunique() Day 121
- A DataFrame or Series method reporting the count of distinct non-missing values per column -- answers "how many different things are actually in here", distinct from .value_counts(), which also says how often each one appears.
- .query() Day 122
- A DataFrame method that evaluates a string of Python-like expression syntax against the frame's own columns, returning the same rows an equivalent boolean mask would. References an external Python value with an `@` prefix, e.g. df.query("amount > @threshold"). Reads well once several conditions stack up; costs the overhead of parsing a string for a single simple condition.
- .str.contains() NA trap Day 122
- On an object-dtype string column, .str.contains(pattern) applied to a missing entry returns None, not False, producing a mask whose own dtype is object rather than bool; filtering a DataFrame with such a mask raises ValueError. na=False makes .str.contains() treat a missing entry as "did not match" up front, producing a clean boolean mask. On pandas 3.0's default str dtype, a missing entry already returns a clean False with no na= needed.
- .transform() Day 123
- A GroupBy method that computes a per-group statistic and returns it aligned to every original row -- the result has the same length and order as the input, unlike .agg(), which reduces each group to one row.
- .value_counts() Day 121
- A Series method returning the distribution of distinct values, sorted most frequent first. The fastest way to see whether a categorical column's values are what you expect, and which one dominates.
- .zshrc Day 11
- The configuration file zsh reads for interactive shells; on macOS, where a new Terminal tab runs zsh, this is usually the file to edit for personal settings.
- **kwargs Day 58
- A parameter written with two stars that gathers all extra keyword arguments into a dictionary, letting a function accept and forward arbitrary named options — the pattern ML and LLM libraries use to pass configuration. At a call site, two stars spread a dict into keyword arguments.
- *args Day 58
- A parameter written with one star that gathers all extra positional arguments into a tuple, letting a function accept any number of positional inputs. At a call site, one star spreads a sequence back out into positional arguments.
- `&`, `|`, `~` Day 122
- The elementwise boolean operators pandas overloads for combining masks -- AND, OR and NOT applied row by row. They work on a Series with no ambiguity because each row's result is independent. Python's `and`, `or` and `not` keywords are control-flow operators that need a single True/False and raise ValueError on a multi-row Series.
- 422 Unprocessable Content Day 82
- The status FastAPI returns when validation fails — defined originally for WebDAV in RFC 4918 and carried into RFC 9110. It means the request was syntactically fine and its contents were not. The body carries a `detail` LIST with one entry per problem, each naming a machine-readable `type`, a `loc` path to the exact field, a human `msg`, and the rejected `input`.
- 429 Too Many Requests Day 27
- The HTTP status code a server returns when you have exceeded its rate limit; it is temporary and clears once you wait and retry.
- 5-fold cross-validation, scored by RMSE Day 154
- Splitting the training rows into five folds and scoring every candidate on all five, so every training row serves as held-out data exactly once. The scoring metric -- RMSE -- is chosen before any candidate is fitted, in the target's own unitless composite-score points.
- 5-fold stratified cross-validation Day 147
- Splitting the training rows into five class-balanced folds and scoring each candidate on all five, so every training row serves as held-out data exactly once. Used here to select the winning configuration without ever touching the test rows.
- 95 percent interval, on a test accuracy Day 147
- test_accuracy plus or minus 1.96 times the standard error sqrt(p(1-p)/n). Computed here at 0.9825 +/- 0.0241, giving [0.9584, 1.0066] -- the range Day 144's arithmetic says the true accuracy plausibly sits in, given only 114 test rows.
- A record Day 16
- A DNS record that maps a name to an IPv4 address; the AAAA record is its IPv6 equivalent.
- Absolute error Day 149
- The loss `sum(|y - prediction|)`. Minimised by the median; piecewise-linear, with a kink at every point where a residual crosses zero; has no closed-form minimiser because its derivative does not exist at a residual of exactly zero.
- absolute import Day 59
- An import that names a module by its full path from the top of the package tree, such as `from wordstats.tokens import tokenize`. Preferred from outside a package because it is explicit and unambiguous about exactly which module is meant.
- absolute path Day 9
- A path that starts at the root directory (/) and gives the full route from the top, so it means the same thing no matter what the current directory is.
- absolute path Day 64
- A path starting from the root of the filesystem, such as `/home/ada/data/train.txt`. It means the same thing no matter which directory the process is running in.
- abstract base class Day 68
- A class built with `abc.ABC` that cannot be instantiated and that names methods subclasses must implement, using the `@abstractmethod` decorator. An incomplete subclass is refused at construction, naming the missing method, rather than failing mysteriously much later.
- Abstract syntax tree Day 76
- The structured representation a parser builds from source text, in which `if match == None:` is a comparison node rather than a string of characters. Both halves of Ruff work on it: the formatter prints it back out with canonical whitespace, and the linter walks it asking each enabled rule's question. Python exposes its own version through the standard-library `ast` module.
- Acceptance harness Day 140
- A program that reads a finished piece of work and reports what is missing or unsupported, returning a structured verdict rather than raising on the first problem. This day's harness, `check_study(path)`, runs eight gates over a study directory. It checks presence and consistency of artefacts, never the quality of the analysis.
- access token Day 25
- A short-lived credential, obtained through OAuth, that an app sends as a bearer token on each API call; it expires quickly to limit the damage from a leak.
- accessibility contract Day 133
- A build check that a report's figures must pass rather than a guideline their author is asked to remember: every mark drawn in a colour from a colourblind-safe palette, and both axes labelled. It is deliberately incomplete -- it checks neither contrast ratios nor whether meaning is encoded by colour alone, and redundant encoding remains the real fix.
- accumulator Day 51
- A variable that starts at a neutral value (0 for a sum, an empty list for a build) and folds in one item per loop pass to build up a running total, count, or collection.
- ACID Day 39
- The four guarantees a relational transaction provides — Atomicity (all-or-nothing), Consistency (no invalid state), Isolation (concurrent clients do not corrupt each other), and Durability (committed data survives a crash).
- ACID Day 85
- The four guarantees a transaction makes. Atomicity: the group of writes happens entirely or not at all. Consistency: every constraint holds before and after. Isolation: concurrent transactions do not see each other's partial work. Durability: once committed, it survives a crash. In SQLite all four are implemented by the pager.
- acknowledgement Day 26
- The 2xx response (typically 200 OK) a receiver sends back to confirm it accepted a delivery, telling the sender it can stop retrying.
- Acquisition Function Day 166
- A mathematical function (such as Expected Improvement or Upper Confidence Bound) that guides search exploration by quantifying the utility of sampling a candidate hyperparameter point.
- activate Day 43
- To turn on a virtual environment (source .venv/bin/activate), which rewires the current shell so python and pip point inside that environment; deactivate turns it off.
- Activation Cache Day 199
- A structured memory store saving intermediate activations A and pre-activations Z during the forward pass for reuse in backpropagation.
- Activation function Day 102
- A deliberately non-linear function placed between the linear layers of a network — ReLU, which replaces every negative number with zero, being the usual choice. Its job is precisely to break the identity that lets consecutive matrices slide together into one. Without it, twenty layers multiply into a single matrix and depth buys nothing at all; with it, the collapse is blocked and the composite can describe boundaries no straight line could.
- Activation Function Day 198
- A non-linear mathematical transformation applied to the linear weighted sum of a neural network layer to enable representation of non-linear functions.
- Activation Sparsity Day 209
- The fraction of neuron outputs in a layer that are exactly zero after applying a non-linear activation like ReLU.
- Active Learning Day 191
- A machine learning framework where the learning algorithm interactively queries an information source (human oracle) to label new data points.
- AdaGrad Day 206
- An adaptive gradient algorithm that scales the learning rate inversely proportional to the square root of the sum of all historical squared gradients.
- Adam Day 206
- Adaptive Moment Estimation combining first-moment momentum with second-moment RMSprop curvature scaling and initialization bias corrections.
- AdamW Day 206
- A formulation of Adam that decouples weight decay from the gradient update, applying true L2 penalty directly to parameter weights.
- Adapter Day 70
- Code at the edge that connects the pure core to the outside world: a command-line front end, a repository, a report printer. Adapters import the core; the core imports no adapter, so every dependency points inward.
- Adapter Day 84
- A small module wrapping one boundary — the network, the clock, the filesystem, a subprocess — so that everything inside it can be pure and testable. Injecting adapters rather than importing them is Day 74's rule applied to a whole program; injecting the sleep function alongside them is what lets a test exercise three retries in microseconds.
- Adapter and converter Day 90
- The two halves of automatic type conversion in sqlite3: an adapter turns a Python object into a SQLite value on the way in, a converter turns a value back into a Python object on the way out, and converters run only when detect_types is passed. The module's default adapters for datetime.date and datetime.datetime are deprecated as of Python 3.12; the alternatives are to store ISO-8601 text or to register your own explicitly.
- Addition rule Day 113
- P(A or B) = P(A) + P(B) - P(A and B). Subtracting the intersection once corrects for the fact that any outcome belonging to both A and B was counted in both P(A) and P(B). Naively adding P(A) + P(B) without the correction overstates the truth by exactly P(A and B) whenever the two events overlap.
- Additive Model Day 164
- A model structure of the form F(x) = sum(eta * h_m(x)), where the final prediction is a linear combination of base learners.
- Adjusted R-squared Day 152
- R-squared penalised by the number of predictors used relative to the number of rows. Corrects the training-R2 climb at a modest predictor count -- measured falling from 0.5415 to 0.5329 at 20 pure noise columns -- but breaks down itself once the predictor count approaches the row count, measured climbing back to 0.6104 at 100 noise columns on 331 rows.
- Adjusted Rand index Day 142
- An external criterion measuring agreement between two partitions while ignoring their labelling, corrected so that a random partition scores about zero. Available only when you have the labels the unsupervised method does not, which is why it is a diagnostic tool rather than a selection tool.
- Adjusted Rand Index (ARI) Day 189
- A metric measuring the similarity between two clustering assignments, adjusted for chance overlap.
- Affine transformation Day 102
- A linear transformation followed by a shift: x maps to M @ x + b. It is NOT linear, because it moves the origin and therefore fails both conditions — the additivity failure is exactly b and the scaling failure is exactly (s - 1) times b. Every neural network layer is affine, which is why the bias is written separately as X @ W + b: a matrix cannot move the origin, and b exists to move it.
- Affine transformation Day 105
- A linear map followed by a translation, written as a 3 by 3 matrix whose bottom row is (0, 0, 1). The top-left 2 by 2 block is Day 102's linear part, whose columns are still where the basis vectors land; the third column is the translation. Six numbers, and that is the entire family. Affine transformations guarantee two things: straight lines stay straight, and parallel lines stay parallel. Rotation, scaling, shear, reflection and translation are all affine, as is any composition of them. Perspective is not, and neither is lens distortion.
- Affine-rescaling invariance Day 152
- A property of ordinary least squares: fitting on features rescaled by a per-column affine transform (mean-centred and divided by a constant, as standardisation does) produces identical predictions to fitting on the original features. Measured here as identical RMSE, MAE and R2 on raw-unit and standardised diabetes features.
- Agg backend Day 127
- matplotlib's pure software rasteriser, selected with matplotlib.use("Agg") before importing pyplot. It draws into memory and needs no display, window server or GPU, which is what makes plotting safe inside a test suite, a container or a continuous integration job.
- Agglomerative Clustering Day 184
- A bottom-up hierarchical clustering method that starts with each observation in its own cluster and iteratively merges closest pairs.
- Aggregate function Day 86
- A function that takes many rows and returns one value: COUNT, SUM, AVG, MIN, MAX, and SQLite's TOTAL. Every one of them except COUNT(*) removes NULL inputs before doing any arithmetic — they are not treated as zero, they are removed. An aggregate is illegal in WHERE because WHERE runs before there is anything to aggregate, and an aggregate over zero rows still returns exactly one row.
- aggregation bias Day 138
- The error introduced by fitting one model to a heterogeneous population. In this lesson's example the pooled slope was +1.98 while both subgroups' true slopes were about -1.0, and the pooled model's error was worse for every subgroup, not merely worse on average.
- AI Winter Day 197
- A historical period of reduced funding and interest in artificial intelligence research, triggered in 1969 by Minsky and Papert analysis of perceptrons.
- alert Day 40
- A rule that turns a metric crossing a threshold into a notification for a human who is not watching, best configured to fire on user-facing symptoms rather than internal causes.
- alias Day 11
- A short name defined in the shell that expands to a longer command by simple text substitution, such as ll for ls -la.
- Alias Day 86
- A name given to a column or expression with AS. It is created at the SELECT stage and not before, which is exactly why ORDER BY may use one — it runs later — while standard SQL forbids it in WHERE, which runs earlier. SQLite accepts an alias in WHERE anyway, as a documented extension; PostgreSQL rejects it, so portable code repeats the expression or wraps the query.
- Alias Day 94
- A second name for a field: the name the data uses on the wire, as distinct from the name your code prefers. Field(alias="pm2_5") lets a vendor export be read into a field called pm25. The alias is what appears in an error's loc, and by default it is not what appears in model_dump output — you ask for that with by_alias=True.
- aliasing Day 44
- The situation where two or more names refer to the same object, so a change made through one name is visible through the others (relevant for mutable objects).
- aliasing Day 52
- Two or more names referring to the same list object, created by plain assignment (`b = a`). A change made through one name is visible through the others, because there is only one underlying list.
- aliasing Day 131
- The phenomenon in which sampling a periodic signal below its own frequency does not simply lose detail but manufactures a specific, different, false period in the sampled data -- a pattern that exists nowhere in the underlying signal and is entirely a product of the sampling interval chosen.
- Alpha (regularization strength) Day 151
- The hyperparameter that scales how much the penalty term matters relative to the residual sum of squares. alpha=0 recovers plain least squares in every model here. Not portable between model classes without correction -- see the Ridge/ElasticNet alpha-scale mismatch.
- Alpha (significance level) Day 118
- The Type I error rate a test is willing to tolerate, fixed before the data is collected -- the pre-agreed burden of proof, not a threshold adjusted after seeing how convincing the evidence turned out to be. Conventionally 0.05, though that number is a historical convention (Fisher, 1925), not a mathematically derived optimum.
- Alternating Least Squares (ALS) Day 188
- An optimization algorithm that alternates between fixing user matrices to solve for items and fixing item matrices to solve for users.
- alternation Day 38
- The | operator meaning "this or that"; cat|dog matches either cat or dog, and gr(a|e)y matches gray or grey.
- alternative constructor Day 67
- A second way to build an instance, written as a classmethod because there can only be one `__init__`. `Account.from_csv_row("ada,120.50")` is one, and it is how parsed data becomes validated objects.
- ALU Day 2
- The arithmetic logic unit — the block of gate circuitry inside a CPU core that performs arithmetic and logic operations on register values and sets the status flags.
- Ambiguous time Day 95
- A wall-clock reading that occurred twice, because the clocks went back across it. 01:30 on 25 October 2026 in Europe/London names two instants an hour apart — epoch 1792888200 and 1792891800 — and the string alone cannot tell you which. Detect it by converting both folds to UTC and testing whether the fold=0 instant is the earlier of the two.
- amend Day 34
- Replacing the most recent commit with a new one — used to fix its message or add a forgotten file. Because it builds a new commit object, the commit's hash changes.
- ANALYZE Day 89
- The statement that measures your data and writes the results into a table called sqlite_stat1 — one row per index, giving the number of entries and the average rows per distinct key — so the planner chooses from facts rather than from a built-in guess. It matters most on skewed data and on tables whose shape changed after their indexes were built. On evenly distributed data it often changes nothing, and this lesson's lab says so rather than implying otherwise.
- anchor Day 38
- A pattern element that matches a position rather than a character: ^ marks the start of a line, $ the end, and \b a word boundary.
- Anemic domain model Day 70
- A design in which classes hold data only while every rule lives in loose functions elsewhere. Named by Martin Fowler in 2003; the harm is that each new caller can forget a check. Field classes plus pure functions are fine in Python provided invariants are still enforced at construction.
- Angle Day 103
- The measure of how far apart two directions are, from 0 degrees for the same direction to 180 for opposite. Recovered from the cosine similarity with arccos, and worth knowing about mostly because it behaves better than the cosine distance does: on the lesson's failing triple the angles satisfy the triangle inequality exactly where 1 minus cosine does not. Any code that turns a similarity into an angle must clamp the similarity into the range -1 to 1 first, because floating-point rounding can put it a hair outside and arccos refuses.
- annotated tag Day 35
- A tag created with git tag -a that stores the tagger, date, and a message as a full git object — the kind used for releases.
- Annotated type Day 94
- typing.Annotated[T, ...] carrying pydantic constraints alongside the base type, so a constrained value can be named once and reused — Percent = Annotated[int, Field(ge=0, le=100)]. It is the modern way to avoid repeating ge=0, le=100 on nine fields and then getting it wrong on the tenth, and it works with static type checkers, which see only the T.
- annotation Day 69
- A recorded claim about what a name is supposed to hold, written as `score: float`. Python evaluates it once, stores it in `__annotations__`, and never compares any value against it. It is the label printed beside a blank on a form: useful, checkable by tools, and powerless on its own.
- annotation Day 75
- A recorded claim about what a name is supposed to hold, written as `score: float` or `def find(name: str) -> Model | None`. Python evaluates it once at definition time, stores it in `__annotations__`, and never compares a value against it — which is exactly why a separate checker is needed for it to mean anything.
- Anomaly Detection Day 187
- The identification of rare items, events, or observations that raise suspicions by differing significantly from the majority of the data.
- Anomaly Detection Day 209
- A PyTorch debugging mode (torch.autograd.set_detect_anomaly) that identifies the exact forward operation that generated NaN or Inf values.
- Anscombe's quartet Day 116
- Four datasets published by Francis Anscombe in 1973 that agree, to documented precision, on mean x, mean y, variance x, variance y, correlation and regression slope -- and look nothing alike in shape: a roughly linear scatter, a perfect parabola, a perfect line with one outlier, and a set where a single non-repeated x-value determines the entire fitted slope.
- Anscombe's quartet Day 148
- Four datasets constructed by Francis Anscombe in 1973 that share nearly identical summary statistics -- including the same fitted regression line -- while looking completely different when plotted, an early and influential illustration of exactly this lesson's argument for residual plots.
- Anti-join Day 87
- The idiom for finding rows with no match: LEFT JOIN the other table, then keep only the rows where its columns came back NULL, which can happen for exactly one reason. Worth memorising as a unit, because it is the shape of every question about absence — which customers never ordered, which documents were never embedded, which books nobody has borrowed.
- Any Day 69
- The typing escape hatch meaning "stop checking here" rather than "some type". A value typed `Any` may be passed anywhere and have anything called on it, so it silently disables checking for everything downstream — deliberate at a genuinely dynamic boundary, a bad habit elsewhere.
- Any Day 75
- The typing escape hatch that means "stop checking here" rather than "some type". A value typed `Any` may be passed anywhere and have anything called on it, and anything derived from it is itself `Any`, so the hole spreads downstream until something re-annotates it. Deliberate at a genuinely dynamic boundary; a way of hiding a real bug everywhere else.
- API Day 22
- An Application Programming Interface: a defined contract by which one program asks another to do something, exposing the requests it accepts and responses it returns while hiding how it works inside.
- API client Day 28
- A program — even a single command — that sends a request to a remote service and uses the response it gets back. Today you build one for weather.
- API key Day 22
- A secret token a caller sends (usually in an Authorization header) to prove who they are; like a password, it must never be shared publicly or sent to an echo service.
- API key Day 25
- A long random string an API issues to your account, attached to each request (usually in a header) to identify and authenticate the caller.
- append/extend Day 52
- `append(x)` adds a single item to the end of a list in place; `extend(other)` adds every item from another iterable to the end. Both mutate the list and return None. Appending is O(1) amortized.
- approval Day 33
- A reviewer's recorded verdict that a pull request is good enough to merge; protected branches can require one or more approvals before the merge button unlocks.
- apt Day 13
- The Advanced Package Tool, the default package manager on Debian and Ubuntu Linux, which resolves dependencies and installs system-wide packages (usually run with sudo).
- AR(1) process Day 117
- An autoregressive series of order 1: each observation equals phi times the previous observation plus fresh, independent noise. Used in this lesson to build a dataset with genuine dependence between consecutive observations, on which the naive standard-error formula is measured to understate the truth by more than a factor of two.
- Argmax tie-breaking Day 142
- What an implementation does when several options share the maximum value. NumPy's argmax returns the lowest such index, which on an all-zero value table makes a greedy policy a constant action -- and an agent that reaches its goal 0 times in 300 episodes with no error raised.
- argparse Day 56
- Python's standard-library module for parsing command-line arguments: you declare the arguments and subcommands your tool accepts, and it reads sys.argv, validates them, converts types, generates --help text, and reports usage errors.
- argsort Day 104
- A function returning the INDICES that would sort an array, rather than the sorted values. a[np.argsort(a)] reconstructs np.sort(a), so nothing is lost by taking the indices, while taking the values loses which row each score came from. That is why a search uses argsort: when the rows mean something — an article, a token, a candidate — the ranking is the answer and the scores are only how you got there. np.argpartition is the cheaper relative that only guarantees the k best land in the first k places, which is what model code uses at scale.
- argument Day 8
- The target a command acts on, such as a file or folder name — for example `/Users` in `ls -l /Users`.
- argument Day 57
- An actual value supplied to a function when it is called; for example [2, 4, 6] in mean([2, 4, 6]). The argument is bound to the matching parameter for the duration of the call.
- Argument parsing Day 80
- Turning the list of strings a program receives into structured, typed values: matching options and positionals, converting through `type=`, checking `choices=`, applying defaults, and refusing anything that does not fit. In argparse all of it happens before a single line of your own logic runs.
- Argument-order bug Day 152
- A class of bug where a function's answer depends on which argument occupies which position, and swapping them produces a plausible-looking but wrong answer rather than an error. sklearn.metrics. r2_score is not symmetric in y_true and y_pred; measured here returning 0.359409 in the correct order and -0.209635 swapped.
- ArgumentTypeError Day 80
- The exception a custom `type=` callable raises to reject a value. argparse catches it and turns it into a usage message on standard error with exit code 2, naming the argument and quoting the offending value — rather than the traceback a bare ValueError would produce.
- ARM Day 2
- The RISC instruction-set family begun as the Acorn RISC Machine in 1985 — simple, uniform, power-frugal instructions — that powers essentially all smartphones and, since Apple Silicon, a growing share of laptops and servers.
- Arrange, act, assert Day 71
- The three-part shape of every test in every language: build the inputs, call the thing once, state what must be true. When the input is a literal, arrange and act share a line — that is normal, not a shortcut.
- array Day 24
- A JSON value that is an ordered list of values of any type, written inside square brackets; it maps to a list in most languages.
- Artifact Day 77
- A file produced by a build or gate run and kept for later inspection — a coverage data file, a built package, a log. In continuous integration, artifacts are uploaded by a step that usually runs even when the gate failed, because a failure is exactly when you want the evidence.
- Artifact Day 143
- Everything the pipeline knows so far, plus how it came to know it. Extended by returning a new copy rather than by mutation, because a stage that mutates its input makes the step log a work of fiction describing states that no longer exist.
- Artifact Provenance Day 196
- The immutable cryptographic audit trail linking a deployed binary to its exact dataset hash, code commit SHA, and metrics.
- Artificial Perceptron Day 197
- The simplest artificial neural network architecture: a single computational unit that computes a weighted sum of inputs and applies a threshold step function.
- Artist Day 128
- matplotlib's base class for literally everything that gets drawn -- a Line2D from a plot() call, a Text from a label or title, a Rectangle from a bar, a Legend. An Axes' plotted content is a list of Artist objects, which is exactly what makes a chart testable: ax.lines is a list of Line2D artists, and each one's get_xydata() returns the numbers that produced it.
- as_index Day 123
- A groupby keyword, default True, controlling whether the grouping key(s) become the result's index (True) or ordinary columns in a flat DataFrame (False).
- ASCII Day 5
- An early 7-bit character encoding that maps 128 codes to English letters, digits, punctuation, and control characters.
- asdict Day 69
- A `dataclasses` function that walks an instance recursively and returns plain dicts and lists — exactly what `json.dumps` accepts. There is deliberately no automatic reverse: rebuilding objects from parsed data is code you write.
- ASGI Day 82
- The Asynchronous Server Gateway Interface — one agreed calling convention between a Python web application and any server that hosts it, developed by Andrew Godwin out of the Django Channels work. It succeeds WSGI (PEP 333, Phillip J. Eby, 2003) by allowing handlers to be coroutines, so a request that is merely waiting can yield its worker.
- ASGI Day 194
- Asynchronous Server Gateway Interface: the standard Python interface for asynchronous web servers (e.g. Uvicorn).
- ASGI server Day 82
- The program that owns the socket, speaks HTTP and calls your application — uvicorn here. It is not part of your application, which is why the lab can drive the application with no server at all.
- assembly language Day 2
- A human-readable notation for machine instructions, one line per instruction, like the toy machine's ADD R1,R2->R3.
- assert Day 66
- A statement that raises AssertionError when its condition is false — and that is removed entirely when Python runs with -O. Use it for internal invariants and tests, never for validating anything a user or a file can supply.
- Assertion Day 71
- A statement of something that must be true at a point in the program. In Python, `assert expression` does nothing when the expression is true and raises `AssertionError` when it is false. Note that the `-O` flag strips assertions entirely, which is why they belong in tests and not in runtime validation of untrusted input.
- Assertion rewriting Day 71
- pytest's import hook, which rewrites a test module's `assert` statements before compiling them so that a failure can report both sides of the comparison — `assert 4 == 3` plus a `where 4 = add(1, 2)` line. The source file is never modified; the rewriting happens in memory on the way to bytecode. It is why pytest needs no `assertEqual`.
- Associative Day 101
- An operation where the brackets may be moved without changing the answer: (A @ B) @ C equals A @ (B @ C). Matrix multiplication is associative. Note the precise claim — the BRACKETS may move freely, the ORDER may not, and confusing those two statements is the usual mistake. Associativity is what makes it legal to pick the cheaper evaluation order, which on realistic adapter shapes is worth a factor of 258 in arithmetic for an identical answer.
- asyncio.to_thread Day 96
- A coroutine that runs a blocking function in a worker thread and can be awaited, propagating the current context variables to that thread. It is the standard repair for a synchronous library you cannot rewrite: the blocking still happens, it simply happens somewhere that is allowed to block, so the event loop keeps its thread. Measured here at 4.9 times faster than calling the same function inline in a coroutine. It is a repair, not a licence to keep adding synchronous calls.
- at Day 14
- A Unix command that runs a job once at a single future time rather than on a recurring schedule, for one-off delayed or reminder tasks.
- at-least-once delivery Day 26
- A delivery guarantee that a sender will keep retrying until acknowledged, so an event arrives one or more times (possibly duplicated) rather than being silently lost.
- atomic commit Day 35
- A commit that contains exactly one logical change, making it possible to review, revert, or bisect that change in isolation.
- Atomic Serialization Day 173
- Saving an entire end-to-end feature transformation and modeling graph as a single immutable joblib artifact.
- Atomic Serialization Day 210
- Saving checkpoints to a temporary file before renaming to prevent corrupted half-written files on crash.
- atomic write Day 64
- The pattern for replacing a file safely: write the complete new content to a temporary file in the same directory, flush, fsync, then `os.replace` it over the target in a single uninterruptible rename. A reader at any instant gets either the complete old file or the complete new one — never a fragment.
- Atomic write Day 81
- Writing output to a temporary name in the same directory and then renaming it into place with os.replace, which is atomic on POSIX. Without it a crash mid-write leaves a truncated file under the real name, which the next run mistakes for a finished result. Same directory matters: the rename is only atomic within one filesystem.
- Atomic write Day 84
- Writing a whole new file to a temporary name in the same directory, flushing and fsyncing it, then replacing the old name with os.replace — so any reader sees either the complete old file or the complete new one, never a mixture. The naive alternative truncates the real file first, so one interruption destroys the record of everything ever processed.
- Atomicity Day 88
- The guarantee that a transaction happens entirely or not at all, so a multi-step change can never be found half-done. The A in ACID, an acronym coined by Theo Härder and Andreas Reuter in 1983 for properties Jim Gray had codified in the 1970s. The word most people misread: it is a promise about the boundary you drew, not a promise that an error will draw one for you.
- attenuation (of correlation) Day 125
- The systematic shrinkage, toward zero, of a correlation between an imputed column and an untouched column. Follows directly from the Pearson correlation formula: a term with a zero deviation on one axis contributes zero to the covariance sum regardless of the other axis's value, so it can only dilute an existing relationship, never strengthen one.
- Attribute Day 91
- A fact about one entity, which therefore becomes a column rather than a table. A published year is an attribute of a book: it has no life of its own and nothing else refers to it. The interesting case is an attribute of a RELATIONSHIP rather than of either side — such as the order an author is credited on a particular book — which belongs on the junction table.
- attribute lookup Day 67
- The rule that resolves a dotted name: search the instance dictionary first, then fall back to the class. Reads fall back; writes always land on the instance, creating an attribute that shadows the class one.
- AttributeError Day 48
- An error raised when you access an attribute or method that an object does not have, often due to a typo in the method name.
- attrs Day 69
- The third-party library that inspired PEP 557 and still offers more than the standard library — inline per-field converters and validators among them. Free and open source; `@dataclass` is the deliberately smaller version of the same idea.
- Augmentation Day 105
- Applying random transformations — rotations, flips, shears, shifts — to training images so that a model learns the invariances you intend rather than accidents of how the data was collected. It is one of the cheapest and most effective regularisers available, and it is nothing but the arithmetic of this lesson run at volume. An augmentation is legitimate exactly when the transformed image is one that could genuinely occur in your data with the SAME label: a mirrored cat is a plausible cat, mirrored text is not text, and a mirrored chest X-ray depicts a rare and clinically significant condition rather than a normal patient.
- authentication Day 25
- The process by which a server verifies who is making a request, usually by checking a secret credential the caller presents; failing it returns HTTP 401.
- authorization Day 25
- The process of deciding what an already-identified caller is permitted to do; failing it returns HTTP 403, distinct from an authentication failure.
- authorization Day 82
- The question of whether a caller is permitted to do what they asked — distinct from authentication (who are you?) and from validation (is this well-formed?). A perfectly valid DELETE from a stranger is still a stranger deleting your data, and no pydantic model, and no passing test suite, provides any of it.
- Authorization Day 18
- A header carrying the credential that proves who the client is, most often as "Bearer <token>"; it is the header that decides between a 200 and a 401.
- autocommit Day 90
- The explicit transaction control added to Connection in Python 3.12, with three states. True commits every statement immediately, so another connection sees the write at once. False keeps a transaction permanently open, which means a long-lived connection holds a lock until it commits. sqlite3.LEGACY_TRANSACTION_CONTROL restores the older behaviour and makes isolation_level meaningful again. Setting autocommit causes isolation_level to be ignored.
- autocomplete Day 36
- A feature that suggests and completes valid names as you type and shows what a function expects; Microsoft's branded version is called IntelliSense.
- Autofix Day 76
- A machine-applicable rewrite that a linter can perform for you, applied with `ruff check --fix`. In a Ruff report, the `[*]` marker next to a finding means a fix is available and considered safe. Autofix is a convenience, not an authority: the interesting findings are deliberately left for a person.
- Autoflush Day 93
- The Session's default behaviour of flushing pending changes before it runs any query, so the query can see work you have not committed yet. It is almost always what you want, and it is why SQL appears in the log at lines where you wrote no query. session.no_autoflush suspends it for a block; reach for that rarely and comment why.
- Autograd Day 202
- PyTorch automatic differentiation engine that dynamically builds a directed acyclic computational graph during forward execution.
- Autograd Day 204
- PyTorch reverse-mode automatic differentiation engine that dynamically builds a Directed Acyclic Graph (DAG) during the forward pass to compute analytical gradients.
- Automatic differentiation Day 108
- Computing exact derivatives by applying the chain rule to a program's own operations as it runs, rather than manipulating a formula (symbolic differentiation) or sampling function values (numerical differentiation). It is neither of the other two: no formula is produced and no approximation is made, so there is no h to choose and no U-shaped error curve. It is what JAX and PyTorch do, and it is what makes training a model with millions of parameters possible at all. Day 110's chain rule is the mechanism it automates.
- Automatic differentiation Day 110
- Computing exact derivatives by applying the chain rule to the operations a program actually performs. It is neither symbolic differentiation, which manipulates formulas and can blow up in size, nor numerical differentiation, which approximates with finite differences and carries truncation and rounding error. Automatic differentiation is exact up to float rounding and costs a small constant factor over the original computation.
- automation Day 14
- Pairing a script that performs a task with a scheduler that runs it at chosen times, so the work happens reliably without a person doing it by hand.
- automation Day 41
- The practice of encoding a repeatable task so a computer performs it without manual intervention, on a defined trigger, producing the same result every time.
- automation Day 42
- Making repeatable work run itself with scripts, hooks, and pipelines, so tasks like formatting, linting, testing, and scheduled jobs happen without manual effort (days 12, 14, 41).
- Automation Day 84
- Something that runs unattended, on a schedule, when nobody is watching — as opposed to a script, which is something you run and observe. The difference is not size or sophistication: it is that everything an automation will ever be able to tell you must already have been designed into it before it ran.
- autonomous system Day 16
- A large network under a single administrative control (an ISP, university, or cloud provider), identified by an AS number and exchanging routes with others via BGP.
- Autoregressive Lag Day 192
- A feature variable representing the historical value of the target series at a prior time step: y_{t-k}.
- autoscale Day 128
- matplotlib's default behaviour of choosing axis limits that fit the plotted data with a small margin, recomputed whenever new data is plotted. An explicit call to set_xlim or set_ylim overrides autoscaling for that axis; autoscaling does not resume unless autoscale() is called again explicitly.
- Autospec Day 74
- Building a double by inspecting the real object, so it has exactly the real attributes with exactly the real signatures. `create_autospec(SomeClass)` or `patch(..., autospec=True)` refuses a misspelled method name and a call with arguments the real method would reject; `spec=` catches only the first of those.
- Availability (in CAP) Day 92
- Every request received by a non-failing node results in a response, with no guarantee that the response reflects the most recent write. A store that returns a slightly stale answer is available; a store that returns an error because it cannot confirm the value with its partner is not.
- Average rate of change Day 108
- The rate of change of f over an interval: (f(b) − f(a)) ÷ (b − a), read as rise over run. It is a true and complete statement about the interval and says nothing about any point inside it — a car averaging 24 metres per second over six seconds may never have travelled at 24 metres per second at all. Computable with nothing but arithmetic, which is why this lesson starts there.
- await Day 96
- The pause point, and the only one. When a coroutine reaches await it hands the thread back to the loop and asks to be resumed when the awaited thing is done. Between two awaits a coroutine cannot be interrupted, which is the property that makes async code so much easier to reason about than threads: every place another task could run is visible in your source. It is not an accelerator, and a coroutine containing no await is an ordinary function wearing a keyword.
- Aware datetime Day 95
- A datetime whose tzinfo is not None and whose tzinfo.utcoffset() returns a value. It carries a wall-clock reading and the offset that was in force, which together name exactly one instant. The documentation gives those two conditions explicitly; anything else is naive.
- Axes Day 128
- A single set of x/y (or x/y/z) coordinates inside a Figure, and the object almost everything in this lesson is a method call on. An Axes owns its plotted Artists, its labels, its title, its limits, its ticks and its legend. Despite the name's similarity to "axis," one Axes typically has two axis objects (x and y) belonging to it -- the plural in "Axes" refers to this pairing, not to there being several of them.
- axes-level function Day 129
- A seaborn plotting function (scatterplot, histplot, boxplot, lineplot, stripplot, and others) that draws into a single matplotlib Axes -- either one you pass with ax=, or a new one it creates -- and returns that Axes. Because the return value is an ordinary matplotlib Axes, every matplotlib Axes method (set_ylabel, set_xlim, and so on) works on it afterward.
- axis Day 104
- A dimension of an array, and the argument that tells an aggregation which one to collapse. The rule worth memorising is that the axis you name is the one that DISAPPEARS: a (3, 4) array summed with axis=0 leaves shape (4,), one number per column, and with axis=1 leaves (3,), one per row. Reading it as "the axis I want to keep" is wrong by exactly one every time. keepdims=True holds the collapsed dimension open at length 1 so the result can broadcast back against the array it came from.
- Axis Day 100
- Which dimension of an array an operation works along, given as a number counting from 0. For a 2-D array, axis 0 is the rows and axis 1 is the columns. The rule that settles every case: the axis you name is the axis that disappears — a (3, 4) array summed with axis=0 returns shape (4,), and with axis=1 returns shape (3,). The rule holds for every reduction and generalises to arrays with more than two axes without amendment.
- Axis-Aligned Split Day 162
- A decision rule evaluating a single feature against a scalar threshold (x_j <= t), creating boundaries strictly orthogonal to coordinate axes.
- B-tree Day 85
- The ordered, page-based tree structure in which SQLite stores both tables and indexes. Because it is ordered and arranged in pages, finding a row by key is a short descent reading a handful of pages rather than a walk through everything — which is what an index actually is, underneath the word.
- B-tree Day 89
- The balanced, disk-oriented tree that stores both tables and indexes in SQLite, described by Rudolf Bayer and Edward M. McCreight in 1972. Each node is a whole page holding many keys rather than the two of a binary tree, and the tree grows at the root, so every leaf stays the same distance from the top and no rebuild is ever needed.
- back_populates Day 93
- The declaration that two relationship attributes are the two directions of one relationship, so that appending to one side updates the other in Python before any SQL is emitted. Without it you get two independent relationships over the same foreign key, and the in-memory graph can disagree with itself until the next reload quietly resolves the argument.
- Backfill Day 81
- Deliberately running a job for a range of past periods. Only possible if the job takes its period as a parameter rather than computing "yesterday" internally — which is the injected-clock argument again, and a thing you discover on the morning you need it most.
- Backfill Day 98
- Running a pipeline for a period in the past — usually because a scheduled run was missed, a source was down, or a bug meant the data you stored was wrong. It is only cheap if two things are already true: the report instant is a parameter rather than a clock reading, so you can ask about last Tuesday; and the store is idempotent, so a backfill that overlaps data you already hold changes nothing.
- background job Day 7
- A command started with & so the shell does not wait for it: the process runs while the prompt returns immediately, its PID captured in $! and listed by jobs.
- Backoff Day 84
- Waiting longer before each successive retry, usually by doubling. Described by Robert Metcalfe and David Boggs in their 1976 Ethernet paper as the way stations recover from a collision without colliding again in lockstep — the same reason a hundred clients that all retry after exactly one second will all collide again after exactly one second.
- Backpropagation Day 110
- Reverse-mode automatic differentiation applied to a neural network: build the computation graph during the forward pass, seed the loss gradient with 1, and walk backwards applying the chain rule to get every parameter gradient in one sweep. It is not a separate algorithm from the chain rule — it is the chain rule with a schedule.
- Backpropagation Day 200
- An algorithm for efficiently calculating the gradient of a scalar loss function with respect to all network parameters using reverse-mode automatic differentiation.
- backreference Day 38
- A reference in a pattern to text an earlier group captured; \1 demands the same text the first group matched, so (\w+) \1 matches a doubled word.
- Backward pass Day 110
- Walking the computation graph from the output back towards the inputs, multiplying by each local derivative and accumulating the result at every node. After k steps the number being carried is the product of the last k local rates, which is exactly the gradient of the output with respect to the value at that point in the chain.
- bag of words Day 137
- Representing a document as counts of the words it contains, one column per word. The consequential decision is the vocabulary -- which words become columns at all -- which is a fitted statistic like any other and belongs on the training side of the split. The transform must also survive tokens it has never seen, by skipping them rather than crashing.
- Bag-of-Words (BOW) Day 158
- A text representation model that simplifies a document to an unordered multiset of word counts, disregarding grammar and word order.
- Balanced Class Weighting Day 160
- A technique that scales the loss contribution of each sample inversely proportional to its class frequency: w_c = N / (K * N_c).
- Ball-Tree Day 157
- A spatial indexing data structure that partitions data points into nested multi-dimensional hyperspheres (balls), effective for metric spaces where KD-Trees struggle.
- bandwidth Day 3
- The rate at which a memory or storage level can move data once transfers are flowing, measured in bytes per second — distinct from latency, which measures a single access.
- bandwidth Day 15
- The amount of data a connection can carry per second; important for large transfers but not for the round trips of connection setup.
- bandwidth Day 130
- The width of the kernel placed at each observation in a KDE -- the direct analogue of a histogram's bin width. A narrow bandwidth shows every bump in the data, including noise; a wide bandwidth smooths real structure away, including a genuine second mode. seaborn exposes it as bw_adjust, a multiplier on its own automatically chosen bandwidth.
- Bare column Day 86
- A column in the SELECT list of an aggregate query that is neither a grouping key nor inside an aggregate. There is no principled value for it, because the bucket holds many rows. PostgreSQL rejects such a query outright; SQLite picks an arbitrary row from the bucket and returns its value, with one documented meaningful exception alongside MIN or MAX. Outside that exception, treat a bare column as a bug that happens to run.
- bare except Day 66
- Writing "except:" with no type. It sits at BaseException level, so it catches Ctrl-C and sys.exit() along with everything else — which is why a program containing one inside a loop cannot be stopped from the keyboard. There is no situation in which it is correct.
- bare repository Day 32
- A repository that stores Git history but has no working directory of checked-out files; this is the form a server-side remote takes, and the lab uses one to act as a local "origin".
- base case Day 62
- The smallest version of a recursive problem — the one answered directly, with no further self-calls, such as factorial(1) returning 1 or the empty list summing to 0. The base case is the brake that stops the recursion; without a reachable one the function recurses forever.
- base class Day 68
- The class being inherited from, also called the superclass or parent. Every Python class ultimately has `object` as a base, which is where the default `__repr__`, `__eq__`, and `__hash__` come from.
- Base-rate neglect Day 113
- The tendency to ignore how rare an event was to begin with — its base rate — when a specific, vivid piece of evidence (such as a positive diagnostic test) is available. A 99%-accurate test for a rare disease can still mean a positive result is more likely a false positive than a true one, once the disease's low prevalence is properly weighed by the law of total probability, contrary to most people's intuitive estimate.
- Base-rate neglect Day 115
- The tendency to weigh how reliable a piece of evidence is (a test's stated accuracy) while ignoring how common the hypothesis was to begin with (the base rate, or prior). It is the mechanism behind the opening scenario's misconception: focusing on 99% accuracy while ignoring the 1-in-1,000 prevalence.
- base64 Day 25
- A reversible text encoding with no key, used to package binary or colon-separated data for transport; it hides nothing on its own, which is why Basic auth needs TLS.
- BaseEstimator Day 146
- scikit-learn's base class supplying get_params/set_params by inspecting __init__'s signature. The class this lesson's centrepiece measurement shows is necessary, in this library version, for Pipeline and cross_val_score compatibility -- not merely for direct use.
- BaseEstimator Day 153
- The scikit-learn base class supplying get_params, set_params and __sklearn_tags__ by introspecting __init__. Day 146 measured that a from-scratch estimator raises AttributeError inside Pipeline.predict() and cross_val_score without it, even though fit, predict and score work fine called directly; OLSRegressor inherits it for that measured reason.
- BaseEstimator Day 173
- The base class for all scikit-learn estimators, providing get_params and set_params parameter introspection for cloning and grid search.
- BaseException Day 66
- The root of the hierarchy. SystemExit, KeyboardInterrupt, and GeneratorExit hang directly off it, deliberately outside Exception, because they are control-flow signals rather than errors.
- Baseline Day 132
- The lower limit of a value axis -- the level from which marks are measured. Whether it is load-bearing depends entirely on the mark: it is part of a bar's encoding and not part of a line's. This is why "always start at zero" is right for bars and wrong for lines, and why stating the rule without the distinction produces charts on which nothing is visible.
- Baseline Day 143
- The score of the simplest thing that could work -- here a model always predicting the majority class, scoring 0.9200 with zero recall. Without it, 0.9435 reads as excellent; with it, as 2.35 points that must justify a model's maintenance cost.
- Baseline Model Day 190
- A simple, deterministic, or rule-based heuristic against which complex machine learning models are quantitatively benchmarked.
- Baseline Rate Day 161
- The performance achieved by a trivial heuristic (such as predicting the majority class or stratified random guessing), establishing the minimum bar for any valid model.
- bash Day 8
- The Bourne Again Shell, written by Brian Fox for the Free Software Foundation in 1989; the most widely documented shell and a common default on Linux systems.
- Basic auth Day 25
- An HTTP authentication scheme that sends a username and password joined by a colon and base64-encoded in the Authorization header; safe only over TLS.
- basicConfig Day 97
- The one-line convenience that quietly attaches a handler to the ROOT logger. Two behaviours worth knowing: it is why every module's getLogger(__name__) suddenly produces output, and it does nothing at all if the root already has a handler unless you pass force=True — which is why a second call appears to be ignored, and why a library must never call it.
- Basis Day 99
- A set of vectors from which every vector in the space can be built as a sum of scaled copies, using exactly one such combination per vector. The standard basis in two dimensions is (1, 0) and (0, 1), so writing v as (3, 4) is already shorthand for 3 times the first plus 4 times the second. This is why coordinates mean anything at all: a list of numbers is a set of instructions relative to a chosen basis, and changing the basis changes the numbers without changing the vector.
- Basis vector Day 101
- One of the vectors that is all zeros except a single 1, such as (1, 0) and (0, 1) in the plane. Feeding one into a matrix picks out exactly one column, so the columns of a transformation matrix ARE the images of the basis vectors. That lets you read a transformation matrix straight off a picture — work out where each basis vector lands and write those down as the columns — with no arithmetic at all.
- Basis vector Day 102
- One of a small set of vectors from which every other vector in the space can be built by scaling and adding. In the plane two are enough, and knowing where a linear transformation sends them determines where it sends everything else — which is the single most useful fact in the subject.
- Batch Day 101
- A stack of examples processed together, conventionally with one example per ROW so that example i lives at X[i], matching the layout of every CSV file and database table. Each row is computed independently of the others, which is exactly what makes batching worth doing: one multiply reuses the same weights across every example. Growing the batch changes the shape of X and nothing else — the weights and the bias belong to the layer.
- Batch gradient descent Day 153
- The update rule coef := coef - eta * gradient, applied to every row of the data on every iteration. Day 111's material, applied here to ordinary least squares' mean-squared-error loss, whose gradient is (2/n) X'(X coef - y).
- Batch Normalization Day 208
- A normalization layer that standardizes layer pre-activations across the mini-batch dimension, applying learned affine scale and shift parameters.
- Batch Prediction Day 194
- An inference pattern where multiple feature vectors are sent together in a single request and processed via vectorized matrix operations.
- Bayes Optimal Error Day 181
- The lowest possible prediction error rate achievable by any classifier due to irreducible noise.
- Bayes' theorem Day 115
- The identity P(hypothesis | evidence) = P(evidence | hypothesis) x P(hypothesis) / P(evidence), derived in two lines from the definition of conditional probability. It converts a likelihood -- how probable the evidence is under a hypothesis -- into a posterior -- how probable the hypothesis is given the evidence -- correctly weighting the prior probability of the hypothesis along the way.
- Bayesian Optimization Day 166
- A sequential design strategy for global optimization that builds a probabilistic surrogate model of the objective function to intelligently select the most promising evaluation points.
- Bayesian Shrinkage Day 170
- A regularization technique that pulls small-sample category estimates toward the global prior distribution mean.
- bbox_inches Day 128
- A savefig argument controlling how much of the Figure's canvas gets written to the output file. The default writes the whole canvas at its declared figsize; 'tight' instead crops the output to the bounding box of everything actually drawn, which is often what you want visually but breaks the exact figsize-times-dpi pixel arithmetic, since the trimmed size depends on the content.
- bearer token Day 25
- A credential sent in the standard Authorization header as "Bearer <token>"; possession alone grants access, so it must be guarded like cash.
- Behaviour-driven development Day 73
- A reframing of TDD around examples written in near-English Given/When/Then form, bound to Python step functions, so that a non-programmer can read and argue about the specification. Free tools include pytest-bdd and behave. Without such a reader, the extra layer is cost with no payer.
- Benchmark overfitting Day 144
- What happens when a public test set is selected on by thousands of researchers over years. No individual sees a test label; the aggregate is a selection over an enormous and uncounted K, and re-collected test data has shown substantial accuracy drops.
- Bernoulli distribution Day 114
- The distribution of a single trial with two outcomes, success with probability p and failure with probability 1-p. Mean p, variance p(1-p). Every other distribution on this page that counts successes is built from a sequence of Bernoulli trials.
- Bernoulli Naive Bayes Day 158
- A Naive Bayes variant designed for binary boolean feature vectors, modeling both the presence and absence of features.
- Bessel's correction Day 116
- Dividing a sample's sum of squared deviations by n-1 rather than n when estimating population variance, correcting a provable low bias of exactly (n-1)/n that arises because the sample's own mean is fitted to that sample and sits closer to it than the true population mean does. numpy.var() defaults to ddof=0 (the biased n divisor) unless ddof=1 is passed explicitly.
- Best linear unbiased estimator (BLUE) Day 149
- The specific claim Gauss-Markov makes about OLS: among all estimators that are (a) linear combinations of the observed y values and (b) correct on average, OLS has the smallest variance. It says nothing about estimators that are nonlinear or biased, some of which can do better -- which is exactly what Huber demonstrated under heavy-tailed errors here.
- BGP Day 16
- The Border Gateway Protocol, by which autonomous systems advertise to their neighbors which address blocks they can reach, stitching independent networks into one internet.
- Bias Day 101
- A vector added to a layer output after the matrix multiply, with one entry per OUTPUT unit rather than per example. It is added to every row of the product by broadcasting, so a layer two units wide takes exactly two numbers however large the batch is. Getting its length wrong raises a broadcasting ValueError rather than failing silently, which is one of the few places in this area where you are told.
- Bias Day 145
- How far the average prediction -- averaged over training sets -- sits from the truth. An error the model class makes every time, in the same direction. Measured here at 4.2985 for a straight line fitted to a cubic, and 0.0033 for a cubic fitted to a cubic.
- Bias Correction Day 206
- Dividing first and second moment buffers by (1 - beta^t) to counteract the zero-initialization bias during early training steps.
- Bias Gradient (db) Day 200
- The vector of partial derivatives dL/db indicating the gradient direction for each layer bias parameter.
- Bilinear Day 105
- The interpolation rule that blends the four pixels surrounding the sampled position, weighted by how close the position is to each — linear in x, then linear in y, hence "bi-linear". The four weights sum to exactly 1, so it can neither brighten nor darken an image overall. Produces smooth edges and produces values that were never in the input, which is both the point and the cost. Right for photographs and any continuous quantity; wrong for anything whose values are categories.
- bin width Day 130
- The chosen width of each interval a histogram sorts values into. Every histogram picks one -- whether the person drawing it thought about it or not -- and the same underlying data can look unimodal, bimodal, or like pure noise depending only on this choice. Sturges, Scott and Freedman-Diaconis (below) are three different rules for choosing it automatically.
- Bin width as an editorial choice Day 132
- The recognition that a histogram's bin width is selected rather than given, and that the selection can decide the conclusion. On the lesson's sample, Sturges' rule draws one hump and the Freedman-Diaconis rule draws two, supporting opposite statements about modality from the same 400 values. Both rules are citable, which is why "I used a standard rule" is not a defence.
- binary Day 1
- A way of writing numbers and encoding all data using only two digits, 0 and 1, which map directly onto a switch's off and on states.
- Binary Cross-Entropy (BCE) Day 199
- The negative log-likelihood loss for binary classification measuring cross-entropy between two Bernoulli probability distributions.
- Binary Cross-Entropy (Log Loss) Day 155
- The loss function used for binary classification, measuring the negative log-likelihood of the true labels given predicted probabilities.
- binding Day 44
- The link between a name and the object it refers to, created by assignment (name = object). Re-binding moves the name to a different object.
- binning Day 137
- Turning a continuous column into a categorical one by choosing boundaries. A bin boundary is a decision with the same power as Day 130's bin width: on the same 500 rows, equal-width edges put 4 rows in the top bin at a rate of 1.000 while equal-count edges put 167 rows in it at a rate of 0.563. Both are correct; only one of them is what you meant.
- Binomial distribution Day 114
- The distribution of the number of successes in n independent Bernoulli(p) trials. Mean np, variance np(1-p). As n grows large while n*p is held fixed at a constant lambda, the Binomial distribution converges to the Poisson(lambda) distribution — a convergence this lesson's lab measures directly.
- Binomial standard error Day 117
- The standard error of a sample proportion (equivalently, a model accuracy measured on n examples): sqrt(phat * (1 - phat) / n). For an accuracy of 91.4% on 500 examples, this comes out to about 1.25 percentage points -- large enough that a 0.3-point difference between two models sits at only about 0.24 standard errors, well inside the range of pure sampling noise.
- bit Day 1
- The smallest unit of information, a single 0 or 1.
- bit Day 4
- A single binary digit, 0 or 1 — the smallest unit of information, physically realized as one two-state switch.
- bit depth Day 5
- How many bits represent each audio sample or color channel, setting how finely a value can be recorded.
- BLAS Day 101
- Basic Linear Algebra Subprograms — a standard interface for vector and matrix routines, published from 1979 onwards, with many competing implementations such as OpenBLAS, Intel MKL and Apple Accelerate. NumPy does not implement floating-point matrix multiplication itself; it calls out to whichever BLAS it was built against. Critically, BLAS matrix-multiply routines exist only for floating-point and complex types, which is why an int64 product in NumPy is measurably far slower than a float64 one of the same shape and values — the integer case falls back to NumPy own compiled loop and never reaches BLAS at all.
- Blending Day 168
- A simplified ensembling method that trains the meta-learner on a single holdout validation split rather than full out-of-fold cross-validation.
- Blocking call Day 96
- A function that does not return until its work is finished and that does not yield to any scheduler while it waits. time.sleep, a synchronous HTTP client, a synchronous database driver, a read from a slow filesystem. Inside a coroutine it is the single most expensive mistake in async Python: it holds the loop only thread, so every other task stops, nothing is raised, and every result is still correct. Measured here at five times slower with 211 milliseconds of starvation inflicted on an unrelated task. The repair for code you do not own is asyncio.to_thread.
- body Day 18
- The optional payload of a message — the JSON prompt you send in a request, or the HTML or JSON data returned in a response.
- Bonferroni correction Day 118
- A simple, conservative fix for multiple comparisons: test each of m hypotheses at alpha/m instead of alpha, which pulls the family-wise error rate back down near the original alpha. Simulated in this lesson at 0.0515 against an analytic target of 0.0488.
- Bonferroni correction Day 136
- Dividing the significance threshold alpha by the number of comparisons, m, so that the family-wise error rate across all m tests stays near the original alpha. Exact and conservative when m is known and correct; useless when the true number of comparisons run exceeds the reported one.
- bool Day 44
- The boolean type with the two values True and False. A subtype of int, so True behaves as 1 and False as 0 in arithmetic. Immutable.
- boolean Day 50
- A value with exactly two possibilities, `True` or `False`, and Python's type (`bool`) for it. Named after George Boole, it is the smallest unit of a decision — a single yes or no — and every comparison produces one.
- boolean mask Day 122
- A Series of True/False values, one per row of the DataFrame it was built against, sharing that DataFrame's index. df[mask] keeps only the rows where mask is True. A mask is not a bare array of booleans; its index is what makes it possible to build a mask from one frame and apply it correctly to a differently-ordered version of the same frame.
- Boolean mask Day 104
- An array of True and False values, one per element, produced by a comparison such as a > 50. Because a comparison on an array is an array, a mask can be summed to count, averaged to get a fraction, negated with the tilde, combined with the ampersand and pipe operators, and used to index or to assign. It must be & and | rather than the keywords and and or, because a keyword is control flow rather than an operator and NumPy has no way to redefine it.
- Bootstrap Day 117
- A technique, introduced by Bradley Efron in 1979, for estimating a statistic's standard error by resampling one dataset with replacement, recomputing the statistic on each resample, and reading the standard error off the spread of the results -- no formula for the statistic's own sampling distribution required. Checked in this lesson against a known formula for the mean (agreement within about 1%) and applied to the median, where no formula exists.
- bootstrap (resampling) Day 129
- A method for estimating the sampling variability of a statistic by repeatedly resampling the observed data with replacement, recomputing the statistic on each resample, and reading the spread of the results -- the same technique Day 117 introduced for the sampling distribution of the mean. seaborn's default error bar on barplot and pointplot is a bootstrapped confidence interval, which is why it is random unless a seed is fixed.
- Bootstrap Aggregation (Bagging) Day 163
- An ensemble technique that trains multiple base estimators on bootstrap samples drawn uniformly with replacement from the original dataset.
- Bootstrap interval on the margin Day 154
- A 95 percent interval built by resampling the test rows with replacement thousands of times and recomputing both RMSEs on each resample. Computed here as [5.5852, 22.3324] -- since it excludes zero, the model is distinguishable from baseline at this test-set size.
- Boruta Algorithm Day 172
- An all-relevant feature selection method that compares real feature importances against randomly permuted shadow noise copies.
- bound method Day 67
- What you get when you reach a function through an instance: an object holding `__func__`, the original function, and `__self__`, the instance. Calling it calls the function with `__self__` supplied as the first argument.
- Boundary Day 74
- A place where code reaches outside its own process — the clock, the network, the filesystem, randomness, the environment, or another process. Every boundary makes a test slower, less reliable, or less predictable, and the six of them are the whole subject of this lesson.
- Boundary Day 94
- The line where data crosses from somewhere you do not control into somewhere you do — an HTTP body, a CSV row, an environment variable, a config file, a message off a queue, a language model's reply. On one side it is somebody else's problem; on the other it is your responsibility. Validation is what you do at that line, and the practical rule is that there should be a small number of such lines and each should have a name.
- branch Day 29
- A separate line of commits that splits off from the main line so you can experiment or build a feature in isolation without disturbing others.
- branch Day 31
- A separate line of development, represented in Git as a movable pointer to a commit; creating one is instant because it copies nothing, only writes a small pointer.
- branch Day 50
- One of the alternative paths through a conditional — the block under an `if`, `elif`, or `else`. In an `if`/`elif`/`else` ladder the branches are mutually exclusive: the first whose condition is true runs, and the rest are skipped.
- Branch coverage Day 77
- The fraction of conditional outcomes that occurred — for an if statement, the true path and the false path count separately. Strictly more informative than line coverage, because it can see an else that was never taken. Enabled in coverage.py with branch = true.
- branch prediction Day 2
- The hardware's educated bet on which way a conditional jump will go, made so the pipeline can keep fetching; a wrong bet forces the speculative work to be discarded.
- Branch protection Day 77
- A repository setting that requires named checks to pass before a pull request can be merged, and forbids pushing straight to the protected branch. It lives in the repository's configuration rather than in the workflow file, and it is what turns a red mark everybody scrolls past into a merge that cannot happen.
- break Day 51
- A statement that immediately exits the innermost loop it is in, jumping to the first line after the loop; the mechanism behind stopping a search as soon as it succeeds.
- Breakdown point Day 116
- The largest fraction of a dataset that can be replaced with arbitrarily extreme values before a statistic can be dragged to an arbitrary value. The mean's breakdown point is exactly zero; the median's is close to 50%.
- breakpoint Day 37
- A marker on a line that tells the debugger to pause the program when execution reaches it; a conditional breakpoint pauses only when a condition you specify is true.
- breakpoint Day 48
- A built-in function (added in Python 3.7) that pauses the program where it is called and drops you into the pdb debugger, replacing the older import pdb; pdb.set_trace() incantation.
- Brier Score Day 176
- Mean squared error between predicted probabilities and actual binary outcomes, quantifying probabilistic calibration.
- Brittleness Day 79
- The property that makes scrapers break: you are reading a user interface, not a data source, and nobody sends a deprecation notice before renaming a div. A redesign, a class rename, a field moving into JavaScript or a new cookie banner will each break a working scraper without warning.
- Broadcasting Day 100
- NumPy's rule for combining arrays of different shapes by conceptually stretching the smaller one. Shapes are lined up from the right-hand end, a missing entry counts as 1, two dimensions are compatible when equal or when one is 1, and anything else is a ValueError. Nothing is copied — the stretching is a fiction maintained by reading the smaller array's memory more than once. It is the point where NumPy stops doing the obvious thing, and therefore where silent wrong answers begin.
- Broadcasting Day 104
- How NumPy reconciles arrays of different shapes in an operation. Its documentation defines it as: "the smaller array is broadcast across the larger array so that they have compatible shapes", with shapes compared from the trailing dimension leftwards and two dimensions compatible when they are equal or one of them is 1. No copy is made — a scalar added to a million elements is not turned into a million scalars. Failure raises ValueError: operands could not be broadcast together. np.newaxis is how you insert a length-1 dimension deliberately, turning a row into a column so that every pairing can be computed at once.
- Broadcasting Day 199
- The automatic arithmetic expansion of lower-dimensional tensors to match the shape of higher-dimensional arrays during elementwise operations.
- bucket Day 39
- The top-level container in object storage that holds objects, each stored under a key; the S3-style equivalent of a namespace for your blobs.
- buffer Day 47
- A temporary in-memory holding area where output collects before being written out in efficient chunks; flushing empties it early.
- buffering Day 64
- The batching of small reads and writes into a few large operations, because a system call per character would be catastrophically slow. Its cost is that a write which has returned successfully may still be nowhere near the disk.
- Build backend Day 83
- The component that actually turns a source tree into artifacts — setuptools, hatchling, flit_core, poetry-core. Named in `[build-system] build-backend`. It is distinct from the build FRONTEND (`python -m build`, or pip), which knows how to ask but builds nothing itself. PEP 517 defined the interface between them, which is why swapping backends is a two-line edit.
- Build matrix Day 77
- Running the same job once per combination of listed variables — most often several Python versions — in parallel. It is how a support claim gets checked: if a package says it requires Python 3.10 or newer, that is a claim about several interpreters, and a claim nothing verifies is a claim that quietly stops being true.
- built-in (scope) Day 58
- The outermost scope, holding names Python always provides without any import — print, len, sum, range, max, and the rest. Every name search eventually reaches it, which is why these names work anywhere.
- builtin generic Day 69
- The modern spelling for a parameterised container type, written with the builtin itself: `list[int]`, `dict[str, float]`, `tuple[int, ...]`. Older code imports capitalised equivalents from `typing` and means the same thing.
- byte Day 1
- A group of 8 bits, enough to store one of 256 possible values, such as a single ASCII character.
- byte Day 4
- A group of 8 bits, able to hold 256 distinct patterns; the smallest unit of memory most machines address, standardized at 8 bits by IBM's System/360 in 1964.
- byte-identical output Day 133
- The property that two runs of a generator over the same input produce files that are equal byte for byte. Achieved by removing every clock reading, hostname and unseeded random draw from the output. For the Markdown in this lab it holds generally; for the figure PNGs it was measured across two runs on one machine only, because matplotlib rasterises text through FreeType and a different font stack can produce different pixels from identical code.
- Byte-identical rebuild Day 140
- The property that running a pipeline twice produces outputs whose bytes match exactly. It requires that nothing reads a clock, every random draw is seeded, text layout is computed rather than hand-wrapped, and image writers are told not to stamp their own version into the file.
- byte-order mark Day 65
- An invisible byte sequence (EF BB BF in UTF-8) that some programs write at the start of a file. It silently prefixes the first column name, so lookups fail in a way that looks like missing data. Opening with encoding="utf-8-sig" strips it.
- Bytecode program Day 85
- What SQLite compiles a statement into: a small program in its own instruction set, executed by a virtual machine. This is what a prepared statement actually is, which is why preparing once and running many times with different bound values skips the tokenizer, parser, planner and code generator on every repeat.
- C3 linearization Day 68
- The algorithm Python has used since version 2.3 to compute the MRO. It guarantees local precedence — a class always precedes its parents — and monotonicity — the order bases are listed in is preserved. If no consistent order exists it raises TypeError at class-definition time rather than guessing.
- cache Day 1
- Small, very fast memory on the CPU chip that keeps recently used data close to the processor so it rarely has to wait on slower RAM.
- cache Day 3
- A small, fast memory that holds copies of recently or soon-to-be-used data from a larger, slower level so most accesses are served at the fast level's speed.
- cache Day 39
- A fast, volatile copy of frequently used data placed in front of a slower store so most reads never reach the slow store; disposable, because the durable data lives elsewhere.
- Cache eviction Day 92
- The policy a cache uses to decide what to discard when it runs out of room — least recently used being the most familiar. It is a property that only makes sense for a store you are allowed to lose: eviction is a correct outcome for a cache and a data-loss incident for a database, and the defining question is which of the two you have built.
- cache invalidation Day 39
- The problem of keeping cached copies from going stale when the underlying data changes, often handled with a time-to-live (TTL) that expires each entry after a set time.
- cache line Day 3
- The fixed-size chunk (commonly 64 bytes) that moves between RAM and cache: a miss on one byte loads the whole line, so neighboring data arrives for free.
- calibration Day 138
- The property that a score can be read as a probability: among everyone scored 0.7, seven in ten really are positive, in every group. The lesson's constructed population is calibrated exactly, with a maximum deviation of zero, which is what makes the impossibility result visible rather than arguable.
- Calibration Day 115
- Checking whether a model's stated confidence matches its actual accuracy, typically by bucketing predictions by their stated probability and measuring the empirical accuracy within each bucket -- a direct application of conditioning as restriction. A model trained on a balanced dataset and deployed against a rare-positive-class population will typically be poorly calibrated, in the same shape as the opening scenario's base-rate failure.
- call stack Day 37
- The ordered chain of function calls that led to the currently executing line — who called whom, with the current function on top — which you can navigate to inspect each caller's variables.
- call stack Day 48
- The ordered chain of function calls active at a given moment — who called whom — which the traceback lists oldest-first so the most recent call sits nearest the error.
- call stack Day 62
- The stack of frames the interpreter keeps for all the function calls currently in progress: a frame is pushed when a function is called and popped when it returns. Recursion relies on it so each nested call has its own private workspace, and its finite size is why recursion depth is limited.
- call stack Day 66
- The chain of function calls currently in progress, each one a frame holding its own local variables and position in the code. A raised exception unwinds this chain outward, frame by frame.
- Canary Deployment Day 190
- A deployment technique where a small fraction of live user traffic is routed to a new model version to monitor reliability before full rollout.
- Cancellation Day 96
- In asyncio, stopping a task by raising CancelledError inside it at its next suspension point. It is an exception rather than a kill, which is why ordinary Python cleanup still works — finally blocks run, context managers exit, sockets close. Two consequences: a task that never awaits cannot be cancelled, because there is nowhere to deliver the exception; and catching CancelledError without re-raising it produces a task that refuses to stop.
- candidate figure Day 133
- A chart made during exploration that has not yet earned a place in the report. In the lab it is a `Candidate` object carrying a slug, an optional question, and -- if it has no question -- a `dropped_because` line. Twelve go into the pipeline and five come out, a survival rate of 41.7%.
- Candidate key Day 85
- Any column or set of columns that uniquely identifies a row. A table may have several; the primary key is the one you chose. In the lab, both member_id and email are candidate keys for members, and member_id is the primary key — because an address can change and everything referring to a row would have to change with it.
- Candidate pipeline Day 147
- One complete, fittable scikit-learn Pipeline -- a specific estimator with specific hyperparameters, any preprocessing folded in. This lesson sweeps 36 of them: 15 k-nearest-neighbours settings, 11 logistic-regression regularisation strengths, 10 decision-tree depths.
- Candidate pipeline Day 154
- One complete, fittable scikit-learn Pipeline -- a specific estimator with specific hyperparameters, any preprocessing folded in. This lesson sweeps 23 of them: 11 ridge regularisation strengths, 11 lasso regularisation strengths, and 1 plain OLS.
- CAP theorem Day 92
- The result that when a network partition occurs, a distributed data store cannot provide both consistency and availability, and must give up one of them for as long as the partition lasts. Formulated by Eric Brewer in autumn 1998, published as a principle in 1999, presented as a conjecture at the 2000 Symposium on Principles of Distributed Computing, and proved by Seth Gilbert and Nancy Lynch in 2002. It is not "pick two of three": nobody chooses partition tolerance, and with no partition a well-built store gives consistency and availability at once.
- Capacity control Day 145
- Choosing how much a model may express, rather than maximising it. Structural risk minimisation is the formal version; a max depth, a dropout rate, a weight decay and an epoch budget are all instances of it.
- Caption contract Day 132
- The reusable review check this lesson builds: a caption stating a claim a reader could disagree with, a labelled y axis, a non-zero baseline named in the caption, and either a zero baseline or an explicit disclosure. It passes an honest chart, fails a truncated one, and passes a line on a non-zero baseline whose caption says so -- because it forbids breaking a rule in silence rather than forbidding the break.
- capture group Day 38
- A parenthesised group whose matched text the engine stores, numbered left to right (\1, \2, ...), so it can be extracted, reformatted, or referenced later.
- Cardinality Day 86
- How many rows there are, or how many distinct values a column holds. It is the quantity every stage of a SELECT changes or preserves: WHERE and HAVING can only reduce it, GROUP BY replaces a row count with a bucket count, SELECT never changes it, ORDER BY never changes it, and LIMIT truncates it. Low cardinality — few distinct values — is also what makes a column a good grouping key and a poor index.
- Cardinality Day 87
- How many rows on one side of a relationship correspond to how many on the other: one-to-one, one-to-many, or many-to-many. It decides where the key goes. In a one-to-many the foreign key lives on the many side, because a column holds one value; in a many-to-many neither side can hold it, so the relationship needs a table of its own.
- Cardinality Day 89
- How many distinct values a column holds. High cardinality — a trace id, a timestamp, a foreign key — makes for a useful index. Low cardinality, such as a status column with three values, usually does not.
- cardinality (of a join) Day 124
- A claim about how many times a merge key may repeat on each side of a join -- for example, that a customer ID appears at most once in a customer table (one) but many times in an orders table (many). validate= turns a stated cardinality claim into an enforced check that pandas performs before completing the merge.
- CART (Classification and Regression Trees) Day 162
- The standard greedy binary recursive partitioning algorithm developed by Breiman et al. using Gini impurity for classification and variance reduction for regression.
- Cartesian product Day 87
- Every row of one table paired with every row of another, which is what a join with no condition produces — four books and seven authors give twenty-eight rows. Usually accidental, caused by a forgotten join condition, and the rule of thumb is that N tables need at least N minus 1 of them. At real scale it is a denial of service: two tables of ten thousand rows produce a hundred million, and the database will honestly try.
- Cascade delete Day 88
- A foreign key rule, ON DELETE CASCADE, that removes child rows when their parent is deleted. Correct when the child is meaningless without the parent, such as a loan with no borrower. The trap worth remembering: changes() reports only the row you named, so the cascaded rows are real but uncounted, and an unintended cascade is therefore easy to miss.
- cast Day 75
- A function that asserts a type to the checker and does nothing whatsoever at runtime — no check, no conversion, no safety. Prefer `isinstance`, which narrows and checks; reach for `cast` only where you genuinely know something the checker cannot, and write a comment saying what.
- cat Day 10
- A command that prints the contents of one or more files to standard output, commonly used to view a short file or feed a file into a pipeline.
- Catastrophic cancellation Day 108
- The loss of significant digits that happens when two nearly equal floating-point numbers are subtracted. The leading digits agree and cancel exactly, leaving only the trailing digits — which are the least accurate ones — to carry the whole result. It is the mechanism behind the rounding-error term above, and it is not confined to calculus: it appears in variances computed as E[x²] − E[x]², in differences of large timestamps, and in running balances.
- CatBoost Day 165
- A Yandex open-source gradient boosting library renowned for native categorical feature handling via ordered target statistics and symmetric oblivious trees.
- Catch-up Day 81
- Running a job whose scheduled moment passed while the machine was unavailable. systemd offers it with Persistent=true and launchd does it on wake; cron has no equivalent and never mentions the missed run. Whether catch-up is correct depends on whether each period's work is a distinct artefact or merely the latest state.
- Categorical Cross-Entropy (CCE) Day 199
- A loss function measuring the divergence between true categorical distributions and predicted multi-class probability distributions.
- categorical palette Day 127
- A set of maximally distinguishable hues, such as tab10 or seaborn's colorblind, for nominal data only. Five tab10 entries measure a rank correlation of -0.20 between position and luminance: the palette carries no order, by design, because "as different as possible" has no direction.
- category dtype Day 121
- A pandas dtype that stores each distinct value once, in a lookup table, and represents every row as a small integer code pointing into it. Converting a low-cardinality string column to category trades repeated string storage for one lookup table plus one integer per row, measured here as a memory-usage ratio rather than a fixed byte count.
- Cauchy distribution Day 117
- A continuous distribution, named for Augustin-Louis Cauchy, with no defined mean or variance -- its tails are too heavy for either integral to converge. The standard counterexample to the central limit theorem: the mean of n Cauchy draws is itself Cauchy distributed, with exactly the same spread, for every value of n. Measured in this lesson's lab, its sample mean's interquartile range changed by only 2% from n=10 to n=1,000, against an Exponential population's 9.85x tightening over the same range.
- Caveats and Recommendations Day 182
- Known failure modes, unexpected performance drops, and guidelines for downstream maintainers.
- Ceiling effect Day 147
- When a metric's possible values are so coarse, or so close to its maximum, that a real difference cannot be observed. Here, 114 test rows move accuracy in steps of about 0.0088, which is part of why the leaky-selection gap lands at exactly zero on some seeds.
- cell.metadata.execution Day 139
- The dictionary nbclient writes into a code cell's metadata on every execution, holding four wall-clock ISO-8601 timestamps (iopub.status.busy, iopub.execute_input, shell.execute_reply, iopub.status.idle). Measured directly in this lesson's lab, this field -- not execution_count -- is what makes two runs of identical, deterministic code differ as committed JSON.
- CellExecutionError Day 139
- The exception nbclient raises when a cell's execution fails during an nbclient run. It carries the original exception's name and message (.ename, .evalue) and names the failing cell's execution position in its string representation, which is what lets a CI log point directly at the broken cell.
- Central difference Day 108
- The estimate (f(x + h) − f(x − h)) ÷ (2h): a secant straddling the point rather than reaching forward from it. It is the average of the forward and backward differences, and that averaging cancels their leading errors, leaving a truncation error proportional to h² rather than h. Halving the step quarters the error. On e^x at x = 1 with h = 1e-5 it was over two hundred thousand times more accurate than the forward difference on the authoring machine, for one extra function call. Note the divisor is 2h, not h; forgetting the 2 doubles every answer.
- Central difference Day 109
- The estimate ( f(x+h) − f(x−h) ) / 2h, carried over from Day 108 and adapted here by moving only one coordinate. Its truncation error shrinks like h squared, against h for a one-sided forward difference, at a cost of one extra evaluation of f. On a quadratic it is algebraically EXACT at any h, since ((x+h)² − (x−h)²)/2h = 4xh/2h = 2x; on a cubic the error is exactly h squared with no other terms. Divide by 2h and not h: the point moved a total distance of 2h.
- Central limit theorem (CLT) Day 117
- The result that, whatever shape a population has, the sampling distribution of its mean approaches a Normal distribution as n grows, provided the observations are independent and the population has finite variance. First appeared as a special case in Abraham de Moivre's 1733 work on the Binomial distribution, generalized by Pierre-Simon Laplace by 1812, and given its modern name by George Polya in 1920.
- centralized VCS Day 29
- A version control design in which one server holds the authoritative history and developers keep only working copies, so most operations require the network (for example, Subversion).
- centred window Day 131
- A rolling window (rolling(..., center=True) in pandas) whose span is positioned symmetrically around each point in time, using both past and future observations relative to it. A centred window's peak lines up with the true peak exactly, at the cost of being unusable in a live, real-time setting where future observations do not yet exist.
- Centroid Day 183
- The geometric mean (center of mass) of all data points belonging to a specific cluster in multi-dimensional space.
- Centroid Profiling Day 189
- Calculating the mean or median values of all business features across each cluster to define distinct qualitative personas.
- Ceremony Day 77
- A check that costs more attention than it saves — one that fails on things nobody would have fixed anyway, whose failures are routinely overridden, or whose usual fix is adding a suppression comment rather than changing the code. Removing a rule that mainly generates suppressions is not a lowering of standards; it is the removal of a tax funding nothing.
- certificate Day 19
- A signed digital document that binds a domain name to a public key and carries an expiry date, presented by a server to prove its identity.
- Certificate Authority Day 19
- A trusted organization (CA) that verifies control of a domain and signs certificates for it; browsers ship with a list of trusted CA roots.
- chain of trust Day 19
- The sequence of signatures from a site certificate up through one or more intermediate CAs to a root the browser already trusts; if any link fails, the certificate is rejected.
- Chain rule Day 110
- The rule that the derivative of a composition is the product of the local rates along it: dy/dx = dy/du x du/dx, where u = g(x). The outer derivative is evaluated at the inner value u, never at x. Stated without notation: if A changes twice as fast as B and B changes three times as fast as C, then A changes six times as fast as C.
- Chain Rule Day 200
- A fundamental theorem of calculus stating that the derivative of a composite function f(g(x)) is f prime(g(x)) * g prime(x).
- Chain rule for probability Day 113
- The multiplication rule extended to any number of events: P(A and B and C) = P(A) x P(B|A) x P(C|A,B), each factor conditioned on everything decided before it. It shares its name with, and nothing else in common with, Day 110's chain rule for derivatives — the resemblance is that both build a quantity by multiplying local pieces each evaluated in the correct context, and the resemblance stops there.
- chained assignment Day 120
- Writing two indexing operations back to back in one assignment statement, such as df[mask]["col"] = value. The first indexing operation produces a temporary object; the assignment writes into that temporary, which is then discarded, so the original object is never modified. On pandas 3.0.5 this raises a ChainedAssignmentError warning.
- chained comparison Day 50
- Writing two comparisons in one expression, as in `0.0 <= score <= 1.0`, which means `score` is between 0.0 and 1.0 inclusive. Python evaluates the middle value once, making the form both readable and correct.
- ChainedAssignmentError Day 120
- A Warning subclass (not a raised exception) that pandas 3.0.5 emits when it detects chained assignment. The statement still completes and execution continues, which is why the warning is easy to miss if warnings are filtered or the script's stderr is not read.
- Channel Day 105
- One of the stacked planes of a colour image. A standard colour image has three — red, green and blue — giving an array of shape (height, width, 3), where the last axis is the channel. Each channel is a greyscale matrix in its own right. The point that matters for this lesson: the three channels share their COORDINATES, and a transformation acts on coordinates, so the same matrix transforms all three and colour introduces no new mathematics at all.
- character class Day 38
- A set of characters written in square brackets, any one of which may match; [abc] matches a, b, or c, [a-z] any lowercase letter, and [^0-9] any non-digit.
- Characteristic equation Day 106
- The polynomial equation det(A minus lambda I) = 0, whose roots are the eigenvalues. It is not an arbitrary formula but a direct translation of the geometry: rearranging A v = lambda v gives (A minus lambda I) v = 0, which says a non-zero vector is sent to the origin, and only a matrix with zero determinant does that. For any 2x2 it always works out to lambda squared minus (trace) lambda plus (determinant) = 0, so trace and determinant are the only two numbers you need. Derive that once and never again. Its DISCRIMINANT carries the whole character of the matrix: positive means two distinct real eigenvalues, zero means one repeated, negative means none that are real. Worth knowing that no serious numerical library computes it — the QR algorithm finds eigenvalues without ever forming the polynomial, because polynomial root-finding is unstable in a way that eigenvalue-finding need not be.
- chartjunk Day 127
- Tufte's term for decoration that adds no information -- three-dimensional effects on two-dimensional data, textured fills, ornamental frames. The measurable version of the complaint is a low data-ink ratio.
- Chebyshev distance Day 107
- The L-infinity distance: the largest single absolute difference. Named after Pafnuty Chebyshev (1821-1894), whose approximation theory minimises the worst error rather than the total one. It is the measure hiding inside every tolerance specification, and it is the one that will accept a part that is slightly out on every dimension while rejecting a part that is exact on all but one. Both L1 and L2 rank those two the other way round, and both are answering a question the inspection department did not ask.
- CHECK constraint Day 88
- A constraint holding an expression that must not evaluate to false for a row to exist: copies >= 0, due_on >= borrowed_on, label IN (three values). It is the most expressive constraint and the one that reads most like an English sentence. Its documented limit is that the expression may not contain a subquery, so any rule spanning more than one row is not a CHECK.
- CHECK constraint Day 91
- A rule the database enforces on every insert and update. A column-level CHECK can only see its own column, so a rule comparing two columns must be written at table level. It is also worth remembering that CHECK (x <> 'bad') is unknown rather than false when x is NULL, and therefore lets the row through.
- check_estimator Day 153
- scikit-learn's own compliance suite for a hand-built estimator. Run against OLSRegressor here: 48 of 52 checks pass; the two failures, named rather than suppressed, are both about input validation this implementation does not perform.
- check_estimator() Day 146
- scikit-learn's own conformance suite for verifying an object satisfies the estimator contract. Measured against this lesson's hand-built classifier at 52 checks, 48 passed, 2 skipped, 2 failed -- both failures explained, not suppressed.
- check_same_thread Day 90
- The connect() argument that controls whether the module enforces its rule that a connection is used only by the thread that created it. Passing False removes the exception and does not remove the problem: you must then serialise access yourself. One connection per thread, built by the same factory, is the answer that keeps working. sqlite3.threadsafety describes what the underlying C library supports, not what your object lifetimes do.
- checkout Day 31
- The classic Git command for switching branches (git checkout NAME) or creating and switching (git checkout -b NAME); it also does other jobs, which is why git switch was later split out of it.
- checkpoint Day 126
- An intermediate result written to disk (here, Parquet) between expensive pipeline stages, so a failure partway through does not require re-running everything from the start. Parquet is used rather than CSV because it preserves dtypes exactly, including a nullable Int64 column's missing values, where CSV round-trips everything through text and loses them (Day 121).
- Checkpointing Day 210
- Persisting complete training state (model, optimizer, scheduler, epoch) to disk to enable recovery and auditability.
- checksum pinning Day 134
- Recording the SHA-256 hash of a downloaded file's bytes alongside its source URL and retrieval date, so anyone -- including yourself, months later -- can prove the file they have is the exact file the source served. "Downloaded from X" is a claim; "downloaded from X, SHA-256 abc123..." is checkable.
- Cherry-picked window Day 132
- A subrange of a time series chosen, deliberately or not, so that the trend within it supports a desired claim. The lesson's series has a fitted slope of -0.7305 per week over its first half, +0.7045 over its second, and -0.0131 over the whole -- three true statements about three windows, only one of which is a statement about the series. The defence is to show the full series and mark the window inside it.
- Chevalier de Méré's paradox Day 113
- A 1650s gambling puzzle: betting on at least one 6 in 4 rolls of one die (P ≈ 0.5177, favourable) was believed equal to betting on at least one double-six in 24 rolls of two dice (P ≈ 0.4914, unfavourable), reasoning that a 6x smaller per-roll probability should be exactly offset by 6x more rolls. It is not offset, and the correspondence between Pascal and Fermat that resolved it is usually credited as founding the mathematical theory of probability.
- Chi-squared goodness-of-fit test Day 119
- A test comparing observed category counts against counts expected under a stated hypothesis (here, a 50/50 split). With two categories and one degree of freedom, the test statistic is the square of a standard normal variable, so its p-value has the closed form erfc(sqrt(chi2 / 2)) -- computable with nothing beyond the math module.
- Chicago school Day 73
- Also called classic or inside-out TDD. You start with the domain logic, use real collaborating objects, and assert on state and return values, using test doubles only where the real thing is genuinely unavailable. Its tests survive refactoring because they say what the code does rather than how.
- chmod Day 9
- The command that changes a file or directory's permissions, using either symbolic form (such as +x) or octal form (such as 754).
- Chronological split Day 144
- Training on the past and testing on the future, because deployment is chronological. Shuffling beat it in 20 of 20 constructions here, and the chronological score turned out indistinguishable from the majority baseline where the shuffled one looked like real signal.
- chunksize Day 121
- A read_csv() argument that turns the function into an iterator of DataFrames, each holding chunksize rows, instead of one DataFrame holding the whole file. Lets a file larger than available memory be processed one piece at a time; an aggregate computed chunk by chunk must equal the whole-file aggregate exactly.
- CI check Day 33
- A continuous-integration check — an automated build, test, or linter that runs on a pull request and reports pass or fail before a human reviews the change.
- CI/CD Day 41
- Continuous integration and continuous delivery/deployment: a shared server that automatically runs checks on every change (CI) and, when they pass, packages and releases the result (CD).
- CIDR Day 16
- Classless Inter-Domain Routing notation, which writes an address block as an address plus a slash and a number of fixed leading bits, such as 192.168.1.0/24 (256 addresses).
- CIELAB and delta-E Day 127
- A colour space built so that Euclidean distance roughly tracks perceived difference, and the distance measured in it. The CIE76 formula is plain Euclidean distance in CIELAB. As a rough guide from the literature, about 2.3 is the just-noticeable difference between adjacent patches.
- cipher Day 19
- An algorithm used to encrypt and decrypt data; TLS negotiates a cipher suite (a bundle of algorithms for key agreement, bulk encryption, and integrity) during the handshake.
- Circuit Breaker Day 190
- A software resilience pattern that detects model invocation failures and redirects requests to a fast heuristic fallback.
- circular import Day 59
- A situation where two modules each import the other, so neither can finish loading — Python cannot complete module A while it waits on module B, which in turn waits on A. The fix is to keep dependencies pointing one way, or to extract the shared code into a third module both import.
- claim-carrying caption Day 133
- A caption that states something a reader could disagree with, so the figure either supports it or fails to. "Revenue by region" is a label -- it restates the axes and asserts nothing. "Three regions grew while the West fell 8.6%" is a claim: it names a direction, a size and a comparison, and a reader who thinks it is wrong knows exactly where to look.
- Clamping Day 103
- Forcing a value back inside a valid range before using it. A vector compared with itself should give a cosine of exactly 1.0, and floating-point rounding sometimes gives a hair more: three of this lesson's six articles miss exact 1.0 through the unguarded formula, and race-day-nutrition comes out at 1.0000000000000002, which arccos refuses outright. One line — max of -1 and the min of 1 and the value — removes the whole class of failure.
- class Day 67
- A template that says what every object made from it will carry and what it can do. The `class` statement runs once and produces one object — the class itself — holding a dictionary of class attributes and the function objects for its methods.
- class attribute Day 67
- A value assigned in the class body, stored once on the class and seen by every instance. Harmless for immutable values; a shared object for mutable ones, which is the classic bug this lesson reproduces.
- Class Imbalance Day 160
- A dataset characteristic where the distribution of examples across target classes is severely unequal (e.g. 99% majority vs 1% minority).
- ClassifierMixin Day 146
- A mixin supplying a default score() method (accuracy) to any class that also implements predict(). Optional -- a classifier can define its own score(), as this lesson's from-scratch version does.
- classmethod Day 67
- A function that receives the class itself as `cls`. Its overwhelmingly common use is the alternative constructor: it calls `cls(...)` and returns a new instance built from some other representation, such as a CSV row.
- Clean checkout Day 77
- A fresh copy of a repository at one exact commit, on a machine holding nothing else — no editor settings, no globally installed package, no uncommitted file, no environment variable from your shell profile. It is what makes "works on my machine" a testable claim rather than an argument, and it usually disproves it.
- cleaning contract Day 125
- A set of post-conditions -- no nulls in named key columns, dtypes matching what was declared, a row count inside an expected range -- asserted mechanically after a cleaning step, so the cleaning either provably holds or fails loudly instead of silently shipping a violated assumption downstream.
- Cleveland-McGill ordering Day 127
- The ranking of encoding channels by measured judgement accuracy: position on a common scale, then position on identical non-aligned scales, then length, then angle and slope, then area, then volume, then colour saturation. Used in this lesson as a decision procedure -- take the highest-ranked channel the task has not already spent and the data type can honestly carry.
- CLI (command-line interface) Day 56
- A program you run by typing its name and instructions in a terminal, which reads its input from command-line arguments rather than a graphical window or interactive prompts, so it can be scripted, scheduled, and tested.
- client Day 15
- The program that initiates a request and waits for a reply, such as your web browser.
- client Day 22
- The program that initiates an API call — it builds and sends the request and reads the response. Your curl command or your program is the client.
- client-side rendering Day 20
- Building a page's content in the browser with JavaScript after a nearly empty HTML file loads; cheap to host but slower to first paint and harder for crawlers to read.
- Clipping Day 105
- What happens to an output pixel whose inverse-mapped source lies outside the input image. The corners of a rotated square do not fit inside a square, so something must go there — a fill colour, a mirror of the edge, a wrap-around, or a larger output canvas that avoids the question. Clipping is a DECISION and not a failure, and it is worth distinguishing carefully from a hole: after a 30 degree rotation, inverse mapping leaves 12 fill-valued pixels and every one of them maps back outside the picture, which the lab proves rather than assumes.
- clock cycle Day 2
- One tick of the CPU's shared timing signal — the chip's indivisible unit of time, within which each pipeline stage must finish its step.
- clone Day 29
- A full local copy of a repository, including its complete history, made when you obtain a project from another copy.
- clone Day 32
- The command that creates a new local copy of a remote repository, including its full history, and sets up the origin remote and tracking branches automatically.
- clone() Day 146
- Builds a fresh, unfitted estimator instance from type(estimator)(**estimator.get_params(deep=False)). Measured to produce identical get_params() and zero learned attributes on the clone, while the original stays fitted -- the mechanism that gives every cross-validation fold a genuinely fresh model.
- Closed-form solution Day 151
- A solution obtained by a single direct calculation rather than an iterative search -- ridge's normal equations, adjusted by adding alpha to the diagonal before inverting. A fitted Ridge model carries no n_iter_ attribute, confirmed here directly, because there was nothing to iterate.
- closure Day 58
- A nested function together with the enclosing variables it has captured, such that it keeps seeing and using those variables even after the enclosing function has returned. Used for factories, stateful helpers like counters, callbacks, and decorators.
- Cluster identifier Day 142
- The integer a clustering algorithm writes on each group. It is determined by the algorithm's internal bookkeeping and carries no relationship to any external class code. Comparing identifiers to labels directly is what turns a partition worth 0.8933 into a reported 0.24.
- Cluster Stability Day 189
- The consistency of learned cluster assignments across bootstrapping samples or consecutive time windows.
- CMLC (Changing Anything Changes Everything) Day 175
- The fundamental machine learning technical debt anti-pattern where changing one feature alters the entire joint optimization landscape.
- CNAME Day 16
- A DNS record that aliases one name to another name, which the resolver must then look up in turn, rather than pointing directly to an address.
- Co-adaptation Day 208
- A pathological condition where neurons depend heavily on the specific presence of other neurons to correct their errors.
- COALESCE Day 86
- A function returning its first non-NULL argument; IFNULL is the two-argument form and NULLIF is the inverse, turning a sentinel value back into NULL. All three are legitimate for display. The hazard is arithmetic: AVG already ignores NULLs, so AVG(COALESCE(rating, 0)) does not handle the missing ratings — it invents ratings of zero and mixes them in, which in this lesson's data moves the answer from 4.16 to 3.47 without a word of warning.
- Code coverage Day 77
- A measurement of which parts of a program were executed during a test run, expressed as a percentage. Described as an idea by Miller and Maloney in 1963. It measures execution, never verification: code can be fully covered and completely unchecked.
- code editor Day 36
- A program for writing and editing source code that understands the text is programming code — coloring it, completing names, and flagging errors — and grows through add-ons called extensions.
- code point Day 5
- The unique number Unicode assigns to a character, written like U+0041 for the letter A.
- code review Day 33
- The practice of having one or more people read a proposed change before it is merged, to catch bugs, share knowledge, and improve design.
- Coefficient of variation Day 150
- A coefficient's bootstrap standard deviation divided by its bootstrap mean, used here to compare instability across predictors on a scale-free basis. Tracks variance inflation factor across the ten diabetes predictors, with one predictor's near-zero mean coefficient excluded as a known distortion.
- Coefficient path Day 151
- Every coefficient's value as alpha is swept from small to large. Lasso's path hits exactly zero for every one of ten features somewhere in a 60-point sweep; ridge's never hits zero at any point in the same sweep. The order lasso's coefficients zero in tracks how much each feature contributes -- the weakest first, the strongest last.
- Coefficient sign flip Day 150
- A predictor's simple-regression coefficient and its multiple-regression coefficient pointing opposite directions. Measured on real data here: a serum measurement is +0.4723 alone and -1.09 once a correlated partner is held constant -- the same mechanism as Simpson's paradox.
- Coercion Day 94
- Converting a value to the declared type rather than refusing it — accepting the string "42" where an int was asked for. Convenient at a boundary where everything arrives as text, and dangerous when the conversion could be wrong in a way nobody notices. Every coercion rule is a judgement call about which mistakes are more likely than which inconveniences.
- Cohen Kappa Day 191
- A statistical coefficient measuring inter-rater agreement for categorical items, normalized against agreement expected by chance.
- cohesion Day 63
- A measure of how well the parts inside one function or module belong together and serve a single purpose. High cohesion is good: everything inside summarize() is about computing the summary and nothing else.
- col= / row= (faceting) Day 129
- Arguments to seaborn's figure-level functions that split the data into one small multiple (facet) per category of the named column, arranging one Axes per category into a grid. col_wrap= reshapes how many facets appear per row without changing how many facets exist in total.
- Cold Start Problem Day 188
- The challenge of recommending items to new users or recommending new items with no prior interaction history.
- Collaborative Filtering Day 188
- A recommendation method based on historical interactions and behavioral similarities between users and items without requiring domain attributes.
- collate_fn Day 205
- A callable argument in DataLoader that takes a list of sample objects and merges them into a batched tensor.
- Collation Day 86
- The rule deciding how text values compare and sort — whether case matters, how accents are handled, what order the characters take. SQLite's default BINARY collation compares byte by byte, and its NOCASE collation folds only the 26 ASCII letters. This is why LIKE's case-insensitivity does not extend to accented or non-Latin text, and why the same query can sort differently on MySQL, where case sensitivity is a property of the column's collation rather than of the operator.
- collection Day 23
- A resource that contains many others, addressed by a plural path such as /users; you create a new member by POSTing to it.
- Collection Day 71
- The phase in which pytest works out what to run, before running anything: it fixes the rootdir, imports every `conftest.py` in scope, imports each file matching `test_*.py` or `*_test.py`, and gathers `test_*` functions and `Test*` classes into items with ids. `--collect-only` shows the result without executing a thing.
- collections Day 60
- A standard-library module of specialised container types, most notably Counter (tally an iterable), defaultdict (group without checking whether a key exists), and namedtuple (a small record type with named fields).
- collision Day 53
- When two different keys reduce to the same bucket in the hash table. Python keeps such pairs together and compares them one by one; collisions are normally rare and cheap, but a pathological hash that clusters keys degrades lookup toward O(n).
- Colour ramp Day 112
- A rule mapping a rescaled value to a colour, usually defined by a small number of named "stops" with linear interpolation between them. This lesson's ramp runs from dark blue (lowest value) through blue and gold to dark red (highest), implemented with numpy.interp on each colour channel independently.
- Column Day 100
- One vertical line of a matrix, selected by the second index. Under the table reading a column is one feature measured across every item; under the vector reading it is a vector of a different length from any row. Reading a column means stepping across the whole array rather than along it. Rows and columns are different kinds of thing living in the same rectangle, and that asymmetry is the source of nearly every axis mistake.
- columnar storage Day 121
- A file layout that stores all values of one column contiguously, rather than row by row. Parquet is columnar; CSV is row-oriented plain text. Columnar storage is what lets a typed format record one dtype per column instead of re-guessing it on every read.
- ColumnTransformer Day 173
- A composite transformer that applies distinct preprocessing pipelines to specified column subsets in parallel and concatenates the results.
- Combinatorial Expansion Day 171
- The rapid, exponential growth in feature space dimensionality when generating high-degree polynomial combinations.
- command Day 8
- A single line of text you give the shell, beginning with the name of a program to run and followed by any options and arguments.
- command dispatch Day 56
- Choosing which function handles the chosen subcommand: each subparser stores its handler (set_defaults(func=...)), so the program simply calls args.func(args) instead of a long if/elif ladder — a small dispatch table built into the parser.
- command history Day 8
- The shell's record of the commands you have run, recalled with the Up arrow or listed with the `history` command, so past commands can be re-run without retyping.
- command line Day 42
- The shell and terminal you use to drive the machine directly, composing small tools with pipes; the hinge between you and every other tool in the section (days 8-14).
- command substitution Day 12
- The `$(command)` form, which runs a command and replaces itself with that command's captured output, letting a script use real results as values.
- Command-line interface Day 80
- A user interface made of text: the program receives a list of strings when it starts, and returns text plus a number when it finishes. It is a screen with no pixels, and it deserves the same care as one — clear labels, sensible defaults, validation at entry, and a confirmation before anything irreversible.
- comment vs docstring Day 61
- A comment (a line starting with #) is a note to whoever reads the source, ideally explaining WHY a piece of code exists or a non-obvious decision; a docstring is structured documentation of an object's purpose and interface, readable at runtime. Rule of thumb: docstrings say what and why for the caller; comments explain why for the maintainer; neither should merely restate what the code plainly does.
- commit Day 29
- One saved snapshot of a project, stamped with its author, a timestamp, a descriptive message, a unique identifier, and a pointer to its parent commit.
- commit Day 30
- A permanent, recorded snapshot of the tracked files at one instant, wrapped with an author, timestamp, message, and the parent commit's hash, and identified by its own hash.
- Commit Day 93
- Ending the transaction, making everything flushed inside it visible to every other connection. commit() flushes first, so the two are often confused; they are different verbs and the difference is exactly one afternoon of debugging, exactly once. By default a commit also expires every loaded attribute, so the next read is fresh — which is the direct cause of the most common DetachedInstanceError.
- Common table expression Day 91
- A named subquery written before the query that uses it, with WITH. It buys readability and the ability to refer to the same intermediate result more than once. It is also the only way to filter on a window function, since a window function cannot appear in a WHERE clause.
- Commutative Day 101
- An operation where the order of the operands does not change the answer. Addition of numbers is commutative; matrix multiplication is NOT. A @ B and B @ A are usually different matrices and frequently not even the same shape, and often only one of them is legal. This is not a technicality to be apologised for: it is the honest consequence of composition, in the same way that putting on socks and then shoes differs from shoes and then socks.
- Comparison count Day 140
- How many analyses were examined before the one being reported was chosen. It belongs in the same paragraph as the estimate, not in a footnote, because a p-value is only interpretable alongside it.
- comparison operator Day 50
- An operator that compares two values and returns a boolean: `==` (equal), `!=` (not equal), `<`, `<=`, `>`, `>=`. Note that `==` compares values while `=` assigns a value to a name.
- Competitive Baseline Day 181
- A tuned standard algorithm (e.g. LightGBM, Random Forest) establishing the state of the art on tabular features.
- Complement rule Day 113
- P(not A) = 1 - P(A). Applied to "at least one success in n trials," it collapses a hard-to-count question into an easy one: 1 minus the probability that every single trial fails. This is the one-line resolution of the Chevalier de Méré's 1654 paradox about two seemingly equal dice bets.
- Component Day 99
- One number inside a vector, identified by its position. The first component of every article vector in this lab counts mentions of cooking; swapping two components produces a different vector that means something else entirely. Components are also called coordinates, and in a dataset they are the columns.
- Composite Hyperparameter Tuning Day 173
- Simultaneously optimizing feature engineering, scaling, selection, and model parameters in a unified search grid using double-underscore syntax.
- Composite index Day 89
- An index on more than one column, sorted by the first column, then by the second within one value of the first, and so on. The order of the columns is the whole of its behaviour, which is why choosing it deliberately matters more than adding another index.
- composition Day 68
- Building a class out of other objects held as attributes rather than inheriting from them. It expresses a "has-a" relationship. An Oven does not need to BE a Timer in order to hold one.
- Composition Day 101
- Doing one transformation and then another. The reason matrix multiplication has the rule it has. Because matrices compose like nested function calls, the rightmost matrix in A @ B @ v is the one that meets the vector first — English reads left to right and the arithmetic does not, which is the single most common conceptual error on this topic.
- Composition Day 102
- Doing one transformation and then another. The single matrix that does both is the product of the two, with the FIRST step written on the RIGHT: applying A then B is B @ A, because A is the one standing next to the vector in B @ (A @ v). Matrix multiplication was defined by Binet in 1812 precisely to be this operation, which is why it does not commute — putting on socks then shoes is not the same as shoes then socks.
- Composition Day 105
- Multiplying several transformation matrices together into one, applied right to left so that compose(B, A) means "do A first, then B" — the Day 101 convention, unchanged. Composition is only possible for translations because homogeneous coordinates gave them a matrix form. It is both cheaper (one pass over the pixels instead of several) and more accurate (one quantisation instead of several), which is a rare combination and worth always taking.
- Composition Day 110
- Feeding the output of one function into another, written f(g(x)) and read from the inside out: g runs first on x, and f runs on whatever g returned. Composition is not commutative — at x = 2, squaring 3x + 1 gives 49 while tripling x squared and adding one gives 13.
- Computation graph Day 110
- A directed graph whose nodes are values and whose edges are operations, built as an expression is evaluated. Each edge carries a local derivative. The gradient of the output with respect to any node is the sum, over every path from that node to the output, of the product of the local derivatives along that path.
- Computed field Day 94
- A property decorated with @computed_field, so that it appears in the model's serialized output and in its JSON Schema while never being an input. Useful for a value derived from other fields that consumers want and nobody should be able to set. It is the most common cause of a surprising round-trip failure.
- computing foundation Day 42
- The durable, portable body of knowledge about how software systems work — the machine, the network, and the workflow — that sits beneath any specific language or framework and changes only slowly.
- concat Day 124
- The pandas function that stacks DataFrames along an axis -- axis=0 adds rows, axis=1 adds columns -- without matching on any key. Aligns by column name (axis=0) or index label (axis=1), filling any position that does not line up across the inputs with NaN rather than raising an error.
- Concept Drift Day 195
- A change in the underlying physical or behavioral relationship P(Y|X) between input features and target outcomes.
- Conceptual, logical and physical schema Day 91
- Three artifacts with three audiences, separated by the ANSI/SPARC committee in 1975. The conceptual model is entities and relationships in the language of the business; the logical schema is tables, columns and keys, independent of any engine; the physical schema is the CREATE TABLE statements for one specific database with its types, constraint syntax and indexes. Bad designs usually contain a conceptual mistake, and a conceptual mistake is invisible in a wall of DDL.
- concurrency Day 7
- Structuring many tasks so they make progress over overlapping time periods — achievable on a single core through time slicing, with no true simultaneity required.
- Concurrency Day 96
- A property of a program structure: several pieces of work are in progress at the same time. It says nothing about how many are executing at any given instant. Cooking rice while the oven heats and you chop is concurrency with one cook. It is a way of organising work, not a performance technique — it sometimes yields performance and sometimes does not, and which it is depends entirely on whether the work waits or computes.
- cond(X'X) = cond(X) squared Day 153
- The textbook reason the normal equations lose more precision than a direct solve of X. Confirmed to ten decimal places on well-conditioned data (51631.1119 against 227.2248 squared); the verification itself degrades under extreme ill-conditioning, measured here at 0.9527 rather than 1.0 on the near-duplicate-column case.
- Condition number Day 111
- The ratio of a Hessian's largest eigenvalue to its smallest (Day 106). For a bowl f(x,y) = 0.5*(x^2 + kappa*y^2), the condition number is kappa exactly. It governs how hard gradient descent's job is: a well-conditioned (low-kappa) bowl is fast to descend at any reasonable fixed learning rate, an ill-conditioned (high-kappa) one forces a tiny learning rate and therefore many more steps.
- Condition number Day 112
- Informally, how stretched a bowl-shaped loss surface is along one axis relative to another. A well-conditioned bowl (equal stretch in every direction) lets gradient descent head almost straight for the minimum; an ill-conditioned one (very different stretch along different axes) forces the steepest-descent direction to point mostly across the narrow axis, producing the zig-zag this lesson measures directly.
- Condition number Day 153
- The ratio of a matrix's largest to smallest singular value, measuring how much a small change in the input can be amplified in the output of a linear solve. 227.2248 for the diabetes design matrix here; 2.4363e+07 for the near-duplicate-column dataset that makes the normal equations explode.
- Condition Number (kappa) Day 170
- The ratio of the largest to smallest eigenvalue of the Hessian matrix, dictating the convergence speed of gradient descent.
- conditional Day 12
- An `if`/`then`/`else` construct that runs commands based on whether a test succeeds, where the test is any command judged by its exit code.
- conditional expression (ternary) Day 50
- A one-line expression, `value_if_true if condition else value_if_false`, that produces a single value based on a condition. Unlike an `if` statement (which runs blocks), the ternary yields a value you can assign or pass to a function.
- Conditional independence Day 115
- Two pieces of evidence are conditionally independent given a hypothesis when knowing one occurred, given the hypothesis, tells you nothing about whether the other occurred. Sequential updating by multiplying likelihood ratios is only valid when this holds; two runs of the same assay on one sample, sharing a failure mode, are a realistic case where it does not.
- Conditional Independence Day 158
- A statistical property where two events or variables X and Y are independent given knowledge of a third variable Z: P(X, Y | Z) = P(X | Z) * P(Y | Z).
- Conditional probability Day 113
- P(A | B) = P(A and B) / P(B), read "the probability of A given B." Operationally, this is restricting the sample space to the rows where B is true and asking the original question again inside that smaller space — computing it by formula and by literally filtering the space must give the same exact answer.
- conditional request Day 134
- An HTTP GET carrying an If-None-Match header with a previously stored ETag value, letting the server answer 304 Not Modified with an empty body when nothing has changed, instead of re-sending the full resource. This is what makes a daily re-run of the same fetch cost close to nothing.
- Confidence interval Day 118
- A range built from data by a procedure whose long-run coverage rate is known -- a (1 - alpha) interval, repeated across many samples, contains the true parameter about (1 - alpha) of the time. This lesson measured 95.09% coverage across 10,000 real intervals from a population with a known true mean, which is the content of "95% confidence," not a probability statement about any single interval.
- Confident Learning Day 191
- A probabilistic framework estimating joint noise distributions to identify and prune mislabeled training instances.
- configuration (pipeline) Day 126
- Thresholds, column lists and mappings kept in a data structure the pipeline reads, separate from the step functions' code, so re-running with different parameters means editing the configuration, never the logic.
- Configuration precedence Day 80
- The order in which competing sources of a setting override one another: built-in defaults, then a config file, then environment variables, then command-line flags. It is the order of increasing specificity, and users expect it because the most specific statement of intent is always the one they just typed.
- Configuration precedence Day 84
- The written-down order in which layers of settings override each other: defaults in the code, then a configuration file, then the environment, then command-line flags. Every program has one; the difference between a good tool and a confusing one is whether anybody can say what it is without reading the source.
- Configuration precedence Day 97
- The order in which layers override one another: default, then config file, then environment, then command-line flag. The justification is specificity — a default is what everybody gets, a file is what this deployment gets, a variable is what this process gets, a flag is what this invocation gets, typed by a person looking at the problem right now.
- Confirmation set Day 140
- A portion of the data set aside before any exploration begins and left untouched until a specific hypothesis has been formed, then tested once. A confirmation set tested more than once is an exploration set with a better name.
- Confirmation set (holdout) Day 136
- A portion of the data set aside before any exploration begins and left untouched until a specific hypothesis has been formed. Testing that hypothesis once against the confirmation set is what separates a real finding from a shape in the noise.
- Confirmatory analysis Day 136
- Testing a specific, pre-declared hypothesis against data that was not used to generate that hypothesis. Confirmatory analysis is where a p-value can be taken at face value; exploratory analysis is where it usually cannot.
- conflict markers Day 31
- The <<<<<<<, =======, and >>>>>>> lines Git inserts around a conflicting region to show both competing versions; a conflict is resolved only once all three are removed.
- conftest.py Day 71
- A file pytest imports automatically, by name alone, from the rootdir down to the directory being collected. Nothing imports it and no configuration names it. Whatever it defines is available to every test file beneath it — which also makes it the quietest place in a repository to hide code that runs on every test invocation, so review its diffs carefully.
- conftest.py Day 72
- A file pytest finds by location rather than by import, whose fixtures become available to every test file in that directory and below. Nearer definitions shadow farther ones, and visibility flows downward only, so a fixture in a subdirectory is invisible above it. It is executable code that runs automatically before any test.
- Confusion matrix Day 143
- The four counts of true and false, positive and negative. On the 0.9435-accurate model here it reads 1810, 30, 83, 77 -- so the model misses more positives than it catches, which one aggregate number could never have told you.
- Confusion matrix Day 147
- A table of predicted class against true class. Here, [[40, 2], [0, 72]]: two malignant cases predicted benign, zero benign cases predicted malignant -- a fact that a single accuracy number does not reveal on its own.
- Confusion Matrix Day 159
- A 2x2 contingency table summarizing the counts of True Positives (TP), True Negatives (TN), False Positives (FP), and False Negatives (FN) produced by a classifier.
- Confusion Matrix Day 203
- A K x K contingency table recording actual versus predicted digit class frequencies to identify systematic classification errors.
- congestion control Day 17
- A TCP mechanism that slows sending when the network shows signs of overload (lost packets or delay) and cautiously speeds back up, sharing capacity fairly.
- Conic Section Day 156
- Geometric curves (ellipses, parabolas, hyperbolas) formed in 2D space by quadratic decision boundaries w1*x1 + w2*x2 + w3*x1^2 + w4*x1*x2 + w5*x2^2 + b = 0.
- Conjunction fallacy Day 113
- The mistaken judgement that a more specific, detailed conjunction of events is more probable than either event alone, when in fact P(A and B) can never exceed P(A) or P(B) — a subset can never be larger than the set that contains it. Adding vivid, plausible-sounding detail to a description can make it feel more probable even though it can only ever be equally or less probable.
- Connection Day 90
- One open database. It holds the file, the transaction state, the settings chosen when it was opened, and the write lock while you are writing. It is not a network connection — there is no server — but it is a resource with state, so it is closed when you are finished with it, and it belongs to the thread that created it.
- Connection pool Day 93
- A set of already-open database connections the engine hands out and takes back, so that a unit of work does not pay the cost of opening one. For a server-backed database that cost is a network round trip and an authentication handshake, which is why pooling matters far more against PostgreSQL than against a local SQLite file.
- connection refused Day 17
- The error returned when a host is reached but no program is listening on the requested port, so the connection cannot be completed.
- Connection reuse Day 78
- Sending several requests down one already-open TCP connection instead of opening a new one each time. Default behaviour in HTTP/1.1, and what a Session gives you: five requests through one Session opened one connection in this lab, where five bare calls opened five. Each connection avoided is one TCP round trip, plus one or two more for TLS.
- connection-oriented Day 17
- Describing a protocol like TCP that establishes a connection (via a handshake) before exchanging data, and maintains state for it; UDP, by contrast, is connectionless.
- Consistency (in CAP) Day 92
- Every read receives the most recent write, or an error. Note that this is a different word from the C in ACID, which is about a transaction leaving the database satisfying its declared constraints. Confusing the two is one of the commonest sources of muddle in this area.
- Console script Day 83
- An entry point in the `console_scripts` group, declared as `[project.scripts] name = "module.path:function"`. Installing the package writes a small executable of that name into the environment's `bin/` directory, whose whole job is to import the function, call it, and exit with what it returns. This is how `pip install` gives a user a COMMAND rather than merely a module.
- Constant-mean predictor Day 152
- The baseline predictor R-squared is defined relative to -- always guess the training mean. Measured here scoring R-squared of -0.0001 on fresh test data, essentially exactly zero by construction, which is the fact R-squared's zero point actually represents.
- Constraint Day 88
- A rule declared in the schema that the database enforces against every writer, forever — NOT NULL, UNIQUE, CHECK, DEFAULT, PRIMARY KEY, FOREIGN KEY. Unlike a comment or a wiki page it cannot drift out of date, because it is the thing being enforced; and unlike application validation it applies to the one-off script nobody reviewed.
- Constraint region Day 151
- The equivalent way to view a penalty: minimizing the plain loss subject to a hard budget on the coefficients. Ridge's region is a circle (or sphere); lasso's is a diamond (or octahedron), and the diamond's corners, sitting on the coordinate axes, are what makes exact zeros possible.
- consumer Day 26
- In event-driven architecture, a service that receives and handles events emitted by producers (for example, your webhook receiver).
- container Day 6
- A kernel-enforced isolated compartment of user space — separate process list, filesystem view, and network stack — that shares the host's kernel, packaged with an application's exact environment so it runs identically anywhere.
- Contamination Day 116
- A small fraction of extreme or corrupted values mixed into an otherwise ordinary sample. This lesson's lab measures how differently the standard deviation and the median absolute deviation respond to the same 3% contamination -- a roughly 15x inflation for the standard deviation against essentially no change for the MAD.
- Contamination Day 187
- The expected proportion of outliers in the dataset, used to calibrate decision score thresholds.
- content hash Day 126
- A cryptographic digest (here, SHA-256 via hashlib) computed from a frame's or a config's exact serialised bytes. Two runs on identical input produce an identical hash; changing even one byte of the input changes the hash. The specific hex digest can depend on serialisation details (float formatting, key order) and is not promised to match across different library versions -- the STABILITY and SENSITIVITY properties are what a pipeline actually relies on.
- Content hash Day 143
- A cryptographic digest of an object's exact bytes -- here including the array's dtype, so that the same numbers stored as int64 and float64 hash differently, on purpose. Silently equal hashes are worse than no hashes.
- Content-Type Day 18
- A header declaring the format of the body, such as application/json or text/html, so the receiver parses the bytes correctly.
- context manager Day 47
- An object used with the with statement that sets up a resource on entry and reliably releases it on exit — closing a file automatically, for example, even if an error is raised inside the block.
- context manager Day 64
- An object that is entered at the top of a `with` block and exited at the bottom no matter how the block ends — clean finish, `return`, or an exception thrown three functions deep. For a file, exiting means flushed and closed, which makes closing structural rather than remembered.
- context manager Day 68
- An object implementing `__enter__` and `__exit__`, usable with the `with` statement. `__exit__` runs on the way out of the block whether it succeeded or raised, receiving the exception type, value, and traceback; returning a truthy value from it suppresses the exception.
- Context manager (for a connection) Day 90
- Two different things that are easy to confuse. "with connection:" commits at the end of the block or rolls back if it raised, and leaves the connection OPEN. contextlib.closing(connection) closes it. The honest full form nests them, because a connection's lifetime and a transaction's lifetime are different questions.
- context switch Day 7
- The act of saving one thread's complete CPU state and loading another's so a core can change what it is running — pure overhead that pays for the illusion of simultaneity.
- contextlib.suppress Day 66
- A context manager that discards the exception types you name. Functionally the same as "except X: pass" for a named X, but it makes the deliberateness syntactically obvious and cannot drift into a bare except. Never pass Exception to it.
- Contextual bandit Day 142
- A reinforcement setting with state and immediate feedback but no long-horizon credit assignment. Much more tractable than full sequential reinforcement learning, and where most industrial decision-making problems actually live.
- contiguous Day 104
- Laid out in one unbroken run of memory, so that consecutive elements sit at consecutive addresses. C-contiguous means the last axis varies fastest — rows laid end to end; F-contiguous means the first does. A transpose of a C-contiguous array is F-contiguous over the same bytes. Contiguity is what lets the processor fetch the next values while it is still working on the current one, and it is inseparable from the fixed dtype: without a fixed width there is no way to pack without gaps.
- Contiguous Memory Day 202
- A memory buffer where tensor elements along consecutive dimensions are stored sequentially without strides gaps.
- continue Day 51
- A statement that abandons the rest of the current loop pass and jumps straight to the next item, leaving the loop running; used to skip items that do not qualify.
- Continuous integration Day 77
- The practice of running the gate automatically on a clean machine on every push, so that integration problems surface within minutes rather than at the end of a project. Named by Grady Booch in 1991 and made a daily practice by Kent Beck's Extreme Programming in 1999. Continuous integration is where a gate runs; it is not the gate itself.
- continuous integration (CI) Day 37
- An automated system that runs checks — such as formatting and linting — on a shared server every time code is pushed, refusing changes that fail, so standards are enforced on every commit.
- Contour line Day 109
- A curve joining points at which a function of two variables takes one fixed value — the line on a walking map that joins points of equal height. Where contours are close together the function is changing fast; where they are far apart it is nearly level. The gradient is perpendicular to the contour through every point, which is why an optimiser's path is drawn crossing the contours at right angles. Every optimisation picture in the rest of this course is a contour map.
- Contour plot Day 112
- A picture of a function of two variables built from level curves or level bands — regions of roughly equal value. Every contour plot in this lesson starts from the same triple of arrays, (X, Y, Z), produced by evaluating a function over a grid.
- contract (on a DataFrame) Day 135
- A set of checks -- required columns present, key column unique, columns holding the expected dtype, row count within an expected range -- run against an assembled frame before anything downstream trusts it, raising an exception that names the specific rule broken rather than a generic error.
- Contract test Day 74
- One set of assertions run against both a real dependency and the double that stands in for it, so the double cannot silently drift away from the thing it doubles. It is the honest fix for mocking what you do not own, and the real half is normally run deliberately rather than on every commit.
- Contraction factor Day 111
- For a 1-D quadratic f(x) = 0.5*a*x^2, the number (1 - eta*a) that gradient descent multiplies x by on every step. Its absolute value predicts the whole outcome: below 1 the run shrinks toward the minimum, exactly 0 lands on it in one step, between 1 and 2 (in a*eta terms) it alternates sign while still shrinking, and above that it grows without bound.
- Control Day 143
- Data with a known answer, put through the pipeline to check the pipeline. Today's noise dataset is one: a pipeline reporting better than chance on it is known to be broken without any argument about the real data. Standard in a laboratory, rare in machine learning, four lines to add.
- control unit Day 2
- The part of the CPU that runs the instruction cycle: it fetches each instruction, decodes its bit pattern, and steers the ALU, registers, and bus to carry it out.
- Conventional Commits Day 35
- A specification for structured commit messages of the form type(scope): description, using a small vocabulary such as feat, fix, docs, and refactor, so humans and tools can read the history.
- Convergence rate Day 112
- The constant ratio r (or its logarithm) that governs how fast a linearly convergent method's error shrinks per step. On a log-scale loss curve it is literally the slope of the line, not a separately computed quantity.
- Convex loss Day 149
- A loss whose landscape has no separate local minima to get trapped in -- squared error, absolute error and Huber are all convex in the model's coefficients, which is part of why the normal equations and iterative solvers alike reliably find the global minimum.
- cookie Day 18
- A small piece of data the server sends with Set-Cookie and the client returns in a Cookie header on later requests, used to fake a continuous session on top of stateless HTTP.
- Cooperative versus preemptive scheduling Day 96
- Preemptive means the scheduler can interrupt you anywhere, which is what threads get from the operating system and why every shared mutation in threaded code needs a story. Cooperative means you are interrupted only where you say, which is what coroutines get at await. Cooperative scheduling does not remove interleaving; it makes every interleaving point visible in the source, which is a large reduction in what you must hold in your head — and the reason one task that never yields stops everything.
- Coordinate descent Day 151
- The iterative algorithm scikit-learn's Lasso and ElasticNet use to find a solution, needed because the L1 penalty is not differentiable at zero and has no closed form. Measured iteration counts on the diabetes split: 368 at alpha=0.001, falling to 6 at alpha=1.0.
- Copy Day 100
- An array with its own memory, independent of whatever it was made from. Produced by .copy(), by .flatten(), and by fancy indexing. A copy costs the memory and shares nothing; a view costs nothing and shares everything; neither is the right answer, and knowing which one you have is. The reliable test is numpy.shares_memory(a, b), not .base is None — after M.copy().reshape(12), .base points at the anonymous copy and is not None even though the result is fully independent of M.
- Copy Day 104
- An array with its own data, so that changing one leaves the other alone. Boolean masking, fancy indexing, .copy(), .flatten() and any arithmetic produce copies. The useful pattern: if the elements requested are evenly spaced, a stride can describe them and NumPy returns a view; if they are not, it has no choice but to copy. Which means the cheap operations are the dangerous ones and the expensive ones are safe — the opposite of most people's intuition. Note that ravel returns a view where flatten always copies.
- Copy-on-Write (CoW) Day 120
- pandas' memory-management strategy, unconditional as of pandas 3.0, in which a Series or DataFrame derived from another shares the same underlying memory until either object is written to, at which point the write triggers an actual copy so the other object is unaffected. It is what makes chained assignment fail to reach the original object.
- Core Point Day 184
- A point with at least MinPts neighbors within distance epsilon, acting as an interior generator of a density cluster.
- Corner solution Day 151
- A solution that lands exactly on a corner of the L1 constraint region, meaning one or more coefficients are exactly zero. Measured directly on a two-feature demonstration: lasso's second coefficient equals exactly 0.0 at alpha=3.0, while ridge's is 1.9141 at the same alpha.
- Coroutine Day 96
- A function that can suspend itself and be resumed later, keeping its local state across the suspension. Written with async def in Python. Calling one does not run it — it builds a coroutine object, which is why "coroutine was never awaited" is such a common first error. The mechanism underneath is the same one generators have had since Python 2.2: a function that runs to a pause point, hands control back, and remembers where it stopped.
- Correlated subquery Day 91
- A subquery that refers to a column of the query containing it, and is therefore conceptually re-evaluated for each outer row. EXISTS and NOT EXISTS are the common form. It expresses a question about the existence of a row without bringing back any columns, so it cannot multiply the outer rows the way a join can.
- Correlation is not causation Day 116
- A correlation between X and Y is consistent with X causing Y, Y causing X, a third factor causing both, or coincidence in a finite sample; the correlation coefficient alone carries no information distinguishing between these. The useful move is actively generating the plausible alternative explanations, not merely reciting the slogan.
- Correlation-causation distinction Day 148
- The principle, established on Day 119, that a regression coefficient describes association in the data it was fitted on and says nothing on its own about whether changing the predictor would change the target. A slope is not a lever.
- CORS Day 82
- Cross-Origin Resource Sharing — a browser mechanism deciding whether a page loaded from one origin may read a response from another. It protects the user's browser session and does nothing whatsoever against a script or a command-line client. Setting `allow_origins=["*"]` to silence a frontend error is a decision about which web pages may read your data, not a security measure.
- Cosine Annealing Day 207
- A learning rate policy that decays the step size following a half-period cosine curve from a maximum to a minimum value.
- Cosine distance Day 103
- 1 minus the cosine similarity, so 0 for the same direction, 1 for perpendicular and 2 for opposite. Called a distance because it grows as things get less alike, and it is not a metric: it fails the triangle inequality, and it gives 0 for pairs that are not equal. On count vectors, where nothing is negative, no pair can be more than 90 degrees apart, so the value never exceeds 1 and orthogonal is as far apart as two documents get.
- Cosine distance Day 107
- One minus cosine similarity. Widely used, genuinely useful, and not a metric: it fails the triangle inequality and it is zero between vectors that are not equal. Precise usage calls it a dissimilarity. Two standard repairs exist when a metric is required: angular distance, the arc cosine of the similarity divided by pi, which is a metric and preserves the same ranking; or normalising every vector to unit length on the way in, after which the squared Euclidean distance equals 2 minus twice the cosine similarity and the two rank identically. The second is what vector databases actually do.
- Cosine Distance Day 157
- A directional similarity metric defined as 1 - (x . z) / (||x|| * ||z||), measuring the angular difference between vectors independent of length.
- Cosine similarity Day 103
- The cosine of the angle between two vectors: the dot product divided by both lengths, or equivalently the plain dot product of the two unit vectors. It runs from 1 for the same direction, through 0 for perpendicular, to -1 for opposite. Dividing by both lengths is what makes it magnitude-free by construction rather than by convention — scale either vector by any positive number and the top and the bottom are multiplied by the same factor, which cancels. That is why an article and its doubled copy score exactly 1.0 rather than approximately 1.0.
- Cosine similarity Day 107
- The dot product of two vectors divided by both their lengths: 1 for the same direction, 0 for perpendicular. Day 103 derived it. Length is divided out, which is the entire point and the entire limitation — a document three times as long with the same term mix scores exactly 1.0, and so does the same document repeated twice. It is a similarity rather than a distance, so it must be sorted descending; sorting it ascending builds a search engine that returns the worst match first with no error message anywhere.
- Cosine Similarity Day 188
- A metric measuring the cosine of the angle between two multi-dimensional vectors, evaluating directional similarity independent of magnitude.
- Cost Matrix Day 176
- A matrix assigning specific economic monetary costs and payoffs to each of the four confusion matrix outcomes (TP, FP, TN, FN).
- Cost-Complexity Pruning Day 162
- A post-pruning technique that minimizes a cost function balancing tree misclassification error against tree size parameterized by alpha.
- Cost-Sensitive Learning Day 160
- A machine learning approach that incorporates asymmetric misclassification costs directly into the loss function during training.
- count() (GroupBy) Day 123
- Counts, per column, the number of non-missing values in each group. A per-column method, unlike size(), which is scalar-per-group and does not vary by column.
- counter Day 40
- A metric that only ever increases (resetting to zero on restart), such as the total number of requests served; its rate of change per second is usually what you chart.
- Counter Day 60
- A collections type that tallies how many times each value appears in any iterable in a single call; Counter.most_common(n) returns the counts largest-first, answering "which category is biggest?" in one line.
- coupling Day 63
- A measure of how much one function or module depends on another. Low coupling is good: functions that interact only through small, clear interfaces (values in, values out) can be changed and tested independently.
- Course 04 Capstone Day 196
- The culminating project demonstrating mastery of classical machine learning algorithms, unsupervised representations, and MLOps.
- Covariance Day 114
- Cov(X, Y) = E[(X - E[X])(Y - E[Y])], a measure of how two random variables move together. It is exactly the correction term that makes Var[X+Y] = Var[X] + Var[Y] + 2*Cov(X,Y) an equality rather than an approximation, and it is zero whenever X and Y are independent (though a zero covariance does not by itself prove independence).
- Covariance matrix Day 106
- For data with d features, the d by d matrix whose (i, j) entry is how much feature i and feature j vary TOGETHER around their own means. Computed as the centred data transposed times itself, divided by n minus 1. Two things about it decide everything downstream. It is always symmetric, because entry (i, j) and entry (j, i) are the same sum of products written in the other order — which is what guarantees real eigenvalues and perpendicular eigenvectors. And the CENTRING is not optional: skip it and you measure how far the cloud sits from the origin rather than how it is shaped, which in this lesson produced an answer 136.583965 degrees wrong with no error and no warning. Note that its size depends on the number of FEATURES, not the number of points: a 400 by 2 dataset has a 2 by 2 covariance matrix.
- Covariance matrix Day 107
- A square matrix whose (i, j) entry is the average product of column i and column j deviations from their own means. The diagonal holds each column variance; the off-diagonal says how strongly two columns move together. On the eight sensor readings used in this lab it comes out as exactly [[7.5, 7.0], [7.0, 7.5]], with a correlation of 0.9333. Day 106 eigenvectors of this matrix are the directions the data spreads along, and Mahalanobis distance is Euclidean distance measured along those directions with each component divided by the square root of its eigenvalue.
- Covariance Matrix Day 185
- A square symmetric matrix containing pairwise covariances between all feature dimensions: Sigma = (1/(N-1)) X^T X.
- Cover’s Theorem (1965) Day 175
- A theorem stating that non-linear projection of a pattern-classification problem into a higher-dimensional space increases the likelihood of linear separability.
- coverage Day 134
- Whether a dataset actually contains everything it claims to. A source titled "national" that is missing one region entirely looks visually identical to one where that region legitimately has a zero value, unless the actual set of keys present is compared against the set the documentation promises.
- Coverage Day 118
- The measured fraction of confidence intervals, built the same way across repeated sampling, that actually contain the true parameter value. The only way to verify a confidence procedure's stated level is genuinely accurate, rather than assumed.
- coverage bias Day 138
- The specific form of selection bias in which some part of the target population is systematically absent or under-represented. Measurable whenever a reference distribution exists, by dividing each group's sample share by its reference share to get a representation ratio.
- Coverage ratchet Day 77
- A coverage floor that only ever moves upward: set it to the project's current figure, raise it deliberately when the real number rises, and never lower it silently. It cannot make a messy codebase clean, but it makes decline impossible, which is the only thing a coverage number is reliably good at.
- Covering index Day 89
- An ordinary index that happens to contain every column a particular query mentions, so the rowid pointer is never followed and the table is never opened. SQLite prints COVERING INDEX in the plan. It is the fastest case, and it is the reason it can be worth adding a column to an index that you never filter on but always select.
- CPU Day 1
- The central processing unit, the chip that executes program instructions one after another by repeating the fetch-decode-execute cycle.
- CPU-bound Day 2
- Describes a workload whose speed is limited by the CPU's instruction stream rather than by memory, disk, network, or an accelerator — as when a starving GPU idles because sequential preprocessing cannot keep up.
- Crawl delay Day 79
- A widely-supported robots.txt directive asking clients to wait a given number of seconds between consecutive requests. It is an extension rather than part of RFC 9309 proper. Python exposes it as RobotFileParser.crawl_delay, which accepts only whole numbers and returns None when nothing is declared — in which case you choose a conservative default yourself.
- Crawler Day 79
- A program that discovers and follows links across a site or the wider web. Crawling finds pages; scraping pulls fields out of them. Most real jobs are a small crawl feeding a focused scrape, and each has its own failure mode: a bad crawler goes where it should not, a bad scraper produces wrong data quietly.
- Credit assignment Day 142
- The problem of deciding which of many earlier decisions earned a later reward. In this lesson it is made countable: with a reward only at the goal, the value signal reaches exactly one new gridworld state per episode for the first ten episodes.
- CRISP-DM Day 143
- The Cross-Industry Standard Process for Data Mining, published in 1999: six phases drawn as a circle because the process was always understood as a loop. Its lasting contribution is insisting the business problem is understood before the data, and the data before the model.
- critical rendering path Day 20
- The sequence of steps from receiving HTML and CSS to painting the first pixels; its length largely determines how fast a page feels.
- cron Day 14
- The classic Unix scheduler: a background program that wakes every minute, checks a table of jobs against the current time, and runs the ones that match.
- cron Day 41
- A background service that runs commands on a repeating schedule, defined by a crontab line with five time fields: minute, hour, day of month, month, and day of week.
- cron Day 81
- The POSIX-standard Unix scheduling service, named from the Greek chronos (time). It reads a table of five-field schedules and runs commands. The implementation most Linux systems descend from is Paul Vixie's, first released in 1987. Ubiquitous and reliable, with no catch-up, no dependency handling, no built-in logging and no overlap protection.
- cron expression Day 14
- The five whitespace-separated time fields at the start of a crontab line — minute, hour, day-of-month, month, day-of-week — that say when a job runs.
- Cron expression Day 81
- Five whitespace-separated fields — minute, hour, day-of-month, month, day-of-week — each of which may be *, a number, a comma-separated list, an a-b range, or a step written */n. Day-of-week runs 0 to 6 with Sunday as 0, and 7 also means Sunday. When both day fields are restricted, cron ORs them rather than ANDing them.
- crontab Day 14
- The cron table — a per-user list of scheduled jobs, one job per line; edited with crontab -e and viewed with crontab -l.
- Cross product Day 72
- The set of all combinations of two or more lists of values, produced by stacking @pytest.mark.parametrize decorators — three topics and three durations give nine test items. Worth reaching for when the *combination* is what might break, and worth avoiding when it multiplies into a hundred items that all say the same thing.
- Cross-Validation Day 167
- A statistical resampling procedure used to evaluate machine learning models on a limited data sample by partitioning data into complementary subsets.
- CRUD Day 23
- The four basic operations on stored data — Create, Read, Update, Delete — which REST maps onto the HTTP verbs POST, GET, PUT/PATCH, and DELETE.
- CSS Day 20
- Cascading Style Sheets, the language that describes a page's presentation — colors, sizes, spacing, and layout — kept separate from its structure.
- CSS selector Day 79
- The pattern language used to address elements in a stylesheet, and in BeautifulSoup's select and select_one. Selectors such as table.catalogue tr.item match on structure rather than on literal text, which is why a cell with class="name featured" is still found by td.name while the obvious regular expression misses it entirely.
- CSSOM Day 20
- The CSS Object Model, the tree the browser builds by parsing all the page's CSS, recording the computed style that applies to each element.
- CSV Day 24
- Comma-separated values, a flat text format for tables of uniform rows; simple and spreadsheet-friendly but unable to express nesting.
- CSV Day 65
- Comma-separated values: one record per line, fields separated by a delimiter, usually with a header row naming the columns. Universal and compact, but untyped, flat, and never formally standardised before the fact.
- Cumulative distribution function (cdf) Day 114
- F(k) = P(X <= k), for either a discrete or continuous random variable. It is monotone non-decreasing, approaches 1 as its argument grows, and a difference of two cdf values gives an interval probability directly — F(7) - F(6) recovers P(Y=7) exactly, with no re-summing of the pmf.
- curl Day 21
- A command-line program that makes a single HTTP request you describe and prints the response, giving you precise control over and full visibility into one exchange.
- curl Day 28
- A small, ubiquitous command-line program that makes an HTTP request to a URL and prints the response — the standard way to send an API call from a terminal.
- Curse of dimensionality Day 103
- The collection of surprises that appear as the number of dimensions grows and that have no analogue in two or three. Two of them are measured in this lesson. Random directions become nearly orthogonal — mean absolute cosine fell from 0.6435 at dimension 2 to 0.0089 at dimension 8192 in the captured run — and distances concentrate, with the furthest of 500 random points going from 63.7 times as far as the nearest at dimension 2 to 1.05 times at dimension 8192. The practical consequence is that a similarity score means nothing until you know the dimension it came from.
- Curse of Dimensionality Day 157
- The phenomenon where exponential growth of volume in high-dimensional spaces causes data sparsity and distance concentration, diminishing the utility of distance metrics.
- Curse of Dimensionality Day 172
- The exponential increase in volume and sparsity of feature space as dimensions grow, requiring exponentially more data to generalize.
- cursor Day 27
- An opaque marker naming the last row a client saw, used in cursor-based pagination to fetch the next batch stably even when rows are inserted or deleted.
- cursor Day 64
- The single remembered position within an open file, also called the file position. Reading and writing move it forward; nothing rewinds it on its own. `tell()` reports it and `seek()` moves it — which is why a second `read()` returns an empty string until you `seek(0)`.
- Cursor Day 90
- One running statement plus a position in its results. connection.execute returns one, which is why the result of execute can be iterated directly. connection.cursor() makes your own when two statements must be in flight at once; several cursors share one connection and therefore one transaction.
- Cursor execution versus parameter set Day 93
- Two different numbers that a careless benchmark conflates. A cursor execution is one statement handed to the driver — the round-trip count, and what people mean by "number of queries". A parameter set is one row it carried: a single executemany is ONE execution carrying five hundred rows. Counting only executions makes a batched insert look free; counting only rows makes it look expensive. The lab records both.
- Curvature Day 108
- Which way a graph bends, read off the sign of the second derivative. Positive is a bowl and negative is a dome, so at a stationary point a positive second derivative means a minimum and a negative one means a maximum. When the second derivative is also zero it decides nothing: x³ at 0 is a flat step and x⁴ at 0 is a genuine minimum, and both read as zero slope and zero curvature.
- Curvature signal Day 154
- The correlation between the squared fitted value and the signed residual, used here as a numeric stand-in for a missed non-linear trend a residual-vs-fitted plot would show as a curve. Measured at -0.1278 -- weak, no strong evidence of a missed curve.
- custom exception Day 66
- An exception class you define yourself, in its minimal form a two-line class inheriting from Exception. It earns its place when callers need to catch your failure by name rather than guessing at the four built-in types your implementation happens to raise.
- Customer Lifetime Value (CLV) Day 189
- The total net revenue a business anticipates generating from a customer over the entire duration of their relationship.
- Customer Segmentation Day 189
- The practice of dividing a customer base into distinct groups of individuals that share similar behavioral, demographic, or economic characteristics.
- cyclical encoding Day 137
- Replacing a wrapping quantity with a sine and cosine pair, so that adjacency survives the wrap. Hour 23 and hour 0 sit 23.0 apart as integers and exactly 2*sin(pi/24) = 0.26105238444010315 apart on the circle -- the same distance as every other adjacent pair, with a spread below 1e-12 across all twenty-four. Opposite hours stay 2.0 apart, the diameter. It is the rare feature decision that can be proved rather than measured.
- Cyclical Encoding Day 171
- Mapping periodic temporal variables (hours, days, months) to 2D continuous coordinates using sine and cosine trigonometric functions.
- Cyclomatic complexity Day 76
- A count of the independent paths through a function — roughly, one plus the number of branch points. Ruff exposes it as `C901`, which fails a function above a configured ceiling. It is a genuine signal that a function is doing too much, and it is also the rule most likely to fire on the one function that legitimately has to be complicated, which makes it a good example of a rule needing judgement rather than obedience.
- Damage report Day 140
- A record of what cleaning changed, measured: for each step, the quantity it affected, its value before and its value after. Distinct from a changelog, which records what was done. Only the measurement lets a reader ask whether the rows that were removed were special.
- dashboard Day 40
- A screen of charts built from metrics that shows a system's vital signs at a glance, such as request rate, error rate, and latency percentiles, for a human who is actively watching.
- data dictionary Day 134
- A document, separate from the data itself, that defines every column in prose: what it measures, its unit, and how edge cases are handled. Two columns can share a name, a dtype and an overlapping range while meaning entirely different things, and the dictionary is the only place that difference is visible -- reading it before joining on a shared column name is this lesson's central habit.
- Data Drift (Covariate Shift) Day 195
- A change in the statistical distribution of input features P(X) while the conditional target mapping P(Y|X) remains stationary.
- data fingerprint Day 133
- A short cryptographic hash of the input data, recorded in the report's provenance section in place of a timestamp. It answers "which data produced this document?", lets two people confirm they hold the same input without either sending it, and is the reason two runs of the generator produce byte-identical output.
- Data Flywheel Day 190
- A self-reinforcing product loop where user interactions generate fresh telemetry, improving future model training and user retention.
- data interchange format Day 65
- An agreement about bytes between two programs that will never meet. One writes and one reads, and the format is the only thing they share — which is why structure cannot survive a trip through a file without one.
- data leakage Day 125
- Information from data that should be unavailable at training time (most commonly, the test or validation set) influencing the model during training, producing evaluation scores that look better than the model actually deserves. Imputing with a statistic computed over the WHOLE dataset before splitting it into train and test is a direct, common cause.
- Data Leakage Day 161
- The spurious introduction of information from outside the training dataset into the model building pipeline, producing unrealistically optimistic evaluations.
- Data Leakage Day 167
- The inadvertent introduction of information about the target or validation set into the model training pipeline, creating deceptively high validation scores.
- Data Leakage Day 180
- The spurious inclusion of information about the target variable that would not be available at actual inference time.
- Data leakage through the split Day 144
- Information about the test rows reaching training through the split itself rather than through a feature: a shared person, a shared moment in time, a fitted transform applied before the cut. All three are silent and all three inflate.
- data model Day 68
- Python's complete system of special method names — the set of hooks that connects syntax to behaviour, so that `len(x)` becomes `type(x).__len__(x)` and `x[k]` becomes `type(x).__getitem__(x, k)`. Implementing them is how a class you wrote joins the language rather than sitting beside it.
- Data Saturation Day 177
- The point on a learning curve where collecting additional training samples yields negligible improvement in validation performance.
- Data-access layer Day 90
- The module in which SQL is allowed to exist, and outside which it is not. Here it is a connection factory, a transaction context manager, one row-to-object mapping function per entity, and one repository class per aggregate. The rule is worth checking mechanically rather than promising: this lab parses every file with ast and fails if a statement reaching execute was built with an f-string, +, % or .format.
- Data-Centric AI Day 191
- An engineering paradigm focusing on systematically improving dataset quality, consistency, and labels rather than solely tweaking model architectures.
- Data-Centric Error Analysis Day 181
- Systematically inspecting misclassified samples to categorize root causes and fix underlying data issues rather than tweaking algorithms.
- data-ink ratio Day 127
- Tufte's measure: of all the ink on the page, the fraction that is the data itself. Computed here from real pixels as 0.367 for a chart with a tinted panel, gridlines and a heavy box, against 0.934 for the identical eight numbers without them. Not a rule that gridlines are forbidden, but a reminder that every non-data mark should justify itself.
- Data-quality gate Day 94
- The place in a pipeline where every incoming record is validated, the valid ones continue, and the invalid ones are collected, counted and reported rather than crashing the run. Its defining property is what it does NOT do: it does not raise on the first bad record. A gate that stops at the first problem processes nothing and tells you about one thing.
- Data-quality gate Day 98
- A validation boundary placed where untrusted data enters, which decides record by record what is allowed to go further. Two properties separate a gate from a type annotation: it collects every failure rather than stopping at the first, and each rejection carries enough detail — the field path and the reason — for somebody who owns the source to fix it. In this day it is a pydantic model with ranges, forbidden extra fields, and a requirement that timestamps carry an offset.
- database Day 39
- A running program whose whole job is to store data so it can be queried and changed safely, even when many clients access it at once.
- dataclass Day 67
- A standard-library decorator that writes `__init__`, `__repr__`, and `__eq__` from a class's annotations. Ideal for a mutable bag of fields; it validates nothing, so a hand-written class still wins where an invariant must hold.
- dataclass Day 69
- An ordinary class whose boilerplate methods were generated for you from annotated field declarations. The `@dataclass` decorator reads the class's annotations at class-creation time and attaches `__init__`, `__repr__` and `__eq__` — and, on request, comparison and hashing methods too.
- dataclasses.fields() Day 69
- A function returning the `Field` objects a dataclass was built from, each recording a name, a type, and a default or default factory. It is how you inspect the result of the code generation instead of taking it on trust.
- DataFrame Day 120
- A pandas data structure representing a table: a collection of Series that all share the same index. Each column keeps its own dtype independently; the shared index is what lets df.loc["c"] pull the same logical row out of every column at once.
- DataFrame.explode Day 135
- A pandas method that turns a single row whose column holds a list-like value into one row per list element, leaving every other column's value repeated across the new rows. Unlike record_path, explode applied to a row whose list is empty keeps one row with NaN rather than dropping the row -- a difference measured directly on pandas 3.0.5 and worth knowing before relying on either.
- DataFrame.pipe Day 126
- A pandas method that composes a sequence of frame-to-frame functions by passing each one's output as the next one's input, read top to bottom like a chain. Readable, but it removes the easy place to insert an inspection or a breakpoint between two steps that sequential function calls give for free -- a real tradeoff, not a stylistic one.
- DataFrameGroupBy Day 123
- The lazy object returned by df.groupby(...). It records the grouping plan but performs no computation until an aggregation, transformation or filter is attached to it.
- datasheet Day 138
- A document travelling with a dataset that records its motivation, composition, collection process and recommended uses -- by analogy with the datasheet shipped with every electronic component. Proposed by Gebru and colleagues in 2018. This lesson's contract enforces eleven fields and names each missing one, because "documentation incomplete" is not actionable and "no exclusion criteria recorded" is.
- Datasheet for Datasets Day 182
- A companion standard document detailing the provenance, collection protocol, and composition of training datasets.
- datetime Day 60
- The standard-library module for dates and times as real objects that know the calendar: datetime.now() stamps the current moment, .isoformat() and .strftime() format it, and timedelta does correct date arithmetic across days.
- DatetimeIndex Day 131
- A pandas index whose entries are real timestamps rather than plain integers or strings. Produced by passing parse_dates to a loader (Day 121) or by pd.date_range, it is what unlocks date-string slicing, resample and rolling by time, and axis formatting that understands months and years -- none of which a RangeIndex or a string column can do.
- Daylight saving Day 81
- The twice-yearly clock change that makes some local wall-clock times not exist and others happen twice. A daily local schedule therefore has one 23-hour day and one 25-hour day per year, and a job scheduled during the repeated hour runs twice. Scheduling in UTC removes the problem entirely; converting to local time for display keeps the human benefit.
- Daylight Saving Time (DST) boundary Day 131
- The specific date on which a timezone observing Daylight Saving Time shifts its clocks forward (losing one hour, producing a 23-hour local day) or backward (repeating one hour, producing a 25-hour local day). A daily resample of hourly, timezone-aware data spans exactly one such day of each kind per year in a DST-observing zone.
- DB-API 2.0 Day 90
- The Python Database API Specification version 2.0, written by Marc-André Lemburg and adopted as PEP 249 in 1999. It standardises the shape of a database driver rather than hiding the differences between databases: connections, cursors, execute, the fetch methods, the exception hierarchy, and a module attribute naming which parameter style the driver uses. Learning it once transfers to almost every Python database driver.
- DBSCAN Day 184
- Density-Based Spatial Clustering of Applications with Noise: a non-parametric clustering algorithm discovering arbitrary-shaped dense regions.
- De Morgan's laws Day 50
- The rules for rewriting a negated combination of booleans: `not (A and B)` equals `not A or not B`, and `not (A or B)` equals `not A and not B`. They let you turn a confusing negated condition into an equivalent, clearer one.
- Dead Feature Day 175
- An unmaintained feature in production that no longer carries predictive signal or whose upstream data feed has silently corrupted.
- Dead man's switch Day 81
- A mechanism that acts when a signal stops arriving rather than when a bad signal arrives — named from the railway handle that applies the brakes when the driver lets go. Applied to scheduled jobs: each success writes a heartbeat, and an alert fires when the heartbeat gets too old. The only mechanism that detects a job which stopped running, because that failure produces no error at all.
- Dead ReLU Day 209
- A state where a ReLU neuron pre-activation is persistently negative across all samples, resulting in permanent zero gradient flow.
- Dead-letter store Day 98
- A place where rejected records are kept, with their reason and their original payload, instead of being logged and forgotten. It turns "we dropped 3,942 records last Tuesday" from an archaeological problem into a replay: fix the source, replay the queue. It is the piece this day's pipeline deliberately does not have, and the extension exercise that most changes how the validation stage feels.
- Deadlock Day 96
- A cycle of waiting from which nothing can escape: thread one holds lock A and wants B, thread two holds B and wants A. Nothing is busy, nothing errors, and the program simply stops. A timeout on acquisition detects it but does not fix it — in production it converts a hang into a mysterious slow path. The fix is a rule rather than a mechanism: every thread takes locks in the same global order, so a cycle cannot form.
- Debug Adapter Protocol (DAP) Day 37
- A shared, open standard that lets a single editor debugging interface drive debuggers for many different languages through language-specific adapters.
- debugger Day 37
- A tool that controls the execution of another program — starting it, pausing it at chosen points, and letting you inspect its live state — so you can watch exactly what the code does rather than guess.
- Decimal Day 46
- A standard-library type (from the decimal module) that performs exact base-10 arithmetic to a chosen precision, correct for money; build it from a string, as Decimal("0.1"), never from a float.
- Decision Boundary Day 155
- The geometric hyperplane in feature space where the predicted probability equals the threshold (typically 0.5), separating predicted classes.
- Decision Boundary Day 156
- The geometric surface in feature space where the model predicts equal probability across classes (or where the score crosses the classification threshold), separating different predicted class regions.
- Decision Manifold Day 201
- The high-dimensional non-linear geometric boundary separating classification regions in feature space.
- Decision Region Day 156
- The contiguous zone in feature space where all points are assigned to the same class label by the classification model.
- Decision Threshold Day 155
- The cutoff probability tau used to convert continuous probabilities into discrete class labels (y_hat = 1 if p >= tau else 0).
- Decision Tree Day 162
- A non-parametric hierarchical supervised learning model that recursively partitions feature space into axis-aligned rectangular regions based on feature threshold tests.
- decision_function() Day 146
- A classifier's raw score before probabilities are computed. For binary classifiers, predict(X) equals classes_ indexed by (decision_function(X) > 0); for multiclass, classes_ indexed by its argmax. Both relationships measured directly in this lesson.
- Declarative model Day 93
- A Python class that both describes a table and is the type its rows are loaded into. In SQLAlchemy 2.0 it subclasses DeclarativeBase and declares its columns with Mapped annotations and mapped_column(). The 1.x declarative_base() factory and the Query object are legacy: they still work and you will meet them in old code, but nothing modern needs them.
- Declarative query Day 85
- A statement of the result you want rather than the steps to produce it. Writing SELECT ... WHERE ... ORDER BY says nothing about whether to use an index, in what order to test conditions, or how to sort. The engine decides, decides again as the data changes, and may reach a different conclusion tomorrow while returning identical rows.
- decode Day 45
- The operation that turns bytes back into a str using a named encoding; the reverse of encode.
- decomposition Day 63
- The act of breaking a program's work into smaller parts — functions and modules — each with a single responsibility and a clear interface. Good decomposition maximises cohesion within parts and minimises coupling between them.
- Decoupled Weight Decay Day 206
- Subtracting a fraction of the current weight value directly during parameter updates, independent of the adaptive gradient scale.
- deduplication Day 54
- Removing duplicate items so that each value appears once. Building a set from a sequence deduplicates it in a single pass, far faster than repeatedly checking a growing list.
- deep copy Day 52
- A copy that duplicates a list and everything it contains, recursively, made with `copy.deepcopy(a)`. The result is fully independent — mutating a nested list in one does not affect the other.
- Deep Learning Transition Day 196
- The pedagogical advancement from classical tabular ML to gradient-based neural networks and PyTorch tensor computing.
- def Day 57
- The Python keyword that begins a function definition, followed by the function name, a parenthesised parameter list, a colon, and an indented body — for example def mean(numbers):.
- default argument Day 57
- A value given to a parameter in the function definition (greeting="Hello") that is used when the caller omits that argument, so the parameter becomes optional at the call site.
- Default Split Direction (GBDT NaNs) Day 174
- The optimal tree branching direction (left or right) chosen by gradient boosted trees to route missing values based on maximum split gain.
- default_factory Day 69
- A callable stored on a field and invoked once per instance to produce that instance's default value. It is the only correct way to default a list, dict or set, because a plain default object would be created once and shared by every instance.
- defaultdict Day 60
- A collections type that supplies a default value for a missing key automatically, so you can append to defaultdict(list)[key] without first checking whether the key exists — removing the "if key in d" boilerplate of grouping.
- delegation Day 68
- Passing a call through to a stored collaborator object — the forwarding method that makes composition work. More typing than inheritance, and far more visible, because the wiring is written out rather than found by walking a hierarchy.
- Deletion anomaly Day 87
- The failure where removing one fact removes another that happened to share the row — withdrawing a library's only copy of a book also erases the only record that its author exists. You meant to remove a book and you removed a person.
- delimiter Day 65
- The character separating fields within a record — a comma by convention, but semicolons, tabs, and pipes are all common in the wild. Always check before parsing rather than assuming.
- demographic parity Day 138
- The criterion that both groups be selected at the same rate, regardless of their base rates. Easy to state and easy to enforce exactly; enforcing it in this lesson's example drove the selection-rate gap to 0.0000 and pushed the precision gap out to 0.3333.
- Demographic Parity Day 179
- A fairness metric requiring the positive prediction rate to be equal across all protected demographic groups.
- Dendrogram Day 184
- A tree diagram recording the sequence of cluster merges or splits and the distance levels at which they occur.
- Denormalization Day 87
- Deliberately storing data pre-joined, trading the three anomalies back in exchange for faster reads. A legitimate engineering decision when you have measured the need and can name every code path that must keep the copies in step. Doing it without that plan is choosing the update anomaly on purpose.
- Denormalization Day 88
- Deliberately storing a value that could be recomputed, to buy a faster answer. It costs you the obligation to keep the copy true forever, through every code path that touches the source. A legitimate choice made against a measurement and paired with a mechanism that keeps it honest; without one it is a bug with a delay on it.
- Denormalization Day 92
- Deliberately storing the same fact in more than one place so that a read needs no join — for example copying a book's title into every loan document. Reads become one lookup. The bill arrives when the fact changes: there is no cascade, no UPDATE across documents and no error if you miss a copy, so the update anomaly that normalization was invented to prevent returns through a different door.
- dependency Day 13
- Other software a package needs installed first in order to run; the branching chain of these is what a package manager resolves automatically.
- dependency Day 43
- A package that a project needs in order to run; a project's dependencies (and their exact versions) are what a virtual environment isolates and requirements.txt records.
- dependency Day 60
- A third-party package your program relies on, installed from the Python Package Index with pip (for example NumPy, pandas, or requests). Every dependency adds capability but also setup, size, security surface, and a maintenance burden — so you add one only when it clearly pays.
- dependency injection Day 82
- Supplying what a function needs as an argument rather than letting it reach for it. FastAPI spells it `Depends(f)`, meaning "call f and pass me the result", resolved per request and cached within one request. `app.dependency_overrides` swaps any dependency in a test, which is Day 74's boundary argument with framework support.
- Dependency injection Day 72
- A design in which a component declares what it needs and something else supplies it, rather than constructing its own dependencies. pytest's version is unusual in that the key is an identifier in a function signature: the parameter name is the request, which is why fixtures need no configuration and why a misspelled name is an error rather than a None.
- Dependency injection Day 74
- Handing a piece of code its collaborators instead of letting it reach out for them — which in Python usually means nothing more elaborate than passing them as arguments. It is the alternative to mocking, and the one this lesson argues for, because it improves the design rather than working around it.
- dependency override Day 82
- An entry in `app.dependency_overrides` mapping a dependency function to a replacement, consulted on every request. It is how a test hands the application an in-memory fake, a frozen clock and a counted id source without patching anything inside the application or putting an "if testing" flag in a handler.
- dependency resolution Day 13
- The process of reading each package's requirements and computing the complete set of packages needed, in an order where nothing is missing when it is used.
- Dependency specifier Day 83
- A package name plus an optional version constraint, such as `requests>=2.31,<3` or `requests~=2.31.0`, optionally with extras and an environment marker. It states what your code is compatible with. A library should specify the widest range it genuinely works with; an application should pin exact versions in a lock file instead.
- Deployed ML Service Day 196
- A complete, production-grade microservice exposing a trained model over a REST API with schema validation and drift monitoring.
- Derivative Day 108
- The instantaneous rate of change of a function at a point: the limit of the difference quotient as the interval width goes to zero, and equivalently the slope of the tangent line there. Written f'(x) or dy/dx. A derivative is itself a function — it has a value at every point where the limit exists — and its own derivative is the second derivative. The reason it matters for this course is one sentence: its sign tells you which way to move to make a quantity smaller.
- Derived data Day 91
- A value that is a function of other stored values — a queue position computed from a timestamp and a status, a cached count, a duplicated name. Storing it means promising to recompute it everywhere any input changes, forever, in every code path that will ever exist. The database cannot enforce that promise, so it is not a promise. Store what you are told; derive what follows from it.
- derived field Day 69
- A field computed from the others rather than passed in, declared with `field(init=False, ...)` so it is not a constructor parameter, and filled in by `__post_init__`.
- deserialization Day 65
- The reverse: turning stored bytes back into in-memory objects, as json.load and csv.DictReader do. The round trip is not always exact, which is where tuples and non-string dict keys catch people out.
- Design matrix Day 150
- The matrix of predictor values the model is actually fitted to, one row per observation and one column per feature (plus an intercept column of ones). PolynomialFeatures and an interaction term both work by adding columns to this matrix before an ordinary linear fit ever runs.
- detached HEAD Day 34
- The state where HEAD points directly at a specific commit instead of a branch, so new commits belong to no branch and can be lost if you switch away without saving them to one.
- DetachedInstanceError Day 93
- The error raised when you touch an attribute of an object whose Session has closed. It has two distinct causes with two distinct fixes, and the message tells you which. "Attribute refresh operation cannot proceed" means commit() expired a loaded column and close() removed the connection that would refresh it — fix with expire_on_commit=False. "Lazy load operation of attribute" means a relationship was never loaded at all — expire_on_commit will not help, because there is nothing to keep; eager-load it while the Session is open instead.
- Determinant Day 102
- The signed factor by which a transformation multiplies area, equal to a*d - b*c for a 2 by 2 matrix [[a, b], [c, d]]. Best met by measuring rather than by formula: send the unit square through and the signed area of what comes out IS the determinant. Its size is the area factor, its sign is the orientation, and a value of zero means the plane was flattened onto a line and nothing can undo it.
- determinism Day 126
- The property that the same input and configuration always produce a byte-identical output, including row order -- which requires every sort to name an explicit tie-break, because a "stable" sort only preserves whatever order tied rows happened to arrive in.
- Determinism Day 74
- The property that the same inputs always produce the same outputs. A test can only assert equality against a deterministic value, which is why the clock, randomness and a language model's sampling must be replaced or injected before a meaningful assertion is possible.
- Determinism Day 143
- The property that identical inputs give identical outputs. Proved by a manifest matching across runs -- and only meaningful when accompanied by the control that a changed input produces a changed manifest.
- Deterministic Seeding Day 210
- Setting identical initial seed states across all random number generators to ensure identical execution results.
- deuteranopia Day 127
- The absence of a working medium-wavelength cone, the most common form of red-green colour vision deficiency. Simulated here with the Machado, Oliveira and Fernandes (2009) severity-1.0 matrix applied in linear RGB. A simulation approximates a deficiency; it does not reproduce anyone's experience, assumes a single severity, and cannot represent anomalous trichromacy.
- Deviance Day 164
- Twice the negative log-likelihood (log-loss), commonly used as the loss metric for binary classification gradient boosting.
- Device Agnosticism Day 202
- Writing code that dynamically selects and executes on available hardware (CPU, NVIDIA CUDA, Apple MPS) without platform hardcoding.
- device driver Day 6
- A hardware-specific module, usually loaded into the kernel, that translates one device's particular dialect into the standard interface the rest of the system expects.
- DevTools Day 21
- A browser's built-in Developer Tools: a panel for inspecting a page's structure, console, performance, and network activity, opened with F12 or Command-Option-I.
- Diagnosis before treatment Day 145
- Establishing which term dominates before choosing an intervention. It costs one fit and rules out the expensive mistakes: commissioning labels against a bias problem, or adding capacity against a variance one.
- Diagonal matrix Day 100
- A square matrix whose only non-zero entries lie on the main diagonal. Applied to a vector it scales each coordinate by its own factor, independently of the others — no coordinate influences any other. numpy.diag builds one from a list of values. The identity matrix is the special case where every diagonal entry is 1.
- Diagonalisation Day 106
- Rewriting a matrix as A = V D V-inverse, where the columns of V are the eigenvectors and D is the diagonal matrix of eigenvalues. In one sentence: changing to the basis where the matrix is just a scaling. Read right to left as Day 101 taught, V-inverse translates a vector into eigenvector coordinates, D scales each coordinate independently, and V translates back — so the complicated matrix in the middle has become a list of numbers, and the k-th application becomes a list of k-th powers. It is possible exactly when there are enough independent eigenvectors to fill V. When there are not — as for a shear — the matrix is called DEFECTIVE and diagonalisation does not exist. The dangerous part is that the attempt fails silently: numpy.linalg.inv on a singular eigenvector matrix does not raise, it returns entries around 4.5e15 and a plausible wrong answer.
- dialect Day 65
- The particular combination of delimiter, quote character, and line ending a producer uses. The csv module lets you name one explicitly, and csv.Sniffer will guess one from a sample.
- diamond problem Day 68
- The ambiguity that arises when a class inherits from two classes that share a common ancestor: in what order should the interpreter search? C3 answers it deterministically and lists the shared ancestor exactly once, so it is never initialised or executed twice.
- dict comprehension Day 53
- A compact expression that builds a new dictionary from an iterable in one line, of the form {key: value for item in iterable if condition} — the dictionary counterpart of a list comprehension.
- dict comprehension Day 55
- A comprehension in curly braces with a `key: value` pair that builds a dictionary — for example `{r["name"]: r["score"] for r in records}`.
- dictConfig Day 97
- Configuring the whole logging system from one dictionary — formatters, filters, handlers, loggers and the root — rather than from a sequence of calls. Because it is data, it can be loaded from the same TOML file as the rest of your configuration, kept in version control and diffed in review. Its trap is disable_existing_loggers, which defaults to True and silences every logger that already existed, including those libraries create at import time.
- dictionary Day 53
- Python's built-in mapping type: a mutable collection of key-value pairs in which each key is unique and maps to one value, offering fast lookup, insertion, and deletion by key, and (since 3.7) preserved insertion order. Written with braces, e.g. {"cat": 4}.
- DictReader Day 65
- The csv module reader that yields each record as a dictionary keyed by header name. It pads a short row's missing fields with None rather than raising — which is convenient and dangerous in equal measure.
- diff Day 29
- The precise list of lines added and removed between two commits, used to answer "what changed?" without reading whole files.
- diff Day 33
- The line-by-line comparison between two versions of the code, showing exactly which lines a change adds, removes, and modifies.
- difference Day 54
- The set operation `a - b` that returns the items in the first set but not the second — e.g. `{1, 2, 3} - {2, 3, 4}` is `{1}`.
- Difference quotient Day 108
- The fraction (f(x + h) − f(x)) ÷ h whose limit defines the derivative. Everything in numerical differentiation is a difference quotient evaluated at a finite h rather than taken to a limit, which is why every numerical derivative is an approximation and why the choice of h matters so much.
- Differentiability Day 149
- Whether a function has a well-defined slope at every point. Squared error is differentiable everywhere, which is what makes the normal equations possible; absolute error is not differentiable at a residual of zero, which is why it has no equivalent closed form.
- Differentiable Day 108
- A function is differentiable at a point when the limit of its difference quotient exists there — which requires the limit from the left and the limit from the right to agree. |x| is continuous at 0 and not differentiable at 0: the left slope is −1 and the right slope is +1, and there is no third number between them that the sequence settles on. Differentiable implies continuous; continuous does not imply differentiable.
- differential privacy Day 138
- A property of the algorithm producing an output rather than of the released table: the guarantee that the output is nearly as likely whether or not any one individual's record is present. Introduced in 2006 by Dwork, McSherry, Nissim and Smith. Structurally different from k-anonymity and not interchangeable with it. Described in this lesson, not demonstrated -- no differentially private mechanism was implemented or run here.
- Dimension Day 99
- The number of components a vector has, and nothing more mysterious than that. Two components is 2-dimensional and can be drawn; three can be drawn with effort; three hundred cannot be drawn at all and is still just a list of three hundred numbers. Every formula on this day is written so that the dimension never appears in it, which is exactly why the arithmetic survives the jump the picture does not.
- Directional derivative Day 109
- The rate at which a function changes as you move from a point along a chosen direction, computed as the dot product of the gradient with the UNIT vector in that direction: D_u f = ∇f · u. Normalising first is not tidiness — without it, handing in a longer arrow would give a bigger answer and the quantity would depend on how the direction was written rather than on which way it points. A partial derivative is the special case where the direction is an axis. Since ∇f · u = |∇f| cos θ, the answer for every direction is recoverable from one gradient.
- directory Day 9
- A named list that maps names to files and to other directories, forming the branches of the filesystem tree (called a "folder" in graphical tools).
- direnv Day 11
- An open-source tool that automatically loads a per-directory set of environment variables when you enter a project directory and unloads them when you leave.
- Discriminated union Day 94
- A union of several models where one field decides which member applies, declared with Field(discriminator="kind"). Without it, pydantic tries every member and reports errors from all of them, which is slow and produces an unreadable report; with it, the discriminator is read first and only the matching model is tried, so the errors name the right branch.
- Disparate Impact Ratio Day 179
- The ratio of the positive selection rate of the unprivileged group to the privileged group (4/5ths or 80% rule threshold).
- Dispatch Day 80
- Routing a parsed subcommand to the function that implements it. The argparse pattern is `subparser.set_defaults(func=cmd_add)`, which puts the handler on the namespace so `args.func(args)` is the whole of dispatch and no branch on the command name exists anywhere in the program.
- DISTINCT Day 86
- Removes duplicate output ROWS, not duplicate values in one column. SELECT DISTINCT author gives one row per author; SELECT DISTINCT author, genre gives one row per distinct pair, so adding a column to a DISTINCT query can only increase the number of rows returned. It runs after SELECT, which is why it de-duplicates the projection.
- Distinguishable from baseline Day 147
- Whether an improvement over the baseline exceeds the test set's own 95 percent half-width. Here, an improvement of 0.3509 against a half-width of 0.0241 is clearly distinguishable; a smaller improvement on the same test set might not have been, and the arithmetic is how you would find out.
- distributed VCS Day 29
- A version control design in which every developer clones the entire repository, history and all, so committing, diffing, and branching are local and instant (for example, Git and Mercurial).
- distributed version control Day 30
- A model, used by Git, in which every clone is a full copy of the repository and its history, so you can commit and inspect history without a central server.
- Distribution name Day 83
- The name you type after `pip install`, and the name an index lists. It must be unique across the whole index and is often chosen for searchability rather than brevity. For this lesson's package it is `wordtally-tools`. It differs from the import name constantly in real projects: `beautifulsoup4` installs `bs4`, `pillow` installs `PIL`, `scikit-learn` installs `sklearn`.
- Distribution package Day 83
- The installable artifact — an archive plus its metadata, such as `wordtally_tools-0.3.1-py3-none-any.whl`. This is what an index lists, what `pip install` fetches, and what the word "package" means when a packaging document says it. The community shortens it to "distribution".
- Distribution shift Day 141
- What happens when the inputs a deployed model meets stop resembling the ones it was trained on. In this lesson a model scoring 0.948 in distribution scores 0.4895 -- below chance -- on the identical problem translated to a different region, while the underlying rule still scores 1.000 there.
- Distributive Day 101
- The property that A @ (B + C) equals A @ B plus A @ C — matrix multiplication splits over addition. It is what allows a layer weight matrix to be decomposed into a base part and a small correction whose results are then added, which is half the reason low-rank adapters work.
- Divergence boundary Day 111
- The learning rate 2/a at which a 1-D quadratic gradient-descent run stops converging, even with alternating overshoot, and starts growing without bound. Above it, |x| grows by a fixed factor every step until the run overflows to inf and the next update becomes nan.
- diverging palette Day 127
- A colour ramp running from one dark end through a light middle to another dark end, such as RdBu, for data with a meaningful midpoint -- profit against loss, anomaly against a baseline, error against none. Using one where no midpoint exists invents a distinction the data does not have.
- divide and conquer Day 62
- An algorithm-design strategy that solves a problem by breaking it into smaller independent subproblems of the same kind, solving each (often recursively), and combining the results. It is the same decomposition as the base-case/recursive-case split, and underlies sorting, searching, and many tree and graph algorithms.
- DNS Day 15
- The Domain Name System, the internet's directory service that translates a human-friendly name like example.com into a numeric IP address.
- DNS Day 16
- The Domain Name System, a distributed, hierarchical directory that maps human-friendly names to records such as IP addresses.
- DNS Day 42
- The Domain Name System, which resolves a human-readable host name to an IP address — the first layer to check when a program cannot connect (day 16).
- docstring Day 49
- A string literal placed as the first line inside a function, class, or module that documents what it does; tools and the built-in help system read it.
- docstring Day 57
- A string literal placed as the first line of a function body that documents what the function returns and how to call it; accessible at runtime as the function's __doc__ and read by help() and tools.
- docstring Day 61
- A string literal written as the first statement of a module, function, class, or method, accessible at runtime as the object's `__doc__` and by `help()`. Unlike a comment, it is part of the program's data and is what documentation tools and IDEs display.
- docstring-driven design Day 63
- Designing a function by writing its signature and docstring — the contract of what it takes, returns, and promises — before writing its body. Fixing the interface first ensures the pieces fit and turns each body into a small, well-targeted task.
- Document store Day 92
- A key-value store that agrees to look inside the value. The value must be in a format the store can parse, usually JSON or a binary encoding of it, and in exchange the store can filter and index on fields inside it. MongoDB and CouchDB are the well-known ones. It still does not check what the fields are called.
- documentation Day 22
- The human-written guide to an API that lists each endpoint, the parameters it accepts, and example requests and responses — what you read to learn how to call a new API.
- documentation Day 28
- The reference an API publishes describing its endpoints, parameters, authentication, and response shape; reading it is the core transferable skill of consuming any API.
- DOM Day 20
- The Document Object Model, a live tree of nodes the browser builds from the HTML; every element is a node, and scripts can add, remove, or change nodes to update the page.
- DOM Day 79
- The Document Object Model — the tree of elements a document becomes once it is parsed, with parents, children and siblings. BeautifulSoup builds one from HTML text; a browser builds one and then lets JavaScript modify it, which is why some pages contain no data until their scripts have run.
- Domain Day 70
- The slice of the real world a program is about — gym memberships, spending, appointments, a document index. The domain is what the rules describe, before any decision about code.
- Domain exception hierarchy Day 70
- A family of exceptions with a single base class — for example SpendError — raised whenever a domain rule is refused, so an adapter can catch one type, know it is holding a broken rule rather than a bug, and translate it into a human message.
- Domain model Day 70
- A set of objects and rules that mirror a domain closely enough that the code reads like the problem: meaningful types, rules living with the data they constrain, and a boundary separating them from files and screens.
- Domain Ratio Day 171
- A custom mathematical quotient representing a known physical, economic, or clinical relationship (e.g. Debt-to-Income, BMI).
- Dominant eigenvalue Day 106
- The eigenvalue of largest absolute value, and the eigenvector belonging to it is the dominant eigenvector. It matters because repeated application of a matrix is eventually governed by it alone: writing any starting vector as a mixture of the eigenvectors, each application multiplies each ingredient by its own eigenvalue, so the ingredient with the largest magnitude outgrows every other one. Nothing is eliminated; it is simply left behind. Note that dominant is about MAGNITUDE, so minus 5 dominates 2. When two eigenvalues share the largest magnitude there is no dominant direction at all, and iterative methods that assume one will never converge.
- Dot product Day 99
- Multiply matching components of two vectors, then add the results. It takes two vectors and returns a single number, and that collapse is why it turns up everywhere: a weighted sum, a projection and a similarity score are all dot products. It is zero exactly when the two vectors are perpendicular, and the dot product of a vector with itself is its magnitude squared.
- Dot product Day 101
- The operation that takes two vectors of the same length, multiplies them entry by entry, and adds up the products, returning a single number rather than a vector. Written u dot v. It has an equivalent geometric form, the product of the two lengths times the cosine of the angle between them, and the two forms give the same number — which is why a dot product of zero means the vectors are perpendicular, and why a vector dotted with itself is its squared length.
- Dot product Day 103
- Multiply two vectors component by component and add up the results: [1, 2, 3] dot [4, 5, 6] is 4 plus 10 plus 18, which is 32. The answer is a single number, not a vector, which is why it is also called the scalar product. Its geometric meaning is the one that matters: a dot b equals the length of a times the length of b times the cosine of the angle between them. Everything else in this lesson is that identity read in a different direction.
- dotenv Day 11
- A convention of storing environment variables as NAME=value lines in a file (commonly .env) that is loaded at run time and kept out of version control via .gitignore.
- Double descent Day 145
- Test error falling again beyond the interpolation threshold, described in work from around 2019. The U-curve of this lesson is the right first mental model and is not the whole story for very large models; this lab reaches the left-hand edge of the effect.
- dpi Day 128
- Dots per inch -- the resolution a Figure gets rendered at when saved to a raster format. Combined with figsize, dpi determines the output's pixel dimensions exactly: a 6x4 inch figure at 100 dpi saves at 600x400 pixels; at 200 dpi, 1200x800.
- draft pull request Day 33
- A pull request marked as work-in-progress to signal it is not yet ready for formal review or merge; it is opened for review by marking it ready.
- Drawn geometry Day 132
- What a chart actually renders, as opposed to the values passed to the plotting call. Every measurement in this lesson reads it back through matplotlib's own transforms -- patch bounding boxes, line data pushed into axes fractions, collection sizes, projected 3D corners -- because a measurement computed from the inputs can never disagree with them and would report a lie factor of 1.0 for every chart ever drawn.
- Drift Day 81
- The accumulating lateness of a loop that sleeps for a fixed duration after doing work, because the interval is measured from when the work finished rather than from when it should have started. Five seconds of work in a sixty-second loop is really a sixty-five-second schedule, and run 100 is 495 seconds late.
- drop_last Day 205
- A DataLoader flag indicating whether to discard the final incomplete mini-batch if dataset size is not divisible by batch_size.
- dropna Day 125
- The pandas method that removes rows or columns containing missing values, controlled by how (any/all), thresh (a minimum count of non-null values required to survive) and subset (which columns to check). Honest when the affected rows are few and the missingness is uninformative; disastrous when missingness itself carries information, because dropping silently discards it.
- dropna (groupby) Day 123
- A groupby keyword, default True, controlling whether rows with a missing group key are excluded from every group (True, the default) or collected into their own NaN-labelled group (False). The default is the mechanism behind this lesson's opening failure: a grouped sum under dropna=True can be silently less than the true overall sum.
- DRY Day 57
- "Don't repeat yourself" — the principle that each piece of logic should have a single home. When the same code appears twice, factor it into a function and call it, so a fix happens in one place.
- dry run Day 14
- A mode in which a script prints the actions it would take without performing any of them, so you can safely preview a destructive job before trusting it.
- Dry run Day 80
- A mode, conventionally `--dry-run`, in which a destructive command reports exactly what it would do and changes nothing. It must still perform its reads and checks for real — otherwise it can promise an impossible deletion — and must return before ever reaching the write. Prove it by hashing the target before and after.
- Dry run Day 84
- A mode that does everything a real run does except the writes, and reports exactly what would have changed. It must still fetch, validate and compute, because the work is where the surprises are; a dry run that skips the work tells you nothing. It is not a test: a test checks behaviour against fixtures, while a dry run reports on this invocation against the actual world.
- DST transition Day 95
- The instant at which a region changes its offset, usually by an hour and usually twice a year. The two directions are not symmetric in their consequences: going forward deletes a stretch of wall-clock readings, going back duplicates one. Not every transition is an hour — Lord Howe Island moves by thirty minutes — so code that special-cases plus or minus exactly one hour is already wrong somewhere.
- dtype Day 104
- The data type shared by every element of an array, recorded once in the header rather than per element. It fixes the width of every element, which is what makes the block contiguous and the address of element i computable as base plus i times stride. It is also a promise about range and precision that can be broken by accident: an int8 holds -128 to 127 and wraps silently past either end, and a float32 has 24 bits of significand and cannot distinguish 16,777,216 from 16,777,217. Check a.dtype first whenever a number looks impossible.
- dtype Day 120
- The single data type every value in a given Series or column shares. Common dtypes include int64, float64, bool, and, as of pandas 3.0, str (replacing object as the default for text columns).
- dtype (as a read_csv argument) Day 121
- A dict mapping column names to the dtype read_csv() should assign them, overriding inference entirely for that column. dtype={"id": "str"} is the fix for an identifier column whose leading zeros or non-numeric-looking values matter.
- dtype pinning Day 135
- Explicitly converting a column to its intended type -- numeric, datetime, categorical -- rather than trusting whatever pandas inferred on load. For ingested JSON, pinning must tolerate a column that is entirely absent from some records, which becomes a fully-NaN column once the frame is assembled rather than raising an error.
- dtype promotion Day 120
- The automatic widening of a column's dtype -- most commonly int64 to float64 -- that pandas performs when a value the original dtype cannot represent (such as a missing value) is introduced. int64 has no bit pattern for "missing"; float64 does, via NaN.
- dtype-mismatch join Day 124
- A join failure caused by the same key values being stored with different pandas dtypes on each side -- for example, int64 on one side and a pandas Categorical of the same digits on the other. On pandas 3.0.5, an int64-versus-categorical mismatch returns zero matching rows silently, while an int64-versus-plain-string mismatch raises ValueError instead.
- Dual number Day 110
- A pair holding a value and its derivative with respect to a seeded input, with arithmetic defined so that the derivative propagates automatically — addition adds both parts, multiplication applies the product rule. Dual numbers are the whole implementation of forward mode.
- Dual y-axis Day 132
- A chart with two independently scaled value axes, typically created with ax.twinx() in matplotlib and automatically by some BI tools when a second measure is added. Contrary to the usual warning, the scaling cannot change the Pearson correlation of the two drawn traces -- correlation is invariant under affine transforms. What it does control is the sign, which inverting one axis negates exactly, and how close the two curves sit, which is what readers actually respond to and which is entirely the author's choice.
- duck typing Day 68
- Treating an object as usable because it has the required methods, not because of its ancestry: if it walks like a duck, it is treated like one. It is why a function that only calls `.read()` should accept a file, a socket wrapper, or a test double equally.
- Dummy Day 74
- A test double passed only to fill a parameter slot on a path that must never use it. A good dummy raises AssertionError if it is ever called, turning a silent assumption about which branch ran into a loud failure.
- dunder method Day 68
- A method whose name begins and ends with double underscores, such as `__len__` or `__eq__`, which the interpreter calls on your behalf when you use ordinary syntax. Short for "double underscore". They are the language's public protocol, not private helpers — though inventing new dunder names of your own is discouraged, since those are reserved.
- durability Day 39
- The guarantee that once data is committed to a store it survives crashes and restarts; object storage and databases provide it, while a cache deliberately does not.
- Dying ReLU Day 198
- A failure mode where neurons become permanently inactive because their pre-activation falls into the negative regime where the gradient is zero.
- dynamic array Day 52
- The data structure underneath a Python list: a contiguous block of references that over-allocates a little spare capacity so most appends are instant, and grows by allocating a bigger block and copying references when the spare runs out.
- Dynamic Computational Graph Day 202
- A graph structure built on-the-fly during forward execution, allowing dynamic control flow, loops, and variable tensor shapes.
- Dynamic Padding Day 205
- Padding sequences in a mini-batch to the maximum length of that specific batch, rather than a global fixed maximum length.
- dynamic typing Day 44
- The rule that a value's type belongs to the object and is checked at run time, so a name may be re-bound to a value of any type at any point.
- EAFP Day 66
- "Easier to ask forgiveness than permission" — attempt the operation and handle the failure. Python's default style, because it has one code path and no window between checking and acting.
- Eager loading Day 93
- Deciding in advance, per query, which related rows you will need, so they are fetched with the parent rather than one at a time. It is a per-relationship, per-query decision rather than a global setting, because whether you need a relationship depends on what the caller is about to do with it.
- Early Exaggeration Day 186
- An optimization heuristic scaling high-dimensional joint probabilities during initial iterations to encourage cluster separation.
- Early stopping Day 145
- Halting gradient descent before it reaches the capacity available to it. Training time is a capacity dial: training error fell at every one of 600 epochs here while test error bottomed at epoch 14 and the gap grew fivefold.
- Early Stopping Day 164
- Halting the boosting iterations when performance on a held-out validation dataset stops improving for a specified number of rounds (patience).
- Early Stopping Day 210
- A regularization technique that halts optimization when validation loss fails to improve after a set number of patience epochs.
- EDA report Day 133
- A document that turns an exploratory analysis into an argument: one stated question, the decision it feeds, a conclusion placed above the evidence, a small number of figures each answering a stated question and captioned with the claim it supports, the caveats, and the provenance. It is not a cleaned-up notebook; a notebook records a search, and a search has a trail rather than a conclusion.
- edge case Day 49
- An input at the boundary of what a program expects — empty input, the wrong type, or an out-of-range or impossible value — that must be handled deliberately rather than assumed away.
- Editable install Day 83
- `pip install -e .` — installs the project into an environment without copying its code, by writing a path file that points back at your source tree. Edits take effect with no reinstall, which is right for development. It is not a test of your packaging: the import path never goes through the wheel, so an editable install can succeed while the wheel is broken.
- EditorConfig Day 36
- A small standard — a file named .editorconfig placed in a project — that many editors read automatically to agree on basic formatting like indentation, line endings, and final newlines, keeping a whole team consistent regardless of editor.
- EFB (Exclusive Feature Bundling) Day 165
- Combining mutually exclusive sparse features (rarely non-zero simultaneously) into a single dense feature bundle to reduce feature dimension.
- Effect size Day 118
- A measure of how large a difference is, independent of sample size -- for example Cohen's d, the standardized mean difference. A tiny effect size can still reach statistical significance given enough data; this lesson demonstrated a fixed 0.5% relative difference going from non-significant (n=30) to overwhelmingly significant (n=100,000) with the effect size itself unchanged.
- Effect size Day 119
- How large an observed difference is, in the metric's own units (percentage points for a rate, seconds for a duration) and often also as a relative lift. Distinct from a p-value, which answers only whether the difference would be surprising under no true effect -- not how large it is or whether it is worth acting on.
- Effect size (Cohen's d) Day 136
- A standardized measure of how large a difference is, expressed in units of pooled standard deviation, independent of sample size or the p-value's magnitude. A conventional rule of thumb (Cohen, 1988) treats d around 0.5 as the boundary between a "medium" and a "large" effect.
- Eigenvalue Day 106
- The scale factor belonging to an eigenvector — how much the matrix stretches that direction. Its value is the news: above 1 means stretched, exactly 1 means unchanged, between 0 and 1 means shortened, negative means reversed end-for-end along the same line, and exactly 0 means the direction was collapsed to the origin. That last case is Day 102 zero determinant arriving in new clothing. Note the asymmetry with its partner: an eigenVALUE of zero is permitted and highly informative, while an eigenVECTOR of zero is excluded because it satisfies the defining equation for every lambda and therefore distinguishes nothing.
- Eigenvalue Day 185
- A scalar lambda representing the magnitude of variance captured along the direction of its corresponding eigenvector.
- Eigenvector Day 106
- A non-zero vector that a matrix scales but does not turn: applying the matrix leaves it on exactly the line it started on, only longer, shorter, or reversed. Formally, v is an eigenvector of A if A v = lambda v for some number lambda, with v not the zero vector. The critical subtlety is that it is really a LINE rather than a vector: if A v = lambda v then the same equation holds for minus v and for 3.7 v, so every non-zero multiple is equally an eigenvector. Any library that returns one vector has made an arbitrary choice, which is why comparing eigenvectors component by component is a bug and comparing absolute cosines is not. The word is half-translated German: eigen means own or characteristic, so this is the matrix own direction.
- Eigenvector (Loading Vector) Day 185
- A directional unit vector w representing a principal axis of variation that satisfies Sigma w = lambda w.
- ElasticNet Day 151
- Both penalties combined, with l1_ratio controlling the mix -- l1_ratio=1.0 recovers plain lasso exactly (confirmed here down to the same zero count and R2), l1_ratio=0.0 recovers ridge's penalty shape but NOT its alpha scale.
- Elementwise operation Day 100
- An operation applied to each entry independently — addition, subtraction, multiplication by a scalar, and NumPy's * between two arrays. Requires shapes that are identical or that broadcast. Not to be confused with matrix multiplication, written @ in NumPy, which has a completely different shape rule and is Day 101's subject. The notation is one character apart and confusing the two is a rite of passage.
- Elementwise product Day 101
- Multiplying two arrays of the same shape entry by entry, with no summing anywhere, written A * B in NumPy. A different operation from the matrix product and not a slower or sloppier version of it. The compact way to hold the distinction: @ is * followed by a sum along the last axis, and it is the summing that loses a dimension and makes the result a transformation rather than a rescaling.
- else block Day 66
- The part of a try statement that runs only when the try body raised nothing. It exists to keep the try block small, so an error raised by the success path can never be mistaken for one raised by the risky call.
- Embarrassingly Parallel Day 163
- A computation that requires zero communication between sub-tasks, allowing random forest trees to train simultaneously across all CPU cores.
- Embedded Method Day 172
- Feature selection performed directly as part of the model learning algorithm (e.g. L1 Lasso sparsity, Tree Gain importance).
- Embedding Day 99
- A vector produced by a model to represent an item — a word, a sentence, a document, an image — arranged so that items which are alike in some way end up near each other. The claim "similar things are near each other" is a claim about distance and is therefore checkable with the arithmetic of this day. Real embeddings have hundreds or thousands of components whose individual meanings nobody assigned; the hand-made four-component vectors in this lab differ only in size and in who chose the columns.
- Embedding Day 103
- A vector produced by a trained model to represent an item — a word, a sentence, a document, an image — such that items with similar meanings get vectors pointing in similar directions. The lesson's six four-component tables are hand-counted stand-ins with features chosen by a person; a real embedding has hundreds or thousands of components whose individual meanings nobody assigned. Everything else is the same: a row of numbers per item, and similarity measured with a cosine.
- Emergent design Day 73
- The idea that a good design can arrive through many small, test-forced changes rather than being drawn up in advance. Cycle 3 of the bowling kata is a real instance — the frame walk appeared because a strike test made summing rolls impossible. How far this scales is one of the genuinely contested claims about TDD.
- empirical cumulative distribution function (ECDF) Day 130
- A step function that, at any value x, reports the fraction of the sample less than or equal to x. It requires no bin width and no bandwidth -- every observation is a step, and nothing is smoothed, grouped, or discarded. A quantile (including the median) can be read directly off it by finding where the curve crosses that fraction.
- encapsulation Day 15
- The layered wrapping of data as it goes down the network stack — an HTTP message inside a TCP segment inside an IP packet inside a link frame — unwrapped again at the other end.
- encapsulation Day 67
- Keeping state and the behaviour that maintains it together, and routing changes through that behaviour. Python does it with conventions and properties rather than access keywords.
- enclosing (scope) Day 58
- The scope of an outer function that wraps a nested function. A nested function can read the enclosing function's variables, and with nonlocal can rebind them — the mechanism behind closures.
- encode Day 45
- The operation that turns a str into bytes using a named encoding such as UTF-8, done at the boundary where text is written to a file or network.
- encoding Day 64
- The rulebook mapping characters to bytes and back. Python cannot infer it, because a file is only bytes. Naming it explicitly (`encoding="utf-8"`) is what makes the same code produce the same bytes on every machine.
- encoding (text) Day 121
- The byte-to-character mapping a file was written with -- UTF-8, latin-1 (ISO-8859-1), and others. read_csv()'s encoding argument defaults to UTF-8; reading a file written in a different encoding either raises UnicodeDecodeError on an invalid byte sequence or, worse, silently decodes into wrong characters ("mojibake") when the bytes happen to also be valid under the assumed encoding.
- encoding channel Day 127
- A visual property a chart uses to carry a number: position, length, angle, area, volume, colour saturation, hue, shape. Choosing which variable rides which channel is the whole craft of chart design; everything else is decoration.
- encryption Day 19
- Scrambling data with a key so that only someone with the right key can turn it back into readable form.
- End-to-End Classification Pipeline Day 161
- A cohesive software pipeline encapsulating data validation, feature preprocessing, model inference, and threshold calibration into a single deployable artifact.
- End-to-End Pipeline Day 196
- A unified engineering workflow connecting data ingestion, feature transformation, training, registration, serving, and monitoring.
- endianness Day 4
- The convention for which byte of a multi-byte number is stored first in memory: least-significant first (little-endian, x86 and most ARM) or most-significant first (big-endian, traditional in network protocols).
- endpoint Day 22
- A specific URL that a web API answers at, usually standing for one resource or operation, such as /todos/1 or /users/1.
- endpoint Day 23
- A specific addressable URL through which a client acts on a resource, such as /users/1.
- endpoint Day 28
- The URL a request is sent to, naming the specific resource or operation you want, like an address on an envelope.
- endpoint Day 82
- One callable address of your API — in FastAPI terms, a path operation: the pairing of one HTTP method with one path pattern and the function that answers it. `GET /bookmarks` and `POST /bookmarks` share a path and are two different endpoints.
- Engine Day 93
- The object that owns a database URL, a dialect and a connection pool. Created once per application with create_engine(), not once per request — it is a factory and a pool, not a connection. Passing echo=True makes it print every statement it sends, with parameters, which is the single best learning tool the library has and a disclosure risk in production.
- Ensemble Decorrelation Day 163
- The mathematical reduction of pairwise correlation rho among ensemble members, maximizing the variance reduction achievable through averaging.
- Ensembling Day 145
- Combining many models so their independent errors partly cancel. Bagging attacks the variance term by averaging high-variance models; boosting attacks the bias term by sequencing high-bias ones. Described here from documentation, not measured.
- ensure_ascii Day 65
- A json.dumps argument, defaulting to True, that escapes every non-ASCII character to a \\uXXXX sequence. Setting it to False writes the characters themselves, which is readable and perfectly safe when you are already writing UTF-8.
- Entity Day 70
- An object with an identity and a life cycle: it stays the same thing even after every one of its values changes. Identified by an identity field, compared on that field, and usually mutable — a Member, a Ledger.
- Entity Day 91
- A thing with an independent existence, which therefore deserves a table. The three-part test: does it exist before and after the row that mentions it, does it have facts of its own, and is it referred to by more than one row? An author passes all three.
- Entry point Day 83
- A declaration in a package's metadata that advertises an object under a named group, so that other software can discover it without importing the package first. Console scripts are the most familiar group; plugin systems use the same mechanism for their own groups.
- Entry point Day 84
- A name declared under [project.scripts] in pyproject.toml that becomes a command on your PATH when the package is installed. It matters for automation because a command name survives you reorganising your directories, while the absolute path in a schedule entry does not.
- enum Day 67
- A class defining a fixed set of named constant members. Its value is that an illegal member cannot be constructed at all, so a typo raises at the boundary instead of flowing quietly through the program.
- enumerate Day 51
- A built-in that pairs each item of an iterable with its position, so a for loop can read both index and value at once (for i, x in enumerate(items):), replacing the error-prone range(len(...)) pattern.
- Environment record Day 139
- A cell (or a companion file) that captures the interpreter version and the exact versions of the packages a notebook depends on at the moment it ran -- Day 126's reproducibility manifest applied inside a notebook, so a reader can tell whether a changed answer came from changed code or a changed environment.
- environment variable Day 11
- A named string value held by a running process and copied by the operating system to every child process it starts, used to pass configuration and secrets without editing code.
- Environment variable Day 97
- A key and a string value held by the operating system for a process and inherited by its children. The Twelve-Factor App argues configuration belongs here because it is set outside the code, per deployment, and is never committed. Its limits are equally real: the values are flat, so nesting has to be faked with prefixes; they are all strings, so every type problem applies; and there is no file to diff in review.
- ephemeral port Day 17
- A temporary high-numbered port (49152–65535) the operating system assigns to a client program for the outgoing side of a connection.
- Epoch Day 95
- A count of seconds since a fixed instant, conventionally 1970-01-01T00:00:00Z. Unambiguous by construction, since no zone, offset or wall clock appears in it, and unreadable by construction, since nobody spots that 1792891800 is a month wrong while scanning a log. Two limits are worth carrying: a signed 32-bit count runs out at 2038-01-19T03:14:07Z, and Python's timestamp() returns a float, so microseconds survive a round trip and nanoseconds do not.
- Epoch Day 201
- One complete pass through the entire training dataset during neural network training.
- Epsilon (eps) Day 184
- The maximum radius distance defining the neighborhood surrounding a given observation in DBSCAN.
- Epsilon-greedy Day 142
- A policy that takes the currently best-looking action with probability one minus epsilon and a uniformly random action otherwise. Crude, and hard to beat as a baseline: at epsilon 0.1 it more than doubles a greedy agent's optimal-action rate for a tenth of the budget.
- equal opportunity Day 138
- The criterion that both groups' genuinely-positive members be selected at the same rate -- equal true-positive rates. Enforcing it in this lesson's example drove that gap to 0.0000 while reopening the selection-rate gap to 0.1160 and the precision gap to 0.3012.
- Equal Opportunity Day 179
- A fairness criterion requiring the True Positive Rate (Recall) to be equal across all protected groups for favorable outcomes.
- equality vs identity (== vs is) Day 50
- `==` tests whether two values are equal; `is` tests whether two names refer to the same object in memory (identity). Use `is` only for `None`, `True`, and `False` (e.g. `if x is None:`), and `==` for ordinary value comparisons.
- Equalized Odds Day 179
- A fairness criterion requiring both True Positive Rate and False Positive Rate to be equal across all protected groups.
- Error analysis Day 143
- The stage that asks which cases fail and why, rather than how many. It is what decides what the next loop is for, and the aggregate score distinguishes none of the possible answers.
- Error Analysis Day 161
- The manual and automated diagnostic inspection of False Positives and False Negatives to uncover systematic failure modes and data quality defects.
- Error Analysis Day 203
- The practice of manually inspecting misclassified samples to diagnose dataset noise, label ambiguity, or model blind spots.
- Error by target level Day 154
- RMSE computed separately on the below-median and above-median halves of the true test targets, to check whether a model is systematically worse for higher-value cases -- a fairness-relevant question on a disease-progression score. Measured here as a ratio of 1.0473: only 4.73 percent worse on the more severe half.
- error code Day 75
- The bracketed identifier at the end of every mypy message — `[union-attr]`, `[arg-type]`, `[return-value]`, `[assignment]`, `[no-untyped-def]`. It is the stable, searchable, individually configurable identity of a check, it is what a `# type: ignore[code]` comment refers to, and it is what a test suite should assert on, because message wording changes between releases.
- error handling Day 28
- Checking whether a request actually succeeded and whether the expected field was present, so a failure produces a clear message instead of garbage or a crash.
- Error Reduction Ceiling Day 181
- The maximum possible percentage gain in overall accuracy if an error category is 100% eliminated.
- Error Residual (dZ) Day 200
- The partial derivative of the scalar loss with respect to the linear pre-activation tensor Z^[l].
- Error type Day 94
- A short machine-readable string naming the rule that was broken — missing, float_parsing, less_than_equal, extra_forbidden, string_pattern_mismatch, datetime_from_date_parsing, value_error, frozen_instance. Stable within a major version and intended to be branched on. Its counterpart msg is human prose, is free to be reworded in any release, and is therefore the one field nothing should ever assert on.
- errorbar (parameter) Day 129
- The seaborn keyword controlling which interval a statistical plot draws around its estimator. Accepts 'sd' (one standard deviation, a closed-form statistic), 'se' (standard error), or a tuple like ('ci', 95) or ('pi', 95) for a bootstrapped confidence or prediction interval at the given percentage. Only the tuple forms depend on the random bootstrap and therefore on seed=.
- escape hatch (matplotlib object API) Day 129
- The practice of calling matplotlib Axes and Figure methods directly (ax.set_ylabel, ax.set_ylim, fig.suptitle, and similar, from Day 128's object model) after a seaborn call has already drawn, to set anything seaborn's own arguments do not expose. Works because seaborn's return value -- an Axes for axes-level functions, a FacetGrid wrapping a Figure for figure-level ones -- is always a real matplotlib object underneath.
- escape sequence Day 45
- A backslash followed by a code that represents a single character hard to type directly, such as \n for a newline or \t for a tab.
- escaped quote Day 65
- A literal double quote inside a quoted CSV field, written as two consecutive double quotes. It is how the quoting mechanism escapes itself, and it is the case that keeps the right field count while still corrupting data under naive parsing.
- estimator Day 129
- The summary statistic a seaborn plotting function computes from raw observations before drawing -- by default the mean, for functions like barplot and pointplot. Passing estimator= changes which statistic (for example, "median" or a custom callable) is drawn instead.
- Estimator Day 117
- A rule for turning a sample into a number that estimates some property of the population -- the sample mean estimating the population mean, the sample proportion estimating the true rate. An estimator is itself a function of the random sample, which is exactly why it is a random variable with its own distribution.
- Estimator Day 146
- Any scikit-learn object that implements fit(). The base of the whole API -- measured here at 210 of 210 discovered estimators, every single one implementing fit, whatever else it does.
- ETag Day 134
- An opaque identifier a server attaches to a specific version of a resource, sent back by a client on the next request as If-None-Match so the server can answer with a cheap 304 rather than the full payload if the resource has not changed since.
- Ethical Considerations Day 182
- Discussion of potential societal risks, biases, surveillance concerns, and privacy safeguards.
- Euclidean distance Day 99
- The distance between two vectors, computed as the magnitude of their difference: subtract componentwise, then take the L2 norm of the result. There is no separate formula to memorise, and seeing that is the moment most of linear algebra stops looking like a list of things to learn. It is symmetric, it is zero only between a point and itself, and it obeys the triangle inequality.
- Euclidean distance Day 103
- The straight-line distance between two points: the length of their difference, from Pythagoras. Day 99's measure, and still the right one whenever magnitude is part of what you mean — physical positions, sizes, counts whose size you care about. It is the wrong one for text, because the length of a document is mostly a fact about the writer rather than about the subject, and Euclidean distance reads that length as if it were meaning.
- Euclidean Distance (L2 Norm) Day 157
- The straight-line distance between two points in Euclidean space: d(x, z) = sqrt(sum (x_i - z_i)^2).
- Euler-Mascheroni Constant Day 187
- A mathematical constant (approx 0.5772156649) used in BST expected path length normalization.
- Evaluation budget Day 144
- The number of times a held-out set may be consulted before its estimate stops being honest. One for a test set. Enforceable mechanically -- today's GatedTestSet refuses the second look and deliberately does not advance its counter on a refusal.
- Evaluative feedback Day 142
- Feedback that scores the action you actually took, and says nothing about the alternatives. This is what reinforcement learning receives. It is not weakened supervision but a different kind of information, and the difference has a measurable price: a bandit agent that never explores takes the best of ten actions 31.3 percent of the time against 70.8 for one that does.
- event Day 26
- A discrete thing that happened on a server (a payment succeeded, a job finished, code was pushed) that a webhook or event-driven system reports so others can react.
- Event Day 113
- A subset of the sample space — the set of outcomes for which something you care about is true. "The dice sum to 7" is the event {(1,6), (2,5), (3,4), (4,3), (5,2), (6,1)}, six of the 36 outcomes. An event is nothing more than a filtered set, built with a predicate over the sample space.
- event loop Day 20
- The mechanism by which the browser runs JavaScript one task at a time from a queue on the main thread, running each task to completion before updating the screen and taking the next.
- Event loop Day 96
- A scheduler: a single thread holding a queue of ready tasks and a set of suspended ones, which takes the front ready task, runs it until it suspends, parks it, and takes the next. When the operating system reports a socket ready, the loop moves the task waiting on it back to the ready queue. asyncio.run creates one, runs a coroutine to completion and closes it, and is the boundary between synchronous code and the loop.
- event-driven architecture Day 26
- A style of building systems in which services communicate by emitting and reacting to events (via webhooks, queues, or streams) rather than constantly asking one another for updates.
- Eventual consistency Day 92
- The guarantee that if writes stop, all replicas will converge on the same value — with no promise about when, and no promise that a read in the meantime sees the latest write. It is the practical shape of choosing availability during a partition, and it makes reconciliation a normal event: last-write-wins, a version vector, or a person deciding.
- Evidence (marginal likelihood) Day 115
- P(evidence), the overall probability of the observed evidence across every possible hypothesis, computed as the denominator of Bayes' theorem. This quantity is exactly Day 113's law of total probability applied to the partition of hypotheses and the event that was observed.
- exact duplicate Day 125
- A row that is identical to another row across every column, detected by DataFrame.duplicated() with no subset argument. The strictest possible definition of "the same row twice."
- Exact duplicate column Day 150
- Two identical columns in a design matrix. The normal equations cannot tell them apart, so any split of their combined coefficient fits equally well -- measured here as an even split, -0.545 and -0.545, summing to the original -1.09 to eight decimal places.
- exception Day 48
- A signal Python raises when it cannot carry out an instruction; it has a type that categorizes the problem and usually a message with the specifics, and it stops normal execution unless the program catches it.
- exception Day 66
- An object a piece of code raises to say it cannot do the job it was asked to do. Unlike a return code it travels outward on its own, so ignoring it takes effort rather than inattention.
- exception chaining Day 66
- Keeping the original exception attached when a new one is raised during the handling of it. Introduced by PEP 3134 in Python 3.0, it is the difference between a log line that explains a failure and one that wastes an afternoon.
- exception hierarchy Day 66
- The tree of built-in exception classes rooted at BaseException. It is not trivia: it is the mechanism by which an except clause decides whether to fire, and it lets you catch at exactly the width you can act on.
- excluded Day 88
- The special table qualifier available inside ON CONFLICT DO UPDATE, holding the values the INSERT was trying to write. Plain column names there mean the value already in the table, so copies = excluded.copies takes the new value while copies = copies keeps the old one. Getting it backwards parses, runs, reports success and does nothing.
- execute permission Day 9
- The permission (x) that, for a file, allows it to be run as a program, and for a directory, allows entering it and reaching items through it.
- executemany Day 90
- Compiling one statement once and stepping it once per row with new bindings each time. It is the tidy way to express a batch, and on the measurements in this lab it was worth about a factor of two — while wrapping the equivalent loop in a single transaction was worth about three orders of magnitude. Batching your writes matters far more than which method issues them.
- executescript Day 90
- The method that runs several statements from one string, used for schema scripts. Two properties make it dangerous with anything variable: it takes no parameters at all, so a value could only get in by being pasted into the string, and it issues an implicit COMMIT before it runs, so it can never be nested inside a transaction. In this lab it is what turns an injected DROP from a blocked attempt into a destroyed table.
- execution_count Day 139
- The integer nbformat stores on every executed code cell, recording the order in which the kernel processed it -- not the order the cell sits in the document. A monotonically increasing sequence (1, 2, 3, ...) top to bottom is what a notebook run cleanly from a fresh kernel produces; any other sequence is direct evidence the cells were run out of document order.
- Executor Day 96
- A pool of workers plus a queue, presented through one small interface: give me a callable, take back a future. concurrent.futures provides ThreadPoolExecutor and ProcessPoolExecutor behind the identical API, which is the module central insight — "run this over these inputs" is one problem whether the workers are threads or processes, so choosing between them should be a one-word edit rather than a rewrite.
- EXISTS versus IN versus a join Day 91
- Three ways to ask about a related table. Use a join when you need columns from the other table, and accept that it duplicates the left row once per match. Use EXISTS when you only need to know whether a row is there. Avoid NOT IN when the subquery can yield a NULL: x NOT IN (1, 2, NULL) is unknown rather than true, so the query silently returns nothing at all.
- exit code Day 7
- The number a process leaves behind when it terminates: 0 means success, other values signal failure, and 128 plus a signal number marks death by that signal (143 for SIGTERM, 137 for SIGKILL).
- exit code Day 12
- The integer a command returns when it finishes — `0` for success and non-zero for failure — which conditionals and loops branch on.
- exit code Day 47
- An integer a program returns to the shell when it ends; 0 means success and any non-zero value (set with sys.exit(1)) signals failure, letting scripts and pipelines detect problems.
- exit code Day 49
- A small integer a program returns to the operating system when it ends: 0 conventionally means success, and any non-zero value means an error occurred, so other programs can detect failure.
- exit code Day 56
- A small integer a program returns to the operating system when it ends: 0 conventionally means success and any non-zero value means failure, so scripts, pipelines, and schedulers can detect whether the program worked.
- Exit code Day 71
- The single small integer a process returns when it ends — the entire interface between a test suite and any automation. For pytest: 0 all passed, 1 something failed, 2 interrupted (including a collection error), 3 internal error, 4 wrong command-line usage, 5 no tests collected. A build step should succeed if and only if the code was 0.
- Exit code Day 77
- The number a program returns to whatever started it: zero means success, anything else means failure. It is the machine-readable half of a gate's answer — the part a hook, a build server or a merge button can act on without understanding a word of the human-readable output.
- Exit code Day 80
- The single number a program hands back to whatever launched it. Zero means success and anything else means failure. This is the mechanism `&&` in a shell and every scheduler and CI system reads — a tool that always exits 0 cannot be automated at all.
- Exit code Day 81
- The number a program returns, and the only thing the scheduler sees. Conventions worth reusing: 0 success, 1 an exception, 75 (EX_TEMPFAIL, from BSD sysexits.h) "already running, try later", and 124 (as GNU timeout uses) "killed for overrunning". An idempotent no-op exits 0, because a skipped run is a success.
- Exit code Day 84
- The number a process returns when it finishes: zero for success, anything else for a specific kind of failure. It is the machine-readable half of a run — the scheduler, the watchdog and any wrapping script read it and nothing else, so the vocabulary you choose for it is a real interface.
- Exit code Day 98
- The integer a process returns to whatever started it, and the only thing cron, launchd, systemd and every CI runner knows about your program. Zero conventionally means success and any non-zero value means something else; the choice of *which* non-zero value is yours, and using distinct codes for "could not run at all" and "ran, stored what it could, one source is dark" is what lets a scheduler react differently to the two.
- Expectation Day 114
- E[X], the probability-weighted average of a random variable's possible values: sum over k of k * P(X=k). It need not be a value the variable can actually take — a single fair die has E[X] = 3.5, and no face of a die ever shows 3.5.
- Expected Improvement (EI) Day 166
- An acquisition function that measures the expected magnitude of performance gain over the current best observed score, integrating over the surrogate posterior uncertainty.
- Expected maximum of K draws Day 144
- The quantity selection optimism actually equals, once expressed in standard errors. Simulated here at 0.55, 1.54, 2.50 and 3.24 standard errors for K = 2, 10, 100 and 1000, tracking the measurement to within 0.2 at every K.
- Expected Value Framework Day 176
- The business decision rule computing total expected profit or cost by weighting confusion matrix rates by their financial values.
- EXPLAIN QUERY PLAN Day 89
- The command that prints how SQLite intends to answer a statement, without running it. It costs nothing, changes nothing, and is the only honest way to find out whether an index is being used. Run it before optimising anything and again afterwards. Its output is a human-readable description rather than an interface, so the exact wording may differ between SQLite versions.
- Explained Variance Ratio (EVR) Day 185
- The percentage of total dataset variance accounted for by an individual principal component.
- Exploding gradient Day 110
- The mirror image: a product of many local rates above 1 growing without bound. Fifty factors of 1.1 give about 117 and two hundred give about 1.9e+8. Nothing raises an exception on the way; a large enough product silently becomes inf, after which one more operation turns every parameter into nan.
- Exploding Gradients Day 209
- A condition where gradients grow exponentially during backpropagation, causing weights to overflow to NaN or Infinity.
- Exploration-exploitation trade-off Day 142
- The tension between taking the action that currently looks best and taking one that would tell you more. It exists only under evaluative feedback -- a supervised learner is handed every label whether it asked for the example or not.
- Exploratory data analysis (EDA) Day 136
- The discipline of looking at data to generate questions and hypotheses, as distinct from confirmatory data analysis, which tests a hypothesis already decided in advance. Named and formalized by John Tukey in his 1977 book of the same title.
- exponent Day 4
- The field of a floating-point number that scales the mantissa by a power of two, controlling range; when it cannot hold a needed power, the number overflows.
- exponent Day 46
- The field of a floating-point number that sets the scale — which power of two the mantissa is multiplied by; a 64-bit double has 11 exponent bits, which set its range.
- exponential backoff Day 27
- A retry strategy that waits a delay which doubles after each failed attempt (1s, 2s, 4s, ...) up to a cap, giving an overloaded server room to recover.
- Exponential backoff Day 78
- Doubling the wait between successive retries — 0.5s, 1s, 2s, 4s, 8s — usually with a cap, so that a client which is failing repeatedly asks progressively less often instead of hammering. The alternative, a fixed short delay, is indistinguishable from an attack when a service is already struggling.
- Exponential backoff Day 98
- Waiting longer between each successive retry, usually by doubling — 50 milliseconds, then 100, then 200. It exists because a service that just failed is often a service under load, and a client that retries immediately three times is three times the load at the worst possible moment. In production, add jitter so that a fleet of clients does not retry in lockstep, and honour Retry-After when the server sends one.
- Exponential distribution Day 114
- The distribution of the waiting time between events in a Poisson process with rate lambda. Mean 1/lambda, variance 1/lambda^2. Sampled from a single uniform draw U as -ln(U) / lambda, the inverse-CDF method applied to its own cdf, F(x) = 1 - exp(-lambda*x).
- export Day 11
- A shell keyword that marks a variable to be included in the environment, so that child processes started afterward inherit a copy of its value.
- Expression index Day 89
- An index built on an expression rather than a bare column, such as lower(trace_id). It stores the computed value and sorts that, which is what rescues a query whose WHERE clause wraps the column in a function. The expression in the query must match the one in the index; an index on lower() does nothing for a query using upper().
- Expression index Day 92
- An index built on the result of an expression rather than on a bare column — for example on json_extract(body, '$.shelf'). It is what makes querying inside a JSON document fast, and it matches the exact expression it indexes rather than the question being asked: the same filter written with the ->> operator will not use it. Confirm it applied by reading EXPLAIN QUERY PLAN for SEARCH rather than SCAN.
- extending Day 68
- Overriding a method but still calling the original through `super()`, so both run. The distinction from plain overriding is the difference between replacing a behaviour and adding to it.
- extension Day 36
- An add-on that expands a code editor with new capabilities — support for a language, a theme, a tool — installed and managed from the editor.
- extra forbid Day 82
- The pydantic model setting `ConfigDict(extra="forbid")`, which turns an undeclared field into a 422 instead of silently ignoring it. It catches the misspelled `titel` that would otherwise waste an afternoon, and it is a security control: a client attempting to supply its own `id` is refused with `"type": "extra_forbidden"`.
- extra="forbid" Day 94
- The model_config setting that turns an unexpected key from a silent discard into a refusal of type extra_forbidden. It is what catches a misspelled field name, which the default extra="ignore" loses without a sound. It is also a security control: whether an unexpected key is ignored or forbidden decides whether a model built from user-supplied data can be mass-assigned a field the user should not control.
- Extrapolation Limit Day 163
- The inherent property of tree-based models where predictions are bounded by the range of observed training target values, preventing linear trend extrapolation.
- Extras Day 83
- Named optional dependency groups, declared under `[project.optional-dependencies]` and installed with bracket syntax: `pip install "wordtally-tools[dev]"`. In the built metadata they appear as `Provides-Extra` plus `Requires-Dist` lines conditional on the extra, so a plain install genuinely skips them. Typical uses are development tooling, optional backends, and heavy dependencies most users do not want.
- f-string Day 45
- A string literal prefixed with f whose {...} braces embed expressions evaluated at run time, the modern default for formatting (added in Python 3.6 via PEP 498).
- f-string Day 47
- A formatted string literal, prefixed with f, in which any expression inside curly braces is evaluated and substituted into the text when the program runs; introduced in Python 3.6.
- F1 Score Day 159
- The harmonic mean of precision and recall: F1 = 2 * (Precision * Recall) / (Precision + Recall).
- FacetGrid Day 129
- The object every figure-level seaborn function returns. It owns a matplotlib Figure and an array of Axes (grid.axes), one per combination of the col= and row= categories requested, plus convenience methods for labeling and adjusting every panel at once.
- fail fast Day 41
- Stopping a pipeline the moment a stage fails, so no later stage runs on a known-bad input and the failure is reported immediately.
- fail fast Day 66
- Validating at the boundary and stopping immediately when the program cannot do its job. A malformed input that reaches the middle of a program has already cost you the ability to report it clearly.
- Fail-fast Day 77
- Stopping a gate at the first failing stage instead of running the rest. Right when the feedback loop is tight and the cost of a wasted run is your own patience — a local run, a pre-commit hook. Its opposite, running everything and reporting all failures, is right in continuous integration, where a run is expensive to trigger and nobody is watching it.
- fairness impossibility Day 138
- The result that demographic parity, equal true-positive rates and equal precision cannot generally all hold at once when two groups have different base rates. Established independently in the mid-2010s and reproducible by hand on a twenty-number table. Choosing among the criteria is consequently unavoidable, and it is a value judgement about what a system is for and who bears the cost of a wrong decision -- not something a library default can settle.
- Fake Day 74
- A real, working implementation, simplified: an in-memory repository instead of a database, a dictionary instead of a filesystem, a scripted client instead of a service. A fake answers the stub, spy and mock questions at once, in code a reader can understand without knowing a mocking library.
- Fake it till you make it Day 73
- Returning a constant or otherwise obviously insufficient code to reach green quickly, and generalising under the pressure of the next test. Its honest purpose is to separate "is my test wired up?" from "what is the algorithm?" so that a hard algorithm is debugged alone.
- Fallback Heuristic Day 194
- A deterministic business rule executed when a primary ML model fails or exceeds its operational latency timeout.
- False negative, in this domain Day 147
- A malignant case predicted benign -- the costlier of the two possible mistakes in cancer screening, because it delays treatment rather than triggering an unnecessary follow-up. This lesson's model makes two of them and zero of the other kind.
- False positive Day 76
- A finding that is correct as a general rule and wrong for this particular code. False positives are unavoidable — a tool that is never wrong about anything is checking nothing interesting — and they are why suppression comments exist. The failure mode is not having them; it is leaving them on the screen undecided until the whole report becomes scenery.
- False Positive Rate (FPR) Day 159
- The proportion of actual negative instances that were incorrectly classified as positive: FPR = FP / (TN + FP) = 1 - Specificity.
- Family-wise error rate (FWER) Day 136
- The probability of at least one false positive across an entire family of comparisons, as opposed to the per-comparison error rate (alpha) of any single one. This is the rate a multiple-comparisons correction is designed to control.
- Fan-out Day 89
- How many children a node of a B-tree has — with a 4,096-byte page and small integer keys, roughly a hundred. Fan-out is why depth grows so slowly: one level reaches about 100 entries, two about 10,000, three about a million. A hundredfold increase in rows adds one page read to a seek.
- Fancy indexing Day 100
- Selecting entries with a list of positions or a boolean mask, as in M[[0, 2]] or M[M > 3], rather than with slices. It always produces a copy, because the selection cannot be described as a stride pattern over the original memory. Worth knowing precisely because basic slicing with colons does the opposite, and the two look similar on the page.
- Fancy indexing Day 104
- Indexing with an array of positions rather than with a slice or a mask, as in readings[[0, 5, 19, 5]]. Three properties distinguish it: the result takes the shape of the index array rather than the source, the order is whatever you asked for, and the same element may be requested more than once. It always returns a copy, because arbitrary positions cannot be described by a stride. It is how a batch of rows is pulled out of a dataset, and how an argsort result is turned into an answer.
- fast-forward Day 31
- A merge in which the target branch has not advanced since the split, so Git simply slides its pointer forward to the other branch tip — no merge commit is created and history stays linear.
- FastAPI Day 194
- An asynchronous Python web framework optimized for building high-performance REST APIs with automatic Pydantic validation.
- feature Day 137
- A number given to a model, computed from data you have. Every feature encodes a hypothesis about what matters: writing spend divided by income asserts that the proportion of income being spent is the thing that carries signal, and that the same ratio means the same thing at every income level. A feature is not a column; it is a column plus a fitting procedure, because "standardised order value" is undefined until you say whose mean and whose standard deviation.
- Feature Ablation Study Day 175
- Systematically removing features from a model to measure their isolated marginal impact on validation performance.
- feature branch Day 31
- A short-lived branch created to hold one distinct piece of work — a feature, fix, or experiment — kept isolated from main until it is ready to merge and then deleted.
- feature cost Day 137
- The requirement that a feature be computable at prediction time, from data that exists then, at acceptable expense. All three clauses bite independently: a lifetime average is not computable before a customer's first order, a nightly table is not current enough for a live request, and a 200-millisecond aggregation is unavailable to a 50-millisecond budget. This is a systems constraint as much as a statistical one.
- Feature Drift Day 175
- The statistical shift in the distribution of an input feature over time due to real-world behavioral or environmental changes.
- Feature Engineering Day 171
- The process of using domain knowledge to extract, transform, and create new input variables from raw data to enhance machine learning model performance.
- Feature Flattening Day 203
- Transforming a multi-dimensional spatial grid (e.g., 28x28 pixels) into a 1D vector of length 784.
- Feature ROI Day 175
- The ratio of predictive metric improvement (e.g. R2 / ROC-AUC gain) to computational inference latency and engineering maintenance cost.
- Feature scaling Day 150
- Rescaling predictors, most commonly to zero mean and unit variance, before fitting. Changes every ordinary-least-squares coefficient's magnitude -- measured here by a factor above thirty for one predictor -- while leaving every prediction and R2 unchanged to eleven decimal places.
- Feature Scaling Day 170
- The process of normalizing or standardizing the range of independent variables to ensure uniform contribution across distance metrics and optimization routines.
- Feature Selection Day 172
- The process of selecting a subset of relevant features for use in model construction to reduce overfitting and improve efficiency.
- Feature selection (as a side effect of fitting) Day 151
- What lasso does that ridge does not: driving some coefficients to exactly zero as part of a single convex optimization, rather than as a separate discrete search step the way stepwise selection works.
- Feature standardization Day 153
- Rescaling every column to zero mean and unit standard deviation before fitting. Not required for the closed form, which is invariant to scale, but measured here to shrink the Hessian eigenvalue ratio from 76278.96 to 470.08 and make gradient descent converge in thousands of iterations rather than hundreds of thousands.
- Feature store Day 92
- A key-value store with time semantics: the key is an entity, the value is its features, and the extra requirement is "as of when". The time dimension exists to prevent training a model on values that were not yet known at prediction time, which produces a model that evaluates beautifully and fails in production.
- Feature Store Day 171
- A centralized operational data management layer that curates, stores, and serves standardized feature definitions across training and production.
- Feature Store Day 175
- A centralized data infrastructure layer that manages, version-controls, and serves standardized features across training and real-time production.
- Feature Timestamp Audit Day 180
- A governance check confirming the creation timestamp of every feature strictly precedes the prediction trigger event.
- FeatureUnion Day 173
- A composite transformer that applies multiple transformers to the same input matrix in parallel and horizontally concatenates all generated features.
- Feedback Delay Day 195
- The time lag between when a model prediction is emitted and when the true ground-truth outcome is recorded.
- fetch Day 32
- The command that downloads new commits from a remote and updates the remote-tracking branches, without changing your working branch or files.
- ffill / bfill Day 125
- Forward-fill and backward-fill: carry the nearest earlier (ffill) or later (bfill) non-missing value forward or backward to fill a gap. Correct only when the DataFrame's row order is the order that matters (typically chronological); run on unsorted data, ffill carries a value across rows that were never actually adjacent, producing a wrong answer with no error raised.
- Field validator Day 94
- A function attached to one field with @field_validator("name"), running either before pydantic's own parsing (mode="before", where the value is still whatever arrived) or after it (mode="after", where the value is already the declared type). It raises a plain ValueError, which pydantic folds into the ValidationError as an entry of type value_error located at that field.
- field() Day 69
- The `dataclasses` function that specifies one field in more detail than a bare default allows — supplying `default_factory`, or setting `init=False`, `repr=False`, and similar per-field options.
- Figure Day 128
- The whole canvas matplotlib draws on -- the object you save to a file with savefig, and the top of the object model. A Figure holds one or more Axes; it owns nothing about what gets plotted, only where the Axes sit and at what overall size and resolution the canvas gets rendered.
- figure lifecycle Day 128
- The fact that every Figure created through pyplot (plt.figure(), plt.subplots()) is retained in a global registry until plt.close(fig) or plt.close('all') removes it -- it does not get garbage-collected just because the variable holding it goes out of scope. A function that plots in a loop and returns without closing leaks one figure per call; matplotlib issues its own RuntimeWarning once more than 20 figures are open at once (rcParams figure.max_open_warning).
- figure-level function Day 129
- A seaborn plotting function (relplot, displot, catplot, lmplot) that always creates and owns its own matplotlib Figure -- it does not accept ax= -- and returns a FacetGrid wrapping that Figure. Figure-level functions are how seaborn builds multi-panel facet grids; their return value is not a plain Axes, which is why matplotlib calls that expect an Axes (like some uses of plt.title) behave differently after one.
- file Day 39
- A named blob of bytes stored on disk and organized by a filesystem into folders; the simplest storage shape, ideal when data is read far more than written and by one program at a time.
- file Day 64
- A named sequence of bytes that lives on a disk and survives the program that wrote it. A file has no built-in notion of lines, records, or columns — any structure beyond "bytes in a row with a name" is a convention that programs agree to read into and out of those bytes.
- file descriptor Day 6
- The small integer the kernel returns when a program opens a file — a ticket the program hands back on every subsequent read or write, while the kernel keeps the real bookkeeping.
- file descriptor Day 64
- The small integer the operating system kernel uses as a handle to an open file. It comes from the Unix design of the early 1970s, and Python still exposes it: `handle.fileno()` returns the descriptor that `os.fsync()` needs.
- file object Day 64
- The object `open()` returns. It knows which file it is attached to, what you are allowed to do with it, how to translate between characters and bytes, and where the cursor currently sits. It also holds a buffer of bytes not yet handed to the operating system.
- filesystem Day 6
- The OS subsystem that organizes raw disk blocks into named files, folders, timestamps, and permissions — the human-usable fiction layered over storage hardware.
- filesystem Day 39
- The part of an operating system that organizes a disk into named files inside a tree of folders and tracks where each file's bytes physically live.
- fillna Day 125
- The pandas method that replaces missing values with a supplied constant, a forward/backward fill, or an interpolated value. Every choice of fill value is a claim about what the missing data would have been, and that claim should be stated, not assumed.
- filter Day 10
- A program that reads a text stream, transforms it, and writes a text stream — such as grep, sed, sort, uniq, cut, or wc — the building block of a pipeline.
- Filter Day 97
- An object with one method that returns True to keep a record and False to drop it, and which is explicitly allowed to EDIT the record on the way through. That permission is what makes redaction possible. Filters can be attached to loggers and to handlers, and the two are not equivalent: a logger's filters run only for calls made on that logger object.
- Filter Method Day 172
- A model-agnostic feature selection approach that evaluates individual feature properties (variance, correlation, mutual information) independently.
- Final Day 75
- An annotation declaring that a name is never rebound after its first assignment. Assigning to it again is reported as an error, which makes a module-level constant genuinely constant as far as any reader or tool is concerned.
- finally block Day 66
- The part of a try statement that runs on every path out — normal completion, a handled exception, an exception travelling through, a break, or a return. It is the only construct that makes that promise, and the "with" statement is built on it.
- Finding Day 140
- A single, actionable statement of what is wrong and where -- "SOURCE.json is missing: checksum_sha256", not "provenance incomplete". A verdict is a list of findings, which makes it a task list rather than a grade.
- fit_intercept Day 148
- A `LinearRegression` argument that, when set to False, forces the fitted line through the origin. Measured to cost 59 percent worse RMSE and a biased slope on data whose true intercept was 25.0 and whose predictor values never approached zero.
- fit_intercept by centring Day 153
- Computing an intercept by subtracting each column's mean before fitting and recovering it afterwards as y.mean() minus X.mean(axis=0) dotted with the coefficients, rather than appending a column of ones to the design matrix. Measured here to agree with the column-append approach to within 1.9554e-11 on coefficients and 2.8422e-14 on the intercept.
- fit() Day 146
- The method that reads hyper-parameters and training data and stores everything learned as attributes ending in a trailing underscore. The only estimator method permitted to add such attributes, and conventionally returns self for chaining.
- fit/transform split Day 137
- Writing every fitted statistic as two operations: fit, which looks at rows and learns numbers, and transform, which applies numbers already learned and looks at nothing. Once they are separate, the question of which rows influenced a feature is answerable by reading the call site instead of guessing. This is what scikit-learn's Pipeline exists to enforce.
- five-number summary Day 130
- The minimum, first quartile (Q1), median, third quartile (Q3), and maximum of a sample -- the entire content a standard boxplot draws. Two samples can share an identical five-number summary while having completely different shapes; the five-number summary alone cannot tell a unimodal distribution from a bimodal one, or reveal outliers a whisker rule would otherwise flag.
- Fixture Day 71
- A named piece of prepared state that a test asks for by declaring a parameter of that name; pytest looks it up — usually in `conftest.py` — calls it, and hands the result over. A parameter that is a request rather than a value. The full subject of Day 72.
- Fixture Day 72
- A function decorated with @pytest.fixture that produces something a test needs. It is the arrange step, extracted and given a name; a test uses it by writing that name as one of its parameters. Fixtures compose — one can request another — and only the tests that ask for a fixture pay for it.
- Fixture scope Day 72
- How often a fixture body actually runs: function (once per test, the default), class (once per test class), module (once per test file), or session (once per pytest run). Scope is not documentation but an observable count, and the rule for widening it is mutability, not speed.
- Fixture server Day 98
- A small HTTP server run locally that stands in for a real API during development and testing. Binding 127.0.0.1 on port 0 lets the kernel pick a free port, which avoids collisions with whatever else is running. Its real value is that it can be hostile on demand — failing twice and then recovering, failing permanently, echoing your token back inside an error body — which a real API will do eventually and never when you are watching.
- flag Day 8
- An option on a command line, usually starting with `-` or `--`, that changes how a command behaves — for example `-l` in `ls -l`.
- Flag Day 80
- An option that takes no value and simply turns something on, such as `--dry-run` or `-v`. Declared with `action="store_true"`, so its presence means True and its absence means False.
- flags Day 2
- Single bits set by the ALU recording facts about the last result — such as "it was zero" or "it was negative" — that later instructions can test to make decisions.
- Flaky test Day 71
- A test that gives different answers on the same code, usually because it depends on the clock, a random value, the network, the machine's speed, or the order tests ran in. Worse than no test, because it trains everyone to re-run the suite instead of reading it — including on the day the failure is real.
- Flaky test Day 74
- A test that passes and fails on unchanged code. It is uniquely corrosive because it makes the correct response to a red build — stop and investigate — irrational: people rerun, then ignore, and eventually ignore a real failure too. A single unreliable dependency reached through a test is enough to start that spiral.
- Flaky test Day 77
- A test that passes and fails on the same code, usually because it depends on a real clock, a real network call, a shared file, or the order the suite happens to run in. Worse than a missing test, because it teaches everyone that a red build might mean nothing. The discipline is to fix it or delete it — never to retry it.
- float Day 44
- The floating-point type: real numbers with a fractional part, such as 3.14 and 2.0. Immutable, and distinct from int even when the value looks whole.
- float Day 46
- Python's floating-point type: a number with a decimal point stored in 64 bits as an IEEE 754 double, fast and wide-ranging but limited to about 15 to 17 significant digits of precision.
- floating point Day 4
- Binary scientific notation for storing fractional numbers as a sign, a mantissa, and an exponent, standardized by IEEE 754 in 1985; it trades exactness for enormous range.
- floating-point error Day 46
- The small, deterministic rounding difference that arises because most decimal fractions (like 0.1) have no exact representation in binary and must be stored as the nearest available value.
- floor division Day 46
- The // operator, which divides two numbers and rounds the result down to a whole number (toward negative infinity); 7 // 2 is 3.
- flow control Day 17
- A TCP mechanism where the receiver advertises how much data it can accept, so a fast sender does not overwhelm a slow receiver.
- flush Day 47
- To force buffered output to be written out immediately rather than held for efficiency; print(..., flush=True) makes text appear the instant it is produced, as in a live progress display.
- flush Day 64
- The call that pushes Python's own buffer out to the operating system. After it, every other program can see the new bytes — but they are still only in RAM, in the page cache, and a power cut still loses them.
- Flush Day 93
- Sending the Session's pending INSERT, UPDATE and DELETE statements to the database, inside the open transaction. After a flush the SQL has been executed and the database has assigned any generated keys — and no other connection can see any of it, because the transaction has not ended.
- Focal Loss Day 160
- A dynamically scaled cross-entropy loss function that down-weights easy majority examples to focus gradient optimization on hard minority examples.
- Fold Day 95
- The single-bit datetime attribute, added in Python 3.6 through PEP 495, that disambiguates a wall-clock reading which occurs twice. fold=0 means the earlier of the two instants and fold=1 the later. On a nonexistent reading it selects instead between the offset in force before the gap and the one after it. It is ignored when two aware datetimes with the same tzinfo are compared, which is documented and is the source of a memorable class of bug.
- for loop Day 51
- A loop that visits each item produced by an iterable exactly once and stops on its own when the items run out; the tool for definite iteration over a known collection.
- force push Day 34
- git push --force: overwriting the remote branch with your local history, used after rewriting history. It can destroy teammates' commits; git push --force-with-lease is a safer variant that refuses to overwrite work you have not seen.
- Foreign key Day 85
- A column declared to REFERENCES a key in another table, so the engine refuses a row pointing at something that does not exist. In SQLite it is enforced only when PRAGMA foreign_keys is ON, which is OFF by default, per connection — so a REFERENCES clause on a connection that has not asked for it enforces nothing.
- Foreign key Day 87
- A column whose values are required to appear as a primary key in another table. It promises that every non-NULL value here exists as a parent row, that you cannot insert a child pointing at a missing parent, and that deleting a parent with children follows whatever the schema says. It does not create an index, does not perform the join, and — in SQLite — does not enforce anything until PRAGMA foreign_keys is switched on.
- fork Day 32
- Your own server-side copy of someone else's repository on a hosting platform, which you can push to freely and use to propose changes back to the original.
- Forking paths Day 136
- The set of all the different analyses -- different subsets, outcome definitions, cutoffs and transformations -- an analyst could plausibly have run on a given dataset. Coined by Andrew Gelman and Eric Loken (2013) to describe how the reported result is one path among many, chosen because it looked good, even when no formal test was declared for the paths not taken.
- format spec Day 45
- The part of an f-string field after the colon that controls display, such as :.2f for two decimal places or :>10 to right-align in a 10-character field.
- format spec Day 47
- The mini-language written after a colon inside an f-string field, such as >10.2f, controlling fill, alignment, sign, width, thousands separator, precision, and type of the formatted value.
- formatter Day 37
- A tool that rewrites code's layout — indentation, spacing, line breaks, quote style — into one consistent style while leaving behavior unchanged; running it twice changes nothing the second time.
- formatter Day 61
- A tool that automatically rewrites code into a consistent layout — indentation, spacing, quote style, line wrapping — so style is machine-applied rather than argued over. Black is the widely used Python formatter; it is deliberately opinionated and has few options.
- Formatter Day 76
- A program that rewrites your source into a canonical layout — quotes, whitespace, line breaks. It parses the code into a tree, discards your whitespace, and prints the tree back out by fixed rules, which is why it is trustworthy: it re-prints structure rather than editing text. It changes how code looks and never what it does.
- Formatter Day 97
- The object that turns a LogRecord into text. It belongs to a handler rather than to a logger, which is why the same records can appear as a friendly console line and as a JSON object at the same moment with no change to any call site. It is also where the traceback is rendered — after every filter has already run, which is why a secret inside an exception message survives redaction.
- Forward difference Day 108
- The estimate (f(x + h) − f(x)) ÷ h: the definition of the derivative with a finite h substituted for the limit. Its truncation error is proportional to h, so halving the step roughly halves the error. It needs two function values, one of which is usually f(x) itself, so where f(x) is already known it costs one extra evaluation — which is why it survives despite being much less accurate than the central difference.
- Forward mapping Day 105
- Transforming an image by walking the INPUT: for each input pixel, work out where it lands and write its value there. It reads like the definition of a transformation, and it does not work. Because the loop runs over the input, nothing guarantees every output pixel is visited — a 30 degree rotation of the 9 by 9 test picture leaves 22 of 81 output pixels never written, including pixels punched through solid ink, and doubling leaves at least 243 of 324 unwritten as a matter of counting. Shrinking leaves no holes but overwrites instead, so which value survives is decided by loop order.
- Forward pass Day 101
- Computing a network output from its input by running the data through each layer in turn. One layer of it is X @ W + b: a matrix multiply and a vector add, with the bias broadcast across the rows of the batch. This is not a simplification for teaching — it is the actual operation, and it is where essentially all the compute in training goes.
- Forward pass Day 110
- Running a computation from inputs to output, computing and storing every intermediate value. The stored values are not optional bookkeeping: the local derivatives are written in terms of them, so a backward pass cannot run without them.
- Forward Propagation Day 199
- The computational pass that feeds input features through successive layers of linear transformations and non-linear activations to produce predictions and calculate loss.
- Forward-mode differentiation Day 110
- Applying the chain rule from the inputs forwards, carrying each value alongside its derivative with respect to one chosen input. It needs no graph and no second pass, but answers about one input per run — so a function of n inputs costs n runs. It wins in the opposite shape from reverse mode: one input, many outputs.
- Fraction Day 46
- A standard-library type (from the fractions module) that stores a number as an exact ratio of two integers, so values like one third stay exact through arithmetic.
- fractions.Fraction Day 113
- Python's standard-library exact-rational-number type, used throughout this lesson so that probability comparisons are exact rather than approximate. Fraction(1, 6) == 6/36 evaluates True exactly; the equivalent float comparison 1/6 == 6/36 can fail to be exact due to floating-point rounding, which is precisely the noise Fraction exists to eliminate.
- fragile base class problem Day 68
- The failure mode where a seemingly safe change to a base class breaks subclasses written by people who never read it, because subclasses depend on the parent's internal behaviour rather than only its public surface. Named as class libraries grew in the 1990s, and the main reason composition is the default advice.
- frame Day 66
- One function call's private workspace: its local variables and where it is in the code. When no handler in a frame matches, the interpreter records the frame in the traceback and abandons it.
- Frame Day 147
- Stating what is being predicted, from what, and what beating it would even mean, before any code is written. The first stage of this lesson's protocol, and the one skipped most often in practice.
- Framing stage Day 143
- The stage that produces the target, the metric and the baseline to beat, before any model exists. The only stage whose omission has no error message, which is why it is the one most often skipped.
- free tier Day 28
- A level of an API that costs nothing to use within stated limits; free public APIs like Open-Meteo make them ideal for learning without a bill.
- Free-threaded build Day 96
- An optional CPython build, available from Python 3.13 following PEP 703, in which the global interpreter lock is disabled so threads can execute Python bytecode in parallel. It is a build-time option rather than a runtime flag, and it is not the default. Check which one you have with sysconfig.get_config_var("Py_GIL_DISABLED"): 0 means the lock is present. Every measurement in this lesson was made on a build reporting 0, and says so.
- Freedman-Diaconis rule Day 130
- A bin-width rule based on the interquartile range (IQR) rather than the standard deviation, choosing a width proportional to 2 * IQR * n^(-1/3). Because the IQR is a robust statistic (Day 116), this rule resists distortion by outliers and skew in a way Sturges' and Scott's rules do not, which is why it recovers structure the other two rules can wash out.
- from-import Day 59
- The `from module import name` form, which reaches inside a module and binds just the chosen name, so you can use it directly — `from stats import top_n` lets you call top_n(...) without the module prefix.
- frozen dataclass Day 69
- A dataclass declared `frozen=True`, whose generated `__setattr__` raises `FrozenInstanceError` on assignment. Because the field values can then never change, a generated `__hash__` can never go stale — which is what makes frozen instances usable as dictionary keys and set members.
- frozenset Day 54
- An immutable set. Because it cannot change, it is hashable and can therefore be a member of another set or a dictionary key, unlike an ordinary mutable set.
- fsync Day 64
- `os.fsync(handle.fileno())` — the call that forces bytes from the operating system page cache onto the physical disk. It is the only step that makes data genuinely durable, and it is slow enough that you reserve it for checkpoints and record stores rather than ordinary output.
- Full table scan Day 85
- Reading every row to answer a query, because no index applies. Its cost grows with the size of the table whether one row matches or all of them do. Writing restrict() by hand in the lab makes this concrete: the predicate is called once per row, always. EXPLAIN QUERY PLAN reports it as SCAN.
- function Day 12
- A named, reusable group of commands defined with `name() { ... }` and called like any command; inside it, `$1` and `$2` are the arguments passed to the function.
- function Day 49
- A named, reusable unit of code that does one job, defined in Python with `def`; it has its own local variables and can return a value, which makes it testable in isolation.
- function Day 57
- A named, reusable piece of a program that takes zero or more inputs, performs one job, and hands back a result; the fundamental unit of code organisation in Python and most languages.
- functional core / imperative shell Day 63
- A way of structuring a program so that all pure logic (values in, values out, no side effects) forms a testable core, while all input/output — files, arguments, printing, the network — is pushed to a thin outer shell. The name was popularised by Gary Bernhardt in 2012.
- Functional Gradient Descent Day 164
- The optimization paradigm of taking gradient steps in the infinite-dimensional space of functions, rather than optimizing a fixed parameter vector in Euclidean space.
- FunctionTransformer Day 173
- A scikit-learn wrapper converting stateless Python functions into transformer objects compatible with Pipelines.
- Fundamental Theorem of Applied ML Day 175
- The principle that data quality and representation richness bound model performance far more than algorithmic complexity.
- Future Day 96
- A placeholder for a result that is not available yet, together with the machinery to wait for it and to carry an exception if the work failed. It is what an executor hands back from submit, and what a task is built on in asyncio. The practical consequence worth remembering: a worker exception is stored in its future rather than raised at submission time, so a map whose results you never consume can hide a failure completely.
- Fuzzy Simplicial Set Day 186
- A topological representation of data used by UMAP to model local metric spaces and fuzzy neighborhood connectivity.
- Gambler's fallacy Day 113
- The mistaken belief that an independent random process is "due" for a particular outcome after a streak — for example, believing tails is more likely after five heads in a row on a fair coin. The coin has no memory; the probability of tails on the next flip remains exactly 0.5 regardless of the preceding streak, because independence means the past streak carries zero information about the next flip.
- Gate Day 140
- One check in an acceptance harness, guarding one seam. A gate returns a result that is either a pass with no findings, or a failure with at least one finding that names a file, field, step or sentence. A failing gate with nothing to say is treated as a bug in the gate.
- Gated Test Evaluation Day 161
- A software design pattern that restricts test set evaluation to a single execution to prevent iterative overfitting to the test split.
- GatedTestSet Day 147
- An object that wraps the held-out test rows and permits exactly one call to evaluate, raising TestSetTouchedTwice on any further attempt without advancing its own counter. The discipline from Day 144, made mechanical again on a real dataset.
- GatedTestSet Day 154
- An object that wraps the held-out test rows and permits exactly one call to evaluate, raising TestSetTouchedTwice on any further attempt without advancing its own counter. The discipline from Day 144 and Day 147, made mechanical again on a regression problem.
- gauge Day 40
- A metric that can rise and fall over time, such as current memory in use or the length of a queue right now.
- Gauss-Markov theorem Day 149
- Under linearity, unbiasedness of the errors, constant error variance and no correlation between errors, ordinary least squares is the best linear unbiased estimator -- lowest variance among estimators that are linear in y and unbiased. Every qualifying word is load-bearing; the guarantee is conditional on those assumptions, not universal.
- Gaussian Error Linear Unit (GeLU) Day 198
- A smooth non-monotonic activation function weighting inputs by the standard Gaussian cumulative distribution function.
- Gaussian Naive Bayes Day 158
- A Naive Bayes variant for continuous real-valued features, assuming features within each class follow independent normal distributions.
- Generalisation Day 141
- Performance on data the model has never seen, drawn from the same source as its training data. It is the entire product of machine learning. Performance on data the model has already seen is free, can always be made perfect by a large enough model, and is evidence of nothing.
- Generalisation gap Day 141
- The difference between a model's score on its training data and its score on unseen data. Measured in this lesson at 0.040 for a full-depth tree on iris and 0.3465 for the same model type on data with 20 percent of labels flipped -- identical training scores of 1.000 in both cases, which is why the gap rather than the training score is the informative number.
- Generalisation gap Day 145
- Test error minus training error. The only part of the decomposition computable from a single fit, which makes it the practical diagnostic -- and its SIGN is what distinguishes the two failures.
- Generalization Gap Day 177
- The numerical difference between validation loss and training loss.
- Generalization Gap Day 210
- The performance difference between training metric and validation metric, indicating the degree of overfitting.
- Generated column Day 88
- A column defined by an expression over the other columns of the same row, added in SQLite 3.31.0. VIRTUAL computes on read, STORED computes on write. It cannot be written to and therefore cannot drift, which is what denormalization cannot promise — but the expression may only see one row, so a count over another table is out of reach. PRAGMA table_info does not list them; only table_xinfo does.
- Generative Classifier Day 158
- A classification model that learns the joint probability distribution P(x, y) of inputs and labels, modeling how data is generated.
- generator expression Day 55
- Comprehension syntax written with round brackets `(...)` that produces items lazily, one at a time, instead of building the whole collection at once; ideal fed straight into `sum`, `any`, or `max`.
- generator function Day 55
- A function that uses `yield` instead of `return`; calling it returns a generator object (an iterator) without running the body, which then executes lazily as items are pulled from it.
- generic Day 75
- A type or function parameterised by other types. `list[int]` and `dict[str, float]` are generic containers; a function written with a TypeVar is a generic function. The modern builtin spelling replaced the capitalised `List` and `Dict` imports from `typing`, which mean the same thing.
- Geometric distribution Day 114
- The distribution of the number of independent Bernoulli(p) trials needed to see the first success. Mean 1/p, variance (1-p)/p^2. The distribution behind "how many attempts until it works."
- Geometric Margin Day 169
- The shortest Euclidean distance from the decision boundary hyperplane to the closest data points in the training set.
- get Day 53
- The dictionary method d.get(key, default) that returns the value for key, or the given default (or None if none is given) when the key is absent — a safe read that does not raise KeyError.
- GET Day 18
- The method for reading a resource without changing anything; it is both safe (read-only) and idempotent (repeating it has the same effect as doing it once).
- get_feature_names_out Day 173
- A scikit-learn API method that tracks and outputs the transformed string names of features passing through complex ColumnTransformer pipelines.
- get_params() Day 146
- Returns an estimator's hyper-parameters as a dictionary, including nested step parameters for composite estimators like Pipeline, prefixed with the step's name and two underscores. Measured at 23 keys for a two-step Pipeline.
- gibibyte Day 4
- The binary giga-unit, GiB = 1,024³ bytes, defined by the IEC in 1998 to end the ambiguity with the decimal gigabyte (GB = 10⁹ bytes) that makes a "1 TB" drive report about 931 GiB.
- gigahertz Day 2
- A billion clock cycles per second; a 3 GHz CPU's clock ticks three billion times each second, making one cycle about a third of a nanosecond.
- GIL (global interpreter lock) Day 96
- A mutex inside CPython that a thread must hold in order to execute Python bytecode. Three facts define its behaviour and every consequence follows from them: it protects the INTERPRETER own state — reference counts, the allocator, interpreter structures — and not your data structures; it is RELEASED while a thread waits on I/O, which is why threads help with waiting; and a thread doing pure computation HOLDS it, which is why threads do not help with computing. It is not a thread-safety guarantee for your code, and believing it is one is how races get shipped.
- Gini Impurity Day 162
- A measure of node label heterogeneity in classification trees: G = 1 - sum(p_k^2), equal to 0.0 for pure nodes and maximized for uniform distributions.
- git add Day 30
- The command that copies changes from the working directory into the staging area, marking them for inclusion in the next commit.
- git commit Day 30
- The command that records everything currently staged as a new permanent snapshot in the repository, with a message describing the change.
- Git Flow Day 35
- A heavier branching model with long-lived main and develop branches plus temporary feature, release, and hotfix branches, suited to scheduled, versioned releases.
- git hook Day 41
- A script that git runs automatically at a point in its workflow, such as before a commit; a hook only takes effect if it is marked executable.
- Git LFS Day 35
- Git Large File Storage, an extension that keeps large binaries (datasets, models, media) out of the repository's normal storage by committing a small pointer and storing the real bytes separately.
- git status Day 30
- The command that reports which files are untracked, staged, or modified — the window that tells you which area holds each file's current content.
- GitHub Flow Day 35
- A lightweight workflow: create a short-lived branch, open a pull request for review, then merge back into a main branch that is always kept deployable.
- global (scope) Day 58
- The top level of a module (a .py file): names defined outside any function, such as constants and function definitions. It is searched after local and enclosing scopes and before the built-in scope.
- global keyword Day 58
- A statement (global name) inside a function declaring that a name refers to the module-level variable, so assigning to it updates the global rather than creating a new local. Used sparingly, because widely mutated globals make programs hard to reason about.
- God object Day 70
- A single class that parses, validates, calculates, formats and prints. It cannot be described in one sentence, cannot be tested in parts, and every change touches it. The remedy is to split by responsibility and push the world to the adapters.
- Golden Signals Day 195
- The four core SRE monitoring dimensions: Latency, Traffic (QPS), Errors, and Resource Saturation.
- Golden Test Set Day 191
- A curated, pristine, manually verified dataset used strictly for final model evaluation and never exposed during training.
- GOSS (Gradient-based One-Side Sampling) Day 165
- A subsampling algorithm that retains all instances with large gradients and samples a small fraction of small-gradient instances to accelerate training.
- graceful degradation Day 27
- Failing usefully when a request cannot succeed — serving a cached or partial result, or returning a clear error — instead of crashing or silently returning misleading data.
- Graceful Degradation Day 196
- The system design principle ensuring that when a component fails, the service falls back to safe heuristics rather than crashing.
- grad_fn Day 204
- A reference on a non-leaf tensor pointing to the backward function node that generated it during forward execution.
- Gradient Day 109
- The vector whose components are all the partial derivatives of a scalar function, one per input, written ∇f. Its direction is the direction of steepest increase and its magnitude is the rate of increase in that direction — Wikipedia states both, and calls the magnitude "the greatest absolute directional derivative". Its formal defining property is sharper and worth knowing: it is "the unique vector field whose dot product with any unit vector v at each point x is the directional derivative of f along v". A function of n inputs has an n-component gradient regardless of how many dimensions its graph occupies: it is an arrow drawn on the flat map you are standing on, not one pointing out of the hillside.
- Gradient accumulation Day 110
- Adding each incoming contribution to a node gradient rather than overwriting it, written += rather than = in a backward step. This one character implements the multivariable chain rule: a value used in several places receives a contribution from each use, and all of them are real. Assignment instead produces code that runs, looks reasonable and is wrong on every graph containing a reused value.
- Gradient Accumulation Day 204
- The default behavior in PyTorch where new gradients computed by backward() are summed into existing .grad buffers rather than overwriting them.
- Gradient Boosting Day 164
- An ensemble method that builds an additive model sequentially by training base estimators (typically shallow decision trees) on the negative gradient of a differentiable loss function.
- Gradient checking Day 109
- Comparing a hand-written or analytic gradient against a numerical one on a small example, to find out whether the analytic one is correct. It is the job numerical differentiation is still genuinely best at, and the reason the method survives in serious toolkits long after nothing trains with it. The comparison should be relative rather than absolute, because a numerical gradient's roundoff error grows in proportion to the size of the function's values.
- Gradient checking Day 111
- Comparing an analytic gradient function against Day 108's central difference, component by component, to catch implementation bugs. A wrong analytic gradient runs, returns numbers of a plausible shape, and can even make training loss go down for a while -- gradient checking is the cheap, mechanical way to catch it before it costs a real training run.
- Gradient Clipping Day 209
- A technique that rescales gradient vectors when their global Euclidean norm exceeds a threshold, preventing explosive parameter divergence.
- Gradient descent Day 111
- The update rule x <- x - eta*grad(x), repeated until the gradient is small enough. Take the direction that increases loss fastest, flip it, scale it by a learning rate, and move. The entire training loop of every model in this course, underneath whatever else surrounds it.
- Gradient norm Day 112
- The magnitude (Euclidean length) of the gradient vector at a point, written ||grad f(x)||. It distinguishes a run that has genuinely converged (gradient near zero) from one merely stalled on a flat plateau or oscillating on a stability boundary (gradient not shrinking toward zero even though the loss has stopped changing).
- Gradient-descent stability threshold Day 153
- The learning rate above which gradient descent on a quadratic loss diverges, from Day 111's condition |1 - eta * a| < 1 applied to the loss's largest Hessian eigenvalue. Measured at 0.2485 for standardized diabetes features; gradient descent converges in 7132 iterations at 80 percent of it and diverges to non-finite values at 102 percent.
- gradual typing Day 69
- PEP 484's design principle that you may annotate as much or as little of a codebase as you like, with unannotated code simply going unchecked. It is what makes it reasonable to annotate boundaries and data models while leaving obvious locals alone.
- gradual typing Day 75
- PEP 484's design principle that a codebase may be annotated as much or as little as you like, with annotated and unannotated code interoperating freely and unannotated functions simply going unchecked. It is what makes adopting types in an existing project possible at all — you type one module at a time — and it is also why a clean run on unannotated code means the checker did not look.
- grain Day 135
- What one row in a table means. A customer-grain table has exactly one row per customer; an order-grain table has one row per order. Neither is more correct in general -- they answer different questions -- but choosing the wrong grain for a given question produces a number that is silently wrong rather than an error, which is why deciding the grain before flattening is this lesson's core discipline.
- Grain Day 140
- The sentence "one row is one ___". The unit of observation a table is keyed on. Every aggregate depends on it, and a sum computed under the wrong grain is not approximately right but wrong by an amount you cannot bound. A grain that is declared but never verified is a hope with a schema.
- grammar of graphics Day 127
- Leland Wilkinson's 1999 idea that charts should be composed from data, a mapping of variables to channels, a geometry, scales and a coordinate system, rather than chosen from a menu of named types. The ancestor of ggplot2 and Vega-Lite, and the reason "which channel?" is a more answerable question than "which chart?".
- granularity Day 134
- What a single row of a dataset represents -- a country-year, a household-month, a single transaction. Two datasets that look comparable because they cover the same topic frequently differ in granularity, and an aggregate computed across mismatched granularities looks precise while measuring nothing real.
- Graph database Day 92
- A store that holds nodes and edges as first-class objects, so following a relationship is a pointer hop rather than an index lookup into a junction table. Neo4j is the well-known one, queried with Cypher. It is the right shape when the questions are about paths and connections, and the wrong one when they are bulk aggregates, which is the opposite trade from a wide-column store.
- graphical perception Day 127
- The study of how accurately people extract quantities from visual encodings, made experimental by Cleveland and McGill in 1984. It is what turns "bar beats pie" from a preference into a measured result.
- Graphical perception Day 132
- The empirical study of how accurately readers decode quantities from visual encodings, established by William S. Cleveland and Robert McGill in the Journal of the American Statistical Association (1984). Their experiments produced the ordering of elementary perceptual tasks -- position along a common scale, then length, then angle and slope, then area, then volume and colour -- that Day 127 introduced and that predicts which encodings fail before any distortion is added.
- GraphQL Day 23
- An API style exposing a single endpoint where the client asks for exactly the fields it wants in one query, addressing REST's tendency toward many round trips or over- and under-fetching.
- Great Expectations Day 126
- A Python library for declaring and running "expectations" about a dataset (row counts, null rates, value distributions) as part of a pipeline, with a paid-hosted layer (Great Expectations Cloud) built around the free open-source core. Not installed in this lesson's environment; described from its documentation only.
- greedy Day 38
- The default behavior of a quantifier, which matches as much text as possible while still letting the overall pattern succeed — the reason .* often matches too much.
- grep Day 10
- A command that searches its input line by line and prints the lines matching a pattern; common flags include -i (ignore case), -c (count), -n (line numbers), -v (invert), and -r (recursive).
- Greyscale Day 105
- An image with a single value per pixel, representing brightness. Stored as a 2-D array of shape (height, width) — rows then columns, which is (y, x). With the usual 8-bit depth each value runs from 0 (black) to 255 (white), one byte per pixel, so a 9 by 9 greyscale image is exactly 81 bytes.
- Grid Search Day 166
- An exhaustive hyperparameter optimization strategy that trains and evaluates models across all combinations in a predefined discrete Cartesian product grid.
- group Day 38
- A sub-pattern enclosed in parentheses, which lets a quantifier apply to the whole sub-pattern and, unless made non-capturing, remembers the text it matched.
- Group Aggregation (Split-Apply-Combine) Day 171
- Computing entity-level summary statistics (mean, std, count, min, max) grouped by a categorical key and merging back onto the dataset.
- Group Contamination Day 180
- Splitting samples randomly when records from the same entity (e.g. patient, user) exist across both train and validation splits.
- Group K-Fold Day 167
- A cross-validation split that ensures no group (patient, user, physical device) is represented in both the training and testing sets of any fold.
- Group split Day 144
- A split that never puts rows from the same unit -- person, device, document, hospital -- on both sides. The fix for the most expensive failure in this lesson: 0.9760 row-wise against 0.4112 group-aware, because all fifty people were in both halves.
- Group-Specific Threshold Calibration Day 179
- A post-processing technique selecting different decision thresholds per demographic group to enforce Equal Opportunity.
- groupby Day 123
- The pandas operation implementing split-apply-combine: partition a DataFrame or Series into groups sharing the same value(s) on one or more key columns, apply a function independently to each group, and combine the per-group results back into a single pandas object.
- GroupBy.filter Day 123
- A method that keeps or drops entire groups based on a predicate evaluated once per group (for example, a minimum group size), returning a subset of the original rows with the surviving groups' structure otherwise unchanged. Distinct from row-level boolean-mask filtering (Day 122), which decides row by row rather than group by group.
- Grouping effect Day 151
- What ElasticNet was designed to restore that plain lasso lacks: treating a group of correlated predictors as a unit, splitting weight among them roughly the way ridge does, rather than picking one arbitrarily and zeroing the rest.
- Grouping key Day 86
- The column or expression named in GROUP BY, whose distinct values decide the buckets. After grouping, the only things you may legitimately ask for are the grouping key itself and aggregates over the bucket, because a bucket of seven books has no single title to give you. GROUP BY is also the one place in SQL where all the NULLs are treated as equal and land in a single bucket — which is why grouping a column can produce one more bucket than COUNT(DISTINCT) on the same column reports.
- GroupKFold Day 180
- A cross-validation scheme ensuring all records from any specific group or entity reside in only one fold.
- guard clause Day 50
- A conditional near the top of a function that handles an exceptional case (invalid input, an early exit) immediately and returns or raises, so the main logic that follows never has to indent. Guard clauses keep decision code flat and readable instead of deeply nested.
- Guardrail metric Day 119
- A metric that must not get worse by more than a pre-declared tolerance, and can veto an otherwise-positive verdict on the primary metric. In this lesson's lab, page-render latency is the guardrail -- dataset A's guardrail holds (latency improves slightly); a guardrail failure is designed to flip the final verdict regardless of how good the primary result looks.
- Hadamard product Day 101
- The formal name for the elementwise product, so called after Jacques Hadamard. Worth knowing because papers use the name and a small circle symbol for it where code uses a bare asterisk, and a reader who does not recognise the name can mistake it for the matrix product and misread the whole equation.
- Hamming distance Day 107
- The number of positions at which two equal-length sequences differ. Introduced by Richard Hamming in "Error Detecting and Error Correcting Codes" in the Bell System Technical Journal in April 1950, where it counted bit flips between code words. Nothing is subtracted, so the values need not be numbers at all — which makes it the right measure for categorical features, and the honest alternative to encoding categories as 0, 1, 2 and thereby asserting that the second category is nearer to the first than the third is. On genuinely binary features it coincides exactly with L1 and with squared Euclidean distance, because every difference is 0 or 1 and 1 squared is 1.
- handler Day 66
- An except clause plus its body. It matches if the raised exception is an instance of the named class or any subclass of it, and clauses are tested top to bottom, which is why specific types must come first.
- Handler Day 97
- A destination — standard output, a file, a rotating file, a syslog socket, a queue. A logger may have several, and each carries its OWN level, its own filters and its own formatter. That independence is the point: the same call can be dropped by one handler, written as prose by a second and written as JSON by a third.
- Handoff object Day 136
- In this lesson's lab, the structured record passed from the exploration stage to a report-writing stage (Day 133), required to carry a finding, its result on the confirmation set, and the number of comparisons run before it was chosen.
- handshake Day 19
- The opening exchange of a TLS connection that authenticates the server and agrees a shared symmetric key, after which data is encrypted symmetrically.
- hard reset Day 34
- git reset --hard: moves HEAD, the index, and the working tree to the target commit, permanently discarding any uncommitted changes. The one genuinely destructive undo mode.
- hash Day 30
- A commit's unique identifier — a long hexadecimal fingerprint computed from the commit's full contents (snapshot, author, time, message, and parent); usually shown as the first seven characters.
- Hash join Day 87
- The join algorithm that builds a dictionary from one side once and then looks each row of the other side up in it. Its cost is the sum rather than the product of the two sizes — six rows and five is eleven operations. Identical results to a nested loop; the entire difference is that one grows as the product and the other as the sum.
- hash table Day 53
- The data structure underneath a dictionary: it hashes a key to a number, reduces it to a bucket (array slot), and stores the pair there, giving average O(1) lookup by jumping straight to the bucket instead of scanning.
- hashable Day 53
- A property of an object whose hash value stays fixed over its lifetime (and where equal objects share a hash), which is what lets it serve as a dictionary key. Immutable built-ins qualify; mutable ones (lists, sets, dicts) do not.
- hashable Day 54
- A value for which Python can compute a stable fingerprint (a hash), which is required to store it in a set or use it as a dict key. Immutable values (numbers, strings, tuples, frozensets) are hashable; mutable ones (lists, dicts, sets) are not.
- hashable Day 68
- An object usable as a dict key or set element, because it has a `__hash__` returning a stable integer. Defining `__eq__` sets `__hash__` to `None`, so the two must be defined together — and only over fields that do not change, since a mutated object is lost in its set.
- HATEOAS Day 23
- Hypermedia As The Engine Of Application State — the REST constraint that a resource's representation includes links telling the client what it can do next and where.
- HAVING Day 86
- The clause that filters groups, using the same TRUE-only rule as WHERE but applied to buckets rather than rows. It exists because there is no other stage that runs after the buckets are built and before the output is projected, and because a fact like "this author has more than three titles" belongs to no individual row. It is not a second WHERE: when a condition really is about one row, put it in WHERE, which runs earlier and does less work.
- HDD Day 3
- A hard disk drive: persistent storage on spinning magnetic platters read by a moving head, cheap per byte but needing several milliseconds per seek.
- He Initialization Day 201
- A weight initialization scheme drawing random values from a normal distribution with variance 2 / n_in, optimized for ReLU activation layers.
- HEAD Day 30
- A pointer to the commit you are currently on, normally the newest commit on your branch; it advances to each new commit you make.
- HEAD Day 31
- A special reference marking the branch (and commit) you are currently on — "you are here." It moves to the new commit each time you commit.
- HEAD Day 34
- A pointer to the commit you currently have checked out — normally the tip of the current branch, and the snapshot you would return to if you discarded everything else.
- header Day 18
- A Name: value line carrying metadata about a request or response, such as Content-Type or Authorization; headers come before the blank line that precedes the body.
- header Day 21
- A named field of metadata attached to an HTTP request or response, such as Accept, Content-Type, or Authorization, that carries information alongside the body.
- Header Day 78
- A name-colon-value line carrying metadata about a request or response. The ones worth memorising: Content-Type (what the body is), Accept (what you would like back), User-Agent (who you are), Authorization (your credentials), Content-Length (how many bytes the body is) and Retry-After (how long to wait). Names are case-insensitive and order is not significant.
- header row Day 65
- The first line of a CSV, naming the columns. DictReader uses it to key each record by column name, so your code stops depending on column order.
- Heartbeat Day 81
- The record a successful run leaves behind — a file, a database row, a ping to a service — carrying the time of the last success. The staleness budget for it is usually about two intervals plus the job's normal runtime: tight enough to notice, loose enough to tolerate exactly one missed run.
- Heaviside Step Function Day 197
- A discontinuous threshold function returning 1 for non-negative inputs and 0 for negative inputs.
- Heavy-tailed distribution Day 149
- A distribution whose extreme values occur far more often than a Gaussian's. Constructed here with a Student's t distribution at 3 degrees of freedom, scaled to a similar central spread as the Gaussian comparison, so the two settings differ only in how often big errors occur.
- Hessian Day 109
- The square matrix of SECOND partial derivatives of a scalar function, with one row and one column per input. It describes curvature, and it is the object that answers the question the gradient cannot: whether a stationary point is a minimum, a maximum or a saddle. Named here and not developed. Its cost is the reason it is rarely used at scale — it has one entry per pair of parameters, so a million-parameter model would have a Hessian with a trillion entries.
- Hessian eigenvalue ratio Day 153
- The condition number of the loss surface gradient descent is optimizing, governing how many iterations the slowest direction needs to converge. 470.08 on standardized diabetes features; 76278.96 on raw, unscaled ones -- over a hundred times worse, which is why gradient descent barely moves on badly scaled data even at a stable learning rate.
- Heteroscedasticity signal Day 154
- The correlation between a model's fitted value and the absolute size of its residual. Near zero means errors do not systematically grow or shrink with the prediction; here, 0.2386 -- a mild fanning-out, not a dramatic one.
- hexadecimal Day 4
- Base-16 notation using digits 0–9 and A–F, written with the 0x prefix; each digit encodes exactly four bits, making it the standard human-readable shorthand for raw binary.
- hexbin Day 130
- A 2-D histogram that tiles the plotting area with hexagons instead of squares and colors each one by how many points fall inside it, fixing overplotting by aggregating count instead of trying to make individual points visible. It answers "how dense is this region" rather than "where exactly are the points," which is a real trade, not a free upgrade.
- hidden file Day 9
- A file or directory whose name begins with a dot, which plain ls and most file browsers skip by default; revealed with ls -a.
- Hidden state Day 139
- A value a kernel remembers that no cell currently in the document defines. It arises when a cell that once defined a variable is deleted (or edited to remove that definition) without restarting the kernel, so cells that depend on the value keep working for whoever is still in that session and fail for anyone who opens the notebook fresh.
- High Bias (Underfitting) Day 177
- A failure regime where model capacity is insufficient, resulting in high training error and high validation error with a small generalization gap.
- High Variance (Overfitting) Day 177
- A failure regime where model capacity is too high, resulting in low training error but high validation error and a wide generalization gap.
- Hinge Loss Day 169
- A convex loss function L(y, f(x)) = max(0, 1 - y * f(x)) used in maximum-margin classification that penalizes margin violations linearly.
- histogram Day 40
- A metric that records the distribution of many measured values into buckets, such as request latencies, from which percentiles like the p95 are computed.
- Histogram-Based Binning Day 165
- Discretizing continuous floating-point features into integer bins (typically 256 uint8 bins) to construct split histograms in O(n_bins) constant time.
- historical bias Day 138
- The case where the data is an accurate record of an unjust process. A model that fits it well reproduces the injustice faithfully, and its accuracy score will be excellent, because reproducing the past accurately is what a high accuracy score means. This is where measurement genuinely runs out: no divergence, ratio or error figure detects it, because nothing in the data is wrong.
- history Day 29
- The ordered chain of commits that records how a project reached its current state, with each commit linked to the one before it.
- HMAC Day 26
- Hash-based message authentication code — a signature made by hashing a message together with a shared secret, used to verify a webhook came from someone who knows the secret and was not tampered with.
- Holding the other predictors constant Day 150
- What a multiple-regression coefficient measures: the change in the target for one unit of change in one predictor, with every other predictor's value fixed at whatever it happens to be. When predictors move together in the data, this condition is met only approximately, which is the seed of every instability measured in this lesson.
- Holdout variance Day 144
- How much a single train/test estimate moves when only the split changes. Measured at 0.0381 standard deviation and a 0.19 range on 400 rows -- larger than most improvements anyone is chasing.
- HOME Day 11
- An environment variable holding the absolute path to your home directory; the shell expands the shorthand ~ to its value.
- home directory Day 9
- The personal directory where a user's own files live and where a terminal usually starts; abbreviated by the shell as the tilde (~).
- Homebrew Day 13
- The popular free, open-source package manager for macOS (and Linux), driven by the brew command; its packages are called formulae.
- homogeneity attack Day 138
- Disclosure of a sensitive attribute from a k-anonymous table because every member of an equivalence class shares the same value. Nobody is re-identified; membership in the class is enough. This is the limit that motivated l-diversity, and it is why a check trusted past its stated guarantee is worse than no check.
- Homogeneous coordinates Day 102
- A trick that makes a shift look like a matrix multiplication by writing a 2D point (x, y) as the 3D vector (x, y, 1), whereupon translation becomes an ordinary 3 by 3 matrix product. It is why a 2D graphics transform is a 3 by 3 matrix and why CSS and SVG take six numbers for a 2D transform: four for the linear part and two for the shift. The shift did not become linear; it was moved to a bigger space where it could pretend to be.
- Homogeneous coordinates Day 105
- Writing the point (x, y) as the triple (x, y, 1) so that a 3 by 3 matrix can add a constant, because the constant is multiplied by that third 1. Introduced by August Ferdinand Möbius in 1827, long before there was any image to apply them to. They exist here for one reason: translation moves the origin, Day 102 proved a linear map cannot, so no 2 by 2 matrix performs a translation — and without a matrix form, a translation cannot be COMPOSED with a rotation into a single operation. The third coordinate is not a z axis and the picture is not three-dimensional; it is a bookkeeping slot.
- Homoscedasticity Day 148
- The assumption that the scatter of errors around the fitted line is roughly the same width everywhere. Its opposite, heteroscedasticity, was measured here as a residual standard deviation of 4.7427 in the low half of the predictor against 12.0684 in the high half.
- honest omission Day 133
- A single line recording something you looked at and found nothing in, kept in the report after the chart itself has been deleted. It costs one line, stops the next reader repeating your dead end, and answers the question "did they check that?" with a fact instead of an assumption.
- hosting platform Day 32
- A service such as GitHub, GitLab, or Bitbucket that hosts Git remotes and adds a website, access control, issue tracking, code review, and automation on top of Git.
- how (join type) Day 124
- The merge() keyword selecting inner (keep only matching keys), left (keep every left row), right (keep every right row), or outer (keep every row from both sides), filling NaN wherever no match exists on the kept side. Named identically to SQL's JOIN clauses, which pandas' merge design deliberately mirrors.
- HSTS Day 19
- HTTP Strict Transport Security, a header telling a browser to contact a site only over HTTPS and never allow clicking through its certificate warnings.
- HTML Day 20
- HyperText Markup Language, the language that describes a web page's structure and content by marking text as headings, paragraphs, lists, links, and other elements.
- HTML parser Day 79
- A library that turns markup into a navigable tree, handling nested tags, attribute lists, entities and broken markup correctly. BeautifulSoup with the html.parser backend is Python's default choice; lxml and selectolax are faster alternatives. A parser is the reason you never match HTML with a regular expression.
- HTTP Day 15
- The HyperText Transfer Protocol, the request-and-response format a browser and server use to ask for and return web resources.
- HTTP Day 18
- The HyperText Transfer Protocol: the set of rules a client and server follow to exchange request and response messages over a network. It is the protocol every web page load and every hosted-model API call speaks.
- HTTP Day 78
- The HyperText Transfer Protocol: a set of rules for one machine to ask another for something and get an answer. Invented by Tim Berners-Lee at CERN around 1989-1991, and remarkable for being plain text — a request is a line, some headers, a blank line, and optionally a body, all of which you can type by hand. Its meaning is defined today by RFC 9110, deliberately separated from the wire formats of HTTP/1.1, HTTP/2 and HTTP/3 so that a GET is a GET on all three.
- HTTP client library Day 28
- A library inside a programming language (such as Python's requests or JavaScript's built-in fetch) that sends HTTP requests from code, used when a shell one-liner outgrows a single line.
- HTTP status code Day 42
- The number a server returns with a response that tells you what happened: for example 401 (authentication failed), 404 (resource not found), or 429 (rate limited) — days 18, 23, 25, 27.
- HTTPException Day 82
- What a handler raises to give a known negative answer — `HTTPException(status_code=404, detail=...)` — producing a small predictable JSON body. It is how a missing thing becomes an answer rather than a crash, and it is the deliberate opposite of an unhandled exception, which becomes a 500 whose body says nothing at all.
- httpie Day 21
- A free, open-source command-line HTTP client, an alternative to curl designed for human readability with coloured, formatted output and a simpler syntax.
- HTTPS Day 19
- HTTP carried inside a TLS-encrypted connection (conventionally on port 443), giving web traffic confidentiality, integrity, and server authentication.
- Huber loss Day 149
- A loss that is squared error inside a threshold `epsilon` and (scaled) absolute error outside it. Continuous, not a hard switch: sweeping epsilon from 1.0 to 100.0 moved the fitted slope smoothly from 3.0064 to 3.8010, the exact OLS answer on the same data.
- Human-Level Performance (HLP) Day 181
- The empirical performance achieved by domain experts on a task, establishing an estimate of Bayes optimal error.
- Hyperband Day 166
- A bandit-based hyperparameter optimization framework that extends Successive Halving across varying initial resource allocations to resolve the exploration vs exploitation trade-off.
- Hyperparameter Day 111
- A value that controls how an algorithm runs rather than being learned by it -- the learning rate and momentum coefficient in this lesson are both hyperparameters. Unlike a model parameter, a hyperparameter is not updated by the gradient; it is chosen (or searched over) before or between training runs.
- Hyperparameter Day 166
- A configuration external to the model whose value is set before the learning process begins, dictating model capacity, optimization dynamics, and regularization.
- Hyperplane Day 156
- A flat affine subspace of dimension d-1 in a d-dimensional feature space, defined by the linear equation w^T x + b = 0.
- IANA time zone database Day 95
- The public-domain database of every recorded and scheduled change of local time worldwide, maintained collaboratively and published by IANA under version names such as 2026c. It is updated whenever a government changes its mind, sometimes with a few weeks' notice. Python's zoneinfo contains none of this data: it reads whatever your operating system has installed, which means a stale container image holds a stale opinion about the future.
- IDE Day 36
- An Integrated Development Environment: an editor bundled with the preconfigured machinery for building, running, and debugging a particular language or platform, all in one package.
- idempotence Day 56
- A property of an operation whose repeated application leaves the system in the same state as a single application; read-only commands like list and find are naturally idempotent, and a delete can be made idempotent by treating "already absent" as success.
- idempotence Day 126
- The property that applying an operation a second time to its own output produces the same result as applying it once: pipeline(pipeline(df)) equals pipeline(df). A pipeline that lacks this property drifts silently every time it happens to run twice, which a retried scheduled job does routinely.
- Idempotence Day 76
- The property that applying an operation twice gives the same result as applying it once. For a formatter it means formatting already-formatted code changes nothing — the second `ruff format` run reports `1 file left unchanged`. It is what makes a formatter safe to put in a commit hook, because the hook cannot fight itself.
- Idempotence Day 78
- The property that doing something twice has the same effect on the server as doing it once. GET, HEAD, PUT and DELETE are idempotent; POST is not, and PATCH need not be. This is the property that makes retrying a timed-out request safe or dangerous, and it is why an idempotency key exists: a unique value you send so the server can recognise a repeat and return the original result instead of doing the work again.
- Idempotence Day 81
- The property that running something twice has the same effect as running it once. The most important property a scheduled job can have, because every other mechanism in this area — retries, catch-up runs, an operator repeating a command, a daylight-saving repeat — eventually causes a second run.
- Idempotence Day 84
- The property that running an operation again does not change the outcome. The term comes from mathematics, coined by Benjamin Peirce in 1870. For a scheduled job it is the single most valuable property there is: it makes catch-up after downtime, manual re-runs during debugging, and overlapping runs into ordinary events rather than data-integrity incidents.
- Idempotence Day 98
- The property that doing something twice has the same effect as doing it once. For a pipeline it is the single most valuable property available, because it converts almost every failure into the same remedy — run it again. A run that crashed halfway, a source that was down, a deploy that went out wrong, a schedule missed while the machine was asleep: all of them are fixed by rerunning, and none of them are if the rerun doubles your data.
- Idempotence key Day 98
- The column or set of columns that identifies a record by what it *is* rather than by when it arrived — here the pair (station_id, reading_id) assigned by the source. Declared UNIQUE, it is what makes a second run store nothing. Choosing it is a modelling decision, not a technical one: it is an answer to the question "what would make two arriving records the same record?"
- idempotency Day 26
- The property that processing the same event more than once has the same effect as processing it once; required because at-least-once delivery can deliver duplicates.
- idempotency Day 41
- The property that running an operation twice on the same input produces the same result, with no leftover state leaking between runs, making automation safe to re-run.
- Idempotency key Day 81
- A stable identifier for a unit of work, sent with a request so that the receiving system can ignore a repeat. The standard answer for work that is naturally once-only, such as sending an email or charging a card; payment APIs support it precisely because retries are unavoidable.
- idempotent Day 14
- A property of a task that makes running it more than once no more harmful than running it once, because it checks the current state before acting.
- idempotent Day 18
- A property of a method meaning that making the same request many times has the same effect as making it once; GET, PUT, and DELETE are idempotent, POST is not.
- idempotent Day 23
- A property of a request such that making it many times leaves the server in the same state as making it once; GET, PUT, and DELETE are idempotent, while POST is not.
- idempotent ingestion Day 135
- An ingestion step that produces the same result whether it runs once or is accidentally run twice with the same input -- typically achieved with a natural key (an identifier that names the same real-world entity across runs) and an upsert that replaces, rather than appends, any row sharing that key.
- idempotent retry Day 27
- Re-attempting a request that is safe to repeat because doing it twice has the same effect as doing it once (as with GET, PUT, and DELETE); non-idempotent writes need an idempotency key or must not be retried blindly.
- identity Day 44
- A permanent, per-object marker of "which object is this," returned by id(). In the standard interpreter it is essentially the object's memory address; the is operator compares it.
- Identity map Day 93
- A dictionary inside the Session mapping (class, primary key) to the one object representing that row. It guarantees that fetching row 1 twice in one Session returns the same Python object, which is what stops two copies of a row drifting apart and one edit silently overwriting the other. It also means a repeat lookup of an already-loaded row emits no SQL at all.
- Identity matrix Day 100
- The square matrix with 1 on the main diagonal and 0 everywhere else. It leaves every vector exactly as it found it, which makes it the "do nothing" transformation and the starting point for defining an inverse. numpy.eye(n) builds one. Recognising it on sight tells you an operation is a no-op without reading any of the numbers.
- Identity matrix Day 101
- The square matrix with 1 on the main diagonal and 0 everywhere else. The transformation that does nothing: applied to a vector it returns that same vector, and multiplying any matrix by it changes nothing. It is really one matrix per size, and the shape rule decides which — a (2, 3) matrix takes a 2 by 2 identity on its left and a 3 by 3 identity on its right. numpy.eye(n) builds one.
- Identity matrix Day 102
- The matrix that leaves every vector exactly where it found it, [[1, 0], [0, 1]] in two dimensions. Under today reading it has a reason rather than a definition: it is what you write down when the basis vectors did not move, so nothing else moves either. Its determinant is 1 and its rank is full. numpy.eye(n) builds one.
- IEEE 754 Day 46
- The international standard, published in 1985, that defines how binary floating-point numbers are laid out in bits and how arithmetic on them rounds, so the same program gives the same result on any conforming hardware.
- if / elif / else Day 50
- Python's conditional statement. `if` runs a block when its condition is true; `elif` (else-if) tests another condition only when the previous ones were false; `else` catches everything remaining. Python takes the first true branch and skips the rest, so order matters.
- Ill-conditioning Day 111
- A large gap between a loss surface's steepest and shallowest curvature directions. Any single fixed learning rate that is safe for the steep direction is forced to be small, which then makes progress in the shallow direction painfully slow -- the mechanism behind the textbook image of gradient descent zig-zagging down a narrow valley.
- immutability Day 54
- The property of a value that cannot be changed after it is created. Tuples, strings, numbers, and frozensets are immutable; lists, dicts, and sets are mutable. Immutability is what makes a value hashable.
- immutable Day 44
- Describes an object that cannot be changed after creation; "modifying" it creates a new object. int, float, bool, str, and tuple are immutable.
- immutable Day 45
- Unable to be changed in place. A string never changes; every operation that seems to modify it actually returns a new string and leaves the original untouched.
- Implicit Feedback Day 188
- Passive user behavioral signals (clicks, views, dwell time, purchases) rather than explicit numeric ratings.
- import Day 59
- The statement that loads a module (running its top-level code once, then caching it) and binds a name so you can use its contents. `import stats` binds the whole module, reached as stats.top_n.
- import as Day 59
- The `import module as alias` form, which binds a module (or `from module import name as alias` a name) under a different, usually shorter name — the reason data-science files begin `import numpy as np`.
- Import name Day 83
- The name you type after `import`. It must be a valid Python identifier, and it is usually short. For this lesson's package it is `wordtally`.
- Import sorting Day 76
- Ordering and grouping import statements into standard library, third party and first party blocks, each alphabetised. Solved narrowly by the isort tool and reimplemented in Ruff as `I001`. Its real value is that it removes a whole category of pointless diff noise: two people adding an import no longer conflict over where it goes.
- Impossibility Theorem of Fairness Day 179
- Mathematical proof that Demographic Parity, Equalized Odds, and Predictive Parity cannot simultaneously hold when base rates differ across groups.
- include_groups Day 123
- A keyword added to GroupBy.apply() in pandas 2.2 controlling whether the grouping column(s) are included in the DataFrame passed to the applied function. Does not exist on pandas versions before 2.2, in which the grouping columns are always included.
- inclusive vs. exclusive boundary Day 135
- The choice of whether an incremental fetch's "since" filter includes records exactly at the watermark timestamp (inclusive, >=) or excludes them (exclusive, >). Exclusive risks silently and permanently dropping a record that shares a timestamp with the watermark record; inclusive risks only a harmless duplicate that an idempotent upsert absorbs for free -- which is why this lesson chooses inclusive.
- Inconclusive verdict Day 119
- A legitimate, first-class experiment outcome in which the confidence interval is too wide to rule out either "no meaningful effect" or "a meaningful effect" -- distinct from, and not silently rounded to, "no effect." The honest response is usually more data or a different design, not a forced ship/no-ship call.
- incremental development Day 63
- Building a program one small, working, tested slice at a time — make the simplest case work, check it, then grow — so you are never far from a version you trust, instead of writing everything at once and debugging blindly at the end.
- IndentationError Day 48
- A special kind of SyntaxError caused by wrong or inconsistent indentation, such as a line indented where Python did not expect it.
- Independence Day 113
- Two events A and B are independent when P(A and B) = P(A) x P(B) — equivalently, when knowing one occurred tells you nothing about the other, P(A | B) = P(A). "Sum is 7" and "first die is 3" are independent on two dice; "sum is 2" and "first die is 1" are not.
- index Day 30
- Git's internal name for the staging area — the list of changes prepared for the next commit.
- index Day 34
- Also called the staging area: a holding area for the changes marked as ready to go into the next commit. git add copies changes into it; a commit freezes its contents into a new snapshot.
- index Day 39
- An extra sorted lookup structure a database maintains so it can jump straight to matching rows instead of scanning every row, turning a slow full scan into a fast lookup.
- index Day 45
- The position of a single character in a string, counted from 0 at the left; negative indices count from the right, so s[-1] is the last character.
- index Day 52
- The position of an item in a list, counted from zero: `nums[0]` is the first item. Indexing a list is O(1) because the items sit in one contiguous block and Python jumps straight to the slot.
- index Day 120
- The array of labels attached to a Series or DataFrame's rows. Two Series with different indexes do not correspond position by position; arithmetic between them aligns on the labels first.
- Index Day 83
- A server that lists distributions and serves their files — the public Python Package Index, a separate test index used for rehearsal, or a private one inside an organisation. It is an OPTIONAL channel: a git URL, a local directory of wheels, or a wheel handed over directly are all complete distribution mechanisms that involve no index at all.
- Index Day 89
- A second, sorted copy of one or more columns, stored alongside the table as its own B-tree, with a pointer back to the full row. Every property follows from that sentence: it costs disk because it is a copy, it speeds reads because it is sorted, and it slows writes because a copy has to be kept correct. It never changes an answer, which is why adding or dropping one is the safest performance change you will make.
- Index Day 100
- The pair of numbers that names one entry. NumPy counts from 0, so M[0, 0] is the top-left entry; mathematics counts from 1, so a paper calls the same entry a-11. The translation is exact and unavoidable: the paper's a-ij is the code's M[i-1, j-1]. This is the single most common source of off-by-one confusion when reading a paper and writing the code at the same time.
- index alignment Day 120
- The rule that binary operations between two Series (or DataFrames) compute the union of both indexes, reindex both operands onto it (filling missing positions with NaN), and only then perform the elementwise operation. Alignment happens unconditionally, whether or not the two indexes already agree.
- index alignment (filtering) Day 122
- The rule that df[mask] looks up each of df's row labels in mask's own index and uses whatever boolean sits at that label -- regardless of the physical row order mask happens to be stored in. Converting a mask to a raw array with .to_numpy() discards this label information and makes selection purely positional.
- Index seek Day 89
- Descending an index from its root to the entries that match, reading one page per level. SQLite calls it SEARCH. Its cost grows with the logarithm of the row count, which in practice means it barely grows at all: measured here at about 0.027 ms at every table size from 25,000 rows to 400,000.
- IndexError Day 48
- An error raised when you access a position in an ordered sequence (a list or tuple) that is out of range.
- indicator Day 124
- A merge() keyword that, when set to True, adds a categorical _merge column to the result recording whether each row's key matched on the left frame only (left_only), the right frame only (right_only), or both (both). The three counts must sum to the merged row count, and left_only plus both must equal the left frame's own row count whenever the left key has no duplicates.
- Individual Conditional Expectation (ICE) Day 178
- A visualization plotting individual instance prediction curves across feature values, exposing heterogeneous subgroup effects obscured by PDP.
- Inductive Bias Day 161
- The set of fundamental geometric and statistical assumptions an algorithm uses to predict outputs for unseen inputs.
- Inertia Day 142
- The k-means objective: the total squared distance from each point to its assigned centroid. It falls monotonically as k increases -- provably, because any k-cluster solution can be split into a valid k-plus-one solution that is no worse -- so minimising it always answers one cluster per point.
- infinite loop Day 51
- A loop whose stopping condition never becomes true, so it runs forever — usually a while loop whose body fails to make progress toward the condition becoming false; a bug that freezes a program and can run up cloud cost.
- Information Gain Day 162
- The reduction in entropy achieved by partitioning a node into child subsets: IG = H(Parent) - sum((N_child / N_parent) * H(Child)).
- Ingest Day 98
- The stage that brings data in from somewhere you do not control. Its whole design problem is that the source is allowed to be slow, wrong, absent or hostile, and none of those may end the run. Three defences: a timeout on every call, a bounded retry for failures that describe a moment rather than a mistake, and a result type that can represent failure instead of raising.
- inheritance Day 68
- A mechanism for one class to acquire the attributes and methods of another and to override or extend them. Written by naming the parent in parentheses. It expresses an "is-a" relationship, and its real purpose is substitutability — a subclass should be usable anywhere the parent is — with code reuse as a side effect.
- Inner dimension Day 101
- In an (m, n) @ (n, p), the n that appears on both sides. It must match because the second transformation has to accept what the first one produces, and it is then CONSUMED — it does not appear in the answer at all. It was the size of the intermediate result, and the combined transformation has no intermediate. When the two inner dimensions disagree, that is the shape error.
- Inner join Day 87
- The default join. Rows that satisfy the predicate come through, one output row per matching pair; rows on either side that match nothing are dropped. This is precisely why it is the wrong join for any question about absence — the rows you are looking for are the ones it removes.
- input Day 47
- The built-in function that reads one line from standard input and returns it as a string with the trailing newline removed; it can display a prompt first, and it always returns text — never a number.
- input contract Day 126
- A check, run before a pipeline's first step, that a frame has every required column with the required dtype. Raises immediately, naming the offending column, rather than letting a malformed frame fail confusingly several steps later.
- input validation Day 49
- Checking input at the boundary of a program to confirm it meets expectations, and refusing bad input with a clear message instead of crashing or computing a wrong answer.
- Insertion anomaly Day 87
- The failure where a fact cannot be recorded because the table has no row shape for it — an author cannot be entered until one of their books is, because every column describing the book is NOT NULL. A fact about the world with no home in your schema.
- inspection battery Day 121
- The ordered sequence of eight commands this lesson recommends running on any unfamiliar DataFrame -- .head(), .info(), .dtypes, .describe(), .isna().sum(), .nunique(), .value_counts(), memory_usage(deep=True) -- each answering a different question and together catching most of the silent load-time failures this lesson covers, in seconds.
- instance Day 67
- One object made from a particular class. Two instances of the same class have distinct identities and their own separate attribute dictionaries, while sharing one copy of every method.
- instance attribute Day 67
- A value stored in one object's own `__dict__`, usually assigned through `self` inside `__init__`. Each instance has its own, so changing one changes nothing else.
- Instance-Based Learning (Lazy Learning) Day 157
- A machine learning paradigm where the algorithm memorizes the training data and delays all computation and generalization until an inference query is received.
- Instant Day 95
- A single moment in the history of the universe, independent of any calendar, clock or place. Everything else in this lesson is a way of writing one down. An epoch count is an instant, a UTC timestamp is an instant, an aware datetime is an instant; a naive datetime is not.
- instantiation Day 67
- Calling a class to produce a new instance, as in `Account("ada", 100)`. Python creates the empty object first and then hands it to `__init__` to be filled in.
- instruction register Day 2
- The register that holds the instruction currently being decoded, parked where the control unit's decoding circuitry can examine its bits.
- instruction set Day 2
- The published catalogue of operations, visible registers, and bit encodings a processor family promises to execute — the contract between software and silicon.
- Instructive feedback Day 142
- Feedback that names the correct answer, independent of what you did. This is what supervised learning receives, and it is why the error on a training example is computable by subtraction -- which in turn is why gradient descent and every evaluation habit built on it are available.
- int Day 44
- The integer type: whole numbers of unlimited size, such as 42, 0, and -7. Immutable.
- int Day 46
- Python's integer type: an exact whole number with arbitrary precision, meaning it grows as large as memory allows and never overflows.
- Int64 (nullable integer dtype) Day 120
- A pandas extension dtype (capital I, distinct from lowercase int64) that stays in the integer family while supporting a missing-value marker (pd.NA) instead of borrowing NaN from float64. It avoids the precision loss that int64-to-float64 promotion causes past 2**53.
- Integer minor units Day 91
- Storing money as a whole number of the smallest unit — pence, cents — rather than as a floating-point number of the major unit. Binary floating point cannot represent 0.10 exactly, and in SQLite 0.1 + 0.2 = 0.3 evaluates to false. The integer stays an integer through every sum and comparison and is divided by 100 exactly once, at the point of display.
- Integer overflow Day 104
- What happens when a fixed-width integer type is asked to hold a value outside its range. In an int8 array, 127 plus 1 is -128: no exception, no promotion, and on numpy 2.5.2 no warning either — the top bit of 0111 1111 plus one carries into the sign bit. A Python int has no such limit because it grows, so this is a hazard you acquire the moment you put data into an array. It is a long-established source of exploitable bugs, because a value that should have been too large becomes negative and passes the check meant to stop it.
- integrated terminal Day 36
- A full command-line shell running inside the editor, so you can run commands, tests, and git without switching to a separate window.
- IntegrityError Day 90
- The exception raised when the data broke a rule written in the schema: UNIQUE, NOT NULL, CHECK, FOREIGN KEY, and — mildly surprisingly given the class names — a type violation in a STRICT table. It is a fact about somebody's input rather than a bug, which is why a data layer usually translates it into a domain error the rest of the program can act on.
- Intended Use Day 182
- Clear statements defining target users, domains, operational environments, and tasks for which the model was designed.
- interaction Day 137
- A feature built from more than one column, expressing something neither carries alone -- usually a ratio or a product. Measured here, income alone separated two classes at 0.54 and spend alone at 0.67, while spend divided by income separated them at 1.00.
- Interaction Feature Day 171
- A feature created by multiplying, dividing, or combining two or more distinct variables to capture joint non-linear effects.
- Interaction term Day 150
- A design-matrix column formed by multiplying two predictors together (x1 * x2), which lets one predictor's effect depend on the level of another. Measured here to cost 0.0043 of R2 when dropped from a two-predictor quadratic fit.
- interactive shell Day 11
- A shell that is reading commands a person types, as opposed to running a script non-interactively; it reads files like ~/.bashrc or ~/.zshrc.
- Intercept Day 148
- The predicted target value when the predictor is zero. Only independently meaningful when a predictor value of zero is a realistic situation; otherwise it exists to make the line fit correctly rather than to be read on its own.
- interface Day 63
- The visible contract of a piece of code — its name, parameters, return value, and the promises it makes (including how it fails) — as opposed to how it is implemented inside. Designing the interface first is where most of the design work happens.
- Internal Covariate Shift Day 208
- The historical hypothesis that the distribution of layer inputs changes during training as preceding layer parameters are updated.
- interpolate Day 125
- A pandas method that fills missing values by estimating them from surrounding non-missing values along a specified method (linear by default), rather than copying a single neighbouring value the way ffill/bfill do.
- Interpolation Day 105
- Deciding what value to use when an inverse-mapped position lands between pixels, which it almost always does. Not an error state and not a failure — it is the normal case, and the two standard answers are nearest neighbour and bilinear. Interpolation cannot recover detail that was never captured; enlarging an image gives you more pixels and not one bit more information, whatever the resampling rule.
- Interpolation and extrapolation Day 141
- Interpolation is filling in between the examples; extrapolation is answering beyond their range. Models interpolate. A nearest-neighbour regressor measured here has 0.180 error inside its training range and 139.704 outside it, and its largest prediction outside the range, 97.307, never exceeds the largest target it saw in training, 98.862 -- it structurally cannot return a value it has not seen.
- Interpolation threshold Day 145
- The point where the number of parameters equals the number of training rows, so the fit is unique and unconstrained between the points. Found here by accident: degree 24 supplies exactly 25 features, and the worst measured error occurred at exactly 25 rows.
- interpreter Day 43
- The program (run as python3) that reads Python code and executes it, either from a whole script file or one line at a time in the REPL.
- Interquartile range (IQR) Day 116
- Q3 minus Q1: the spread of the middle half of a dataset, deliberately ignoring the extreme quarter on each end, which makes it substantially less sensitive to outliers than the standard deviation.
- Interquartile range (IQR) Day 117
- The 75th percentile minus the 25th percentile of a sample -- a spread measure that depends only on the order of the data, not on its moments. Used in place of the standard deviation when comparing the Cauchy and Exponential sampling distributions, because a Cauchy sample's own standard deviation is not an estimate of anything: the population variance it would estimate does not exist.
- intersection Day 54
- The set operation `a & b` that returns only the items appearing in both sets — e.g. `{1, 2, 3} & {2, 3, 4}` is `{2, 3}`.
- invariant Day 67
- A rule that must hold for an object to be valid — the balance is never negative, the pages lent never exceed the total. A class earns its place by making an invariant impossible to break rather than merely documented.
- Invariant Day 70
- A sentence that must be true of a valid model at all times, such as "an expense amount is positive". Every invariant needs a named enforcement point; a rule with no enforcement point is a hope, not a rule.
- Inverse Day 102
- The transformation that undoes another one, so that composing the two gives the identity. For 2 by 2 it is one over the determinant times [[d, -b], [-c, a]], and it exists precisely when the determinant is not zero — the same sentence as "precisely when no area was destroyed". Often writable by reasoning rather than formula: the inverse of shear_x(2) is shear_x(-2), of scaling by 2 and 3 is scaling by a half and a third, and of a reflection is the same reflection.
- Inverse mapping Day 105
- Transforming an image by walking the OUTPUT: for each output pixel, take its centre, send it backward through the inverse matrix, and take the value it came from. Every real implementation works this way. The guarantee is structural rather than numerical — a loop over the output visits every output pixel exactly once, so "never assigned" is not a state that can occur. Two consequences: the transformation must be invertible, so a determinant of 0 fails before any pixel is touched; and the coefficients a library asks for are in the output-to-input direction, which is the algorithm showing through the interface.
- Inverse-CDF sampling Day 114
- A method for turning a single uniform draw U on (0, 1) into a sample from any target distribution, by finding the value x such that F(x) = U, where F is the target's cdf. For a discrete pmf this is "find the smallest value whose cdf is at least U"; for the exponential distribution it collapses to the closed form -ln(U) / lambda.
- Inverted Dropout Day 208
- A regularization technique that randomly zeros activations with probability p during training and scales surviving activations by 1/(1-p).
- inverted pyramid Day 133
- The ordering that puts the conclusion nearest the top and the machinery nearest the bottom, so each band is read by fewer people than the one above it. It is the exact reverse of the order in which the analyst discovered things, which is why it has to be imposed deliberately rather than falling out of how the work was done.
- IP address Day 15
- The numeric address (such as 104.20.23.154) that identifies a machine on the network, so packets can be routed to it.
- IP address Day 16
- A numeric identifier for a network interface that routers use to deliver packets; a machine's location on the network, not a permanent name for a device.
- IPC Day 2
- Instructions per cycle — how many instructions a core completes per clock tick on a given workload; performance is roughly clock speed times IPC.
- IPv4 Day 16
- The original internet addressing scheme using 32-bit addresses (about 4.3 billion), written as four numbers 0–255 separated by dots, such as 93.184.216.34.
- IPv6 Day 16
- The newer addressing scheme using 128-bit addresses, written as eight groups of hexadecimal digits, created because the IPv4 space was exhausted.
- IQR rule Day 125
- An outlier-detection rule flagging any value more than 1.5 times the interquartile range (Q3 - Q1) below Q1 or above Q3. A statistical detection procedure, not a decision about whether to remove the flagged point -- that decision is a judgement call, covered separately.
- Irreducible Error Day 177
- Noise inherent in the data-generating process that cannot be eliminated by any model regardless of capacity or dataset size.
- Irreducible error ceiling Day 141
- The maximum accuracy any model can reach on held-out data, given a known fraction of wrong labels. If a fraction r of labels is wrong, a model that recovered the underlying rule perfectly would still be marked wrong on that fraction, so the ceiling is 1 minus r. Measured here as exactly 0.750 for a 25 percent noise rate, with the best of four model families reaching 0.73725.
- Irreducible noise Day 145
- The part of the target that nothing could predict. Here it is exactly 4.0000, the square of the noise standard deviation, and two different models converge on it from opposite sides given enough data. The number that tells a project when to stop spending.
- ISO 8601 Day 91
- The international date and time notation first published in 1988, written here as YYYY-MM-DDTHH:MM:SSZ. Three properties earn it a place in a database with no date type: fields are fixed-width and most-significant-first, so text order is chronological order; it is unambiguous, unlike 01/08/2026; and it is readable by a human looking at the raw file. Because it sorts, a plain text column can carry a CHECK constraint that enforces chronology.
- ISO 8601 Day 95
- The international date and time standard, first published in 1988 and revised several times since, which orders fields from the most significant leftwards so that lexicographic order corresponds to chronological order. It is large: it also permits the basic form with no separators, week dates, ordinal dates, durations and intervals, so "valid ISO 8601" is a much weaker statement than people mean by it.
- Isolation Forest Day 187
- An unsupervised tree-based ensemble that isolates anomalies by randomly partitioning feature values.
- isolation_level Day 90
- The connection attribute controlling the module's implicit transaction handling. The default, an empty string, means the module opens a transaction for you before a data-modifying statement — but not before DDL — and keeps it open until you commit. Setting it to None turns that machinery off entirely, so BEGIN, COMMIT and ROLLBACK are yours to issue. A string such as "IMMEDIATE" changes which kind of BEGIN is emitted.
- items/keys/values Day 53
- The three dictionary view methods used to iterate: .items() yields each (key, value) pair, .keys() yields the keys, and .values() yields the values, all in insertion order.
- iterable Day 51
- Anything you can loop over — a list, string, range, dictionary, or file. A for loop asks an iterable for an iterator and then visits its items one at a time.
- iterable Day 55
- Any object you can call `iter()` on to obtain an iterator — including lists, strings, dictionaries, sets, files, and generators. It is what a `for` loop can walk over.
- IterableDataset Day 205
- A PyTorch dataset subclass implementing __iter__ for sequential, out-of-core streaming data access.
- Iteration budget Day 143
- How many times you may traverse the loop before the loop itself starts fitting your judgement to the validation data. Bounded by deciding what to try before trying it, and by counting the traversals.
- IterativeImputer (MICE) Day 174
- Multivariate Imputation by Chained Equations: modeling each missing feature as a regression function of all other features in round-robin cycles.
- iterator Day 51
- A one-use helper a loop obtains from an iterable: it remembers the current position and returns the next item each time the loop asks, signalling when the items are exhausted.
- iterator Day 55
- The object returned by `iter()` that remembers your position in a sequence and yields the next item each time `next()` is called, raising `StopIteration` when exhausted.
- iterator protocol Day 55
- The contract every iterator follows: an `__iter__` method that returns the iterator itself and a `__next__` method that returns the next item or raises `StopIteration`. It is what makes `for` work uniformly over any source.
- itertools Day 55
- A Python standard-library module of fast, lazy iterator building blocks — including `chain` (splice iterables into one stream), `islice` (slice an iterator lazily), and `count` (count upward forever).
- itertools Day 60
- A standard-library module of fast, memory-light building blocks for iterators, such as chain (join iterables end to end), islice (slice without building a list), and groupby (group adjacent equal items) — lazy pipelines over sequences.
- Jaccard similarity Day 107
- The size of the intersection divided by the size of the union of two sets: 1 for identical, 0 for disjoint. Published by the Swiss botanist Paul Jaccard in 1901 while comparing the plant species found at different alpine sites, which is exactly the situation of two lists of very different lengths. Because the union sits in the denominator, everything the two do not share is charged for in both directions — so an eleven-ingredient recipe containing all four ingredients you asked for scores 0.3636 while a three-ingredient recipe sharing two scores 0.4000. Unlike cosine distance, 1 minus Jaccard similarity is a genuine metric.
- Jacobian Day 109
- The matrix of first partial derivatives of a function that returns a VECTOR rather than a single number, with one row per output and one column per input. A gradient is the one-row case. It is named here and not developed; it becomes necessary on Day 110, because the chain rule for composed multi-output functions is a chain of matrix products.
- Jacobian Matrix Day 200
- A matrix of all first-order partial derivatives of a vector-valued function.
- JavaScript Day 20
- The programming language that runs in the browser to give a page behavior: responding to clicks, updating content, and talking to servers without reloading.
- Jensen's inequality Day 114
- For a convex function g, E[g(X)] >= g(E[X]). Its simplest case is g(x) = x^2, giving E[X^2] >= (E[X])^2 — and the gap between the two sides is exactly Var[X], since Var[X] = E[X^2] - (E[X])^2 and a variance can never be negative.
- jitter Day 27
- A small random amount added to each backoff delay so that many clients do not all retry at the same instant and stampede the server (the "thundering herd").
- jitter Day 66
- A small random offset added to each retry delay so that many clients recovering from the same outage do not retry in lockstep and knock the service over again.
- jitter Day 130
- A small amount of random noise added to a variable's plotted position -- never to the underlying data -- so that discrete or repeated values do not draw exactly on top of each other. Jitter is a deliberate, disclosed distortion of position for the sake of visibility; the caption or a stated jitter width should say so, because an unlabelled jittered axis can be read as more precise than it is.
- Jitter Day 78
- A random factor applied to each backoff delay, so clients that failed simultaneously do not retry simultaneously. Without it, a thousand clients that saw one outage all return at exactly 0.5s, 1s and 2s, and knock over the server that was just recovering. It is the cheapest reliability control in this lesson and the one most often left out.
- join Day 45
- A string method called on a separator that glues a list of strings into one, placing the separator between the pieces; the inverse of split.
- Join Day 87
- An operation that combines rows from two tables into one result, pairing each row on the left with the rows on the right that satisfy a condition you supply. Nothing is stored joined: the result is assembled when you ask and thrown away when you are done. A left row matching three right rows produces three output rows, so joining does not preserve your row count.
- join (DataFrame method) Day 124
- A DataFrame method that merges on the index rather than a column, calling merge() internally with left_index=True and right_index=True. Convenient when the join key already is a table's index.
- Join predicate Day 87
- The condition in the ON clause that decides which pairs of rows belong together, usually an equality between a foreign key on one side and a primary key on the other. On an outer join it is not interchangeable with a WHERE clause: the predicate in ON decides what counts as a match, while WHERE filters the finished result after the NULL-filling has already happened.
- joinedload Day 93
- An eager-loading strategy that adds an OUTER JOIN to the same query. One statement, at the cost of repeating every parent column once per child row — in the lab, 24 rows returned to build 6 objects. Right for many-to-one, where each child has exactly one parent and no multiplication can occur; on a collection it requires .unique() on the result, and SQLAlchemy raises if you forget, because the driver really did return those duplicate rows.
- jq Day 28
- A command-line tool that reads JSON structurally and extracts fields by path (for example .current.temperature_2m), the way grep extracts lines by pattern.
- json Day 60
- The standard-library module for the JSON data format: json.dump / json.dumps turn Python objects into JSON text, and json.load / json.loads turn JSON text back into Python objects — the safe, cross-language way to save and reload structured data.
- JSON Day 22
- JavaScript Object Notation, a simple text format of nested keys and values that is the near-universal way web APIs format their request and response bodies.
- JSON Day 24
- JavaScript Object Notation — a compact, human-readable text format for representing structured data, and the dominant format for web data exchange.
- JSON Day 65
- JavaScript Object Notation: a minimal format with exactly six types — object, array, string, number, true/false, and null. It nests arbitrarily, which is its strength, and carries no date, comment, or integer/float distinction, which is its cost.
- JSON Lines Day 65
- A convention rather than a standard: one complete JSON object per line, with no wrapping array. It combines JSON's structure with CSV's streamability, which is why training data, evaluation records, and logs use it.
- JSON parsing Day 28
- Pulling the fields you want out of a JSON response by their path, so a larger reply becomes the one or two values your program needs.
- JSON Schema Day 94
- A standard vocabulary for describing the shape of JSON data. model_json_schema() generates one from your annotations for free. It is what FastAPI publishes as OpenAPI, and it is what you hand a language model when you want structured output back — which is why the same schema can serve as documentation, as request validation and as a generation constraint.
- JSON serialization Day 56
- Turning in-memory Python data (lists, dicts, strings, numbers) into JSON text with json.dump so it can be stored or sent, and back into Python data with json.load — the encode/decode pair that lets a program save and reload its records.
- json_extract Day 92
- SQLite's function for reading a value out of a JSON document by path, as in json_extract(body, '$.title'). It returns SQL NULL for a field that does not exist, which is why a misspelled field name produces a query that silently returns nothing rather than an error — and why the audit for such documents is written WHERE json_extract(body, '$.title') IS NULL.
- Junction table Day 87
- A table whose only job is to record a many-to-many relationship, holding one foreign key to each side and keyed on the pair. Also called a bridge, link or associative table. It is not a special kind of object: it is two one-to-many relationships back to back, which is why joining across it always takes two JOIN clauses.
- Junction table Day 91
- A table whose job is to record a many-to-many relationship, holding one foreign key to each side and keyed on the pair — which is what makes it impossible to record the same relationship twice. Also called a bridge, link or associative table. It earns columns of its own the moment the relationship itself has an attribute; and when the same pair can legitimately occur more than once, it has stopped being a junction table and become an entity.
- k-anonymity Day 138
- The property that every combination of quasi-identifiers appearing in a released table appears at least k times, so no individual can be isolated to fewer than k people. Introduced by Latanya Sweeney in 2002. Bought with generalisation and suppression, and the rows suppression removes are the unusual ones -- frequently the people an analysis was supposed to be about.
- k-fold cross-validation Day 144
- Dividing the data into k parts so every row serves as test data exactly once. Six times steadier than a single holdout here, at k times the fits, and estimating the same quantity -- the two means agreed to within 0.003.
- K-Means Clustering Day 183
- A centroid-based unsupervised algorithm that partitions N observations into K disjoint clusters by minimizing within-cluster sum of squares.
- k-means++ Day 183
- An initialization scheme that selects initial cluster centers with probability proportional to their squared distance from already chosen centers.
- k-Nearest Neighbors (KNN) Day 157
- A non-parametric, instance-based classification and regression algorithm that predicts the target value of a query point by aggregating the labels of its k closest training examples.
- K, counted Day 147
- The number of candidates actually tried in a selection sweep. Day 144 named it as the number nobody remembers; this lesson counts it explicitly at 36, because the selection-optimism formula needs it as an input.
- K, counted Day 154
- The number of candidates actually tried in a selection sweep. Day 144 named it as the number nobody remembers; this lesson counts it explicitly at 23, because a defensible model comparison needs it stated, not estimated.
- Kata Day 73
- A small exercise repeated to practise a technique rather than to produce a useful artefact — the word borrowed from martial arts, the programming usage from Dave Thomas's code-kata writing in the early 2000s. Scoring a game of ten-pin bowling is the most-performed kata for test-driven development.
- KD-Tree (k-d Tree) Day 157
- A binary space-partitioning tree structure that organizes points in k-dimensional space to enable fast O(log N) nearest neighbor lookups.
- KDE boundary problem Day 130
- The fact that a standard (Gaussian-kernel) KDE has no concept of a hard boundary in the data, so a KDE of a strictly positive quantity (a price, a duration, a count) places real, non-zero density on the impossible region below zero. The fraction of mass placed there depends on how close the data sits to the boundary and how wide the bandwidth is.
- keep_default_na Day 121
- A read_csv() argument that, set to False, disables the default na_values list entirely, so no string is treated as missing unless explicitly listed in na_values yourself. The fix for the Namibia trap.
- keepdims Day 100
- An argument to every NumPy reduction that leaves a 1 in place of the axis it collapsed instead of removing it, so a (4, 4) array reduced with axis=1 and keepdims=True gives shape (4, 1) rather than (4,). It matters because a (4,) result pads on the LEFT and lines up against the columns, which is how row-centring silently becomes column-centring on a square matrix. Make it your default whenever a reduction is about to be broadcast back against the array it came from.
- kernel Day 6
- The privileged core of an operating system, running in a special CPU mode with unrestricted access to memory and devices; it contains the scheduler, memory manager, filesystems, drivers, and security machinery.
- Kernel Day 139
- The running process that actually executes a notebook's code. A kernel has its own persistent namespace -- every variable any cell has ever defined stays alive in it until the kernel is restarted or shut down, regardless of what the notebook document itself currently contains.
- kernel density estimate (KDE) Day 130
- A smooth curve estimating a distribution's probability density, built by placing a small bump (kernel, almost always Gaussian in practice) at every observation and summing them. A KDE looks more authoritative than a histogram because it has no visible bin edges, but it depends just as completely on a chosen parameter -- its bandwidth -- as a histogram depends on its bin width.
- Kernel Trick Day 169
- A mathematical technique enabling linear algorithms to operate in high-dimensional implicit feature spaces by replacing inner products with kernel functions.
- key Day 53
- The label under which a value is stored in a dictionary. Keys are unique and must be hashable (immutable), such as a string, number, or tuple of those; you fetch a value by giving its key.
- key-value pair Day 24
- A single entry inside a JSON object: a double-quoted key, a colon, and a value, such as "lat": 26.9124.
- key-value store Day 39
- A NoSQL database that works like a giant dictionary — hand it a key, get a value back very fast — ideal for sessions, caches, and simple lookups; Redis and DynamoDB are examples.
- Key-value store Day 92
- A database whose entire contract is: given a key, store these bytes; given the key again, return them. It never parses, validates or indexes the value. Lookup by the key is the fastest operation available; lookup by anything else is a scan of every key, written by you, in your own process. Redis and Memcached are the well-known ones; Python's dbm is a real one that ships with the standard library.
- keybinding Day 36
- A mapping from a keystroke to an editor action, letting frequent operations become muscle memory instead of menu hunts.
- KeyError Day 48
- An error raised when you look up a key in a dictionary that does not exist.
- KeyError Day 53
- The exception Python raises when you read a key that is not present using square brackets, e.g. d["missing"]. It signals a genuinely absent key; avoid it for optional keys with .get() or an "in" check.
- Keyset pagination Day 86
- Paging by remembering the last key you saw and asking for what comes after it — WHERE id > :last_id ORDER BY id LIMIT 20 — instead of counting rows to skip. Every page costs the same, because an index can jump straight to the starting point rather than walking to it. It is the standard fix for OFFSET on any table large enough for the problem to matter.
- keyword argument Day 57
- An argument that names the parameter it is for, such as punctuation="." in greet("Ada", punctuation="."), making it order-independent and letting the caller skip earlier optional parameters.
- keyword-only argument Day 58
- A parameter that must be passed by name rather than by position, created by placing it after a bare * (or after *args) in the signature. It keeps important options explicit and prevents a positional value from being mistaken for them.
- KL Divergence Day 186
- Kullback-Leibler divergence: a non-symmetric statistical measure of the difference between high-dimensional and low-dimensional probability distributions.
- KNNImputer Day 174
- A multivariate imputation algorithm that imputes missing coordinates using the distance-weighted average of the k nearest neighbors.
- Kolmogorov-Smirnov (KS) Test Day 195
- A non-parametric statistical test comparing the continuous empirical cumulative distributions of two independent samples.
- kw_only Day 69
- The `kw_only=True` option, making every field keyword-only in the generated `__init__`. It earns its place on records with many fields, where positional construction becomes unreadable and reordering the declarations would silently change what a call site means.
- L-infinity norm Day 107
- The largest single absolute component, computed as the limit of the p-norm rather than by substituting infinity into the formula, which overflows. The distance built from it is Chebyshev distance. Every feature except the worst one is ignored entirely, which sounds like a weakness until you meet an acceptance rule of the form "no dimension may be out by more than X" — that rule is an L-infinity ball and cannot be expressed as anything else. Its unit ball is a square. It also predicts the finishing time of a two-axis machine whose motors run simultaneously, since the slower axis alone decides.
- L1 cache Day 3
- The smallest, fastest cache, private to each CPU core and usually split into instruction and data halves; typically tens to a couple of hundred KB, reached in about a nanosecond.
- L1 norm Day 99
- The taxicab or Manhattan magnitude: add up the absolute values of the components, with no squaring and no square root. It is how far you would travel on a street grid rather than how far apart two points are as the crow flies. It is never smaller than the L2 norm of the same vector, and — the point worth remembering — it can rank two candidates in the opposite order to L2, so naming the norm is part of stating the question.
- L1 norm Day 107
- The sum of absolute values, and the distance built from it is Manhattan or taxicab distance. Every unit of difference costs the same wherever it occurs, so ten features each one out costs exactly what one feature ten out costs. Its unit ball is a diamond, with corners sitting on the axes — which is precisely why L1 regularisation drives coefficients to exactly zero and produces sparse models where L2 does not. Correct whenever movement is constrained to the axes, and often the better choice in very high dimensions.
- L2 cache Day 3
- The second cache level — larger and slightly slower than L1 (typically hundreds of KB to several MB), private to a core or shared by a cluster of cores.
- L2 norm Day 99
- The Euclidean magnitude: square every component, add the squares, take the square root. It is Pythagoras applied one dimension at a time — in two dimensions it is literally the hypotenuse of the right triangle formed by the components — and the formula is unchanged in three hundred dimensions. This is the default meaning of length, of size and of distance, and unless someone says otherwise it is what they mean.
- L2 norm Day 107
- The square root of the sum of squares, and the distance built from it is Euclidean distance: ordinary straight-line separation. Its unit ball is the familiar circle, and it is the only member of the family that ordinary geometry hands you. Squaring before summing means one large disagreement costs far more than several small ones adding to the same total, which is a real difference in behaviour and not a technicality: on four part dimensions, four errors of 0.04 cost less under L2 than one error of 0.09, and more under L1.
- L3 cache Day 3
- The largest on-chip cache level, typically shared by all cores; some designs (such as Apple's) use a shared system-level cache in the same role under a different name.
- Label noise Day 141
- Recorded outputs that are wrong: mis-entered, disputed between annotators, or genuinely ambiguous. It is the usual cause of a low ceiling, it is measured by re-labelling a sample and counting disagreements, and it cannot be fixed by a better model or by more data.
- label-then-legend pattern Day 128
- The convention of passing label= to every plot call that should appear in the legend, then calling ax.legend() once, after every relevant artist has been created. The legend's entries appear in plotting order, which is why the pattern names it "label-then" -- the labelling happens first, the single legend() call happens last.
- Labeling Function (LF) Day 191
- A user-defined heuristic function that inspects an unlabelled sample and outputs a proposed label or abstains from voting.
- Lag Feature Day 171
- A historical value of a time-series variable from k time steps prior (x_{t-k}) used to capture temporal momentum.
- LambdaLR Day 207
- A PyTorch scheduler that sets the learning rate of each parameter group to the initial lr times a user-defined lambda function.
- language server Day 36
- A separate program that understands one programming language and provides completion, go-to-definition, and error-checking to an editor, usually through the Language Server Protocol.
- Laplace (add-alpha) smoothing Day 115
- Computing P(word | class) as (count(word, class) + alpha) / (total_words(class) + alpha x vocabulary_size) rather than the raw count ratio. With alpha=1, every word in the vocabulary receives a small nonzero probability under every class, preventing a single word absent from a class's training data from forcing that class's entire probability to exactly zero.
- Laplace Smoothing (Additive Smoothing) Day 158
- A technique to smooth categorical probabilities by adding a pseudocount alpha to observed counts, preventing zero-frequency probability failures.
- Lasso Day 151
- Linear regression with an L1 penalty: the sum of squared residuals plus alpha times the sum of the ABSOLUTE VALUES of the coefficients. Measured to zero progressively more coefficients as alpha grows -- 0, then 1, then 3, then 8 of 10 over the same sweep ridge never moved on.
- LassoCV Day 151
- Scikit-learn's cross-validated lasso, which searches an alpha grid automatically rather than requiring a value chosen by eye. Measured here to pick alpha=0.07874, zeroing 4 of 10 coefficients and keeping sex, bmi, bp, s1, s3 and s5.
- lastrowid Day 90
- The rowid of the last successful INSERT on a particular cursor — which is why the cursor that execute returned is worth keeping rather than discarding. It coincides with your primary key when the column is declared INTEGER PRIMARY KEY, and does not otherwise.
- latency Day 3
- The time one access takes to complete, from request to first data — about 1 ns for L1 cache, ~100 ns for RAM, ~100 µs for an SSD random read (approximate orders of magnitude).
- latency Day 15
- The delay before data begins to arrive, dominated by round-trip time and set largely by distance; distinct from bandwidth.
- launchd Day 14
- The service manager and scheduler on macOS, introduced in 2005 and now the recommended tool there; it can also run jobs that were missed while the Mac was asleep.
- launchd Day 81
- Apple's single system for launching and supervising processes, introduced in Mac OS X 10.4 (Tiger, 2005), replacing init, startup items, inetd, cron and at. A job is described by a property list whose ProgramArguments key is argv rather than a shell command line, and it runs a job whose scheduled moment passed while the Mac was asleep.
- Law of large numbers Day 114
- As the number of independent samples n grows, a sample mean converges to the true expectation. It is why simulation works at all; it says nothing about how fast that convergence happens — that rate is the central limit theorem, covered on Day 117.
- Law of large numbers (LLN) Day 117
- Jacob Bernoulli's 1713 result that a sample mean converges to the true population mean as the sample size grows. A weaker claim than the central limit theorem: the LLN says convergence happens; the CLT says how fast (1/sqrt(n)) and what shape the errors take (Normal, given finite variance) along the way.
- Law of total probability Day 113
- P(A) = sum over i of P(piece_i) x P(A | piece_i), for any partition of the sample space into non-overlapping pieces. Used across two urns of different composition in this lesson, checked against a direct enumeration of the combined experiment. Day 115's Bayes' theorem runs this exact computation backwards, with this rule supplying its denominator.
- Lax mode Day 94
- pydantic v2's default. Conversions that are unambiguous and lossless are performed: "42" becomes 42, "14.8" becomes 14.8, 3 becomes 3.0, a tuple becomes a list. Conversions that would lose information are refused: 42.7 as an int fails with int_from_float rather than silently truncating. Verified in pydantic 2.13.4 by asking, not by reading.
- Layer Normalization Day 208
- A normalization layer that standardizes activations across the feature/channel dimensions of a single sample independently of other batch samples.
- layout Day 20
- The pipeline step, also called reflow, in which the browser computes the exact size and position of every element in the render tree.
- lazy Day 38
- A quantifier made non-greedy by adding ?, which matches as little text as possible; .*? stops at the first point that lets the rest of the pattern succeed.
- lazy evaluation Day 55
- Computing a value only when it is actually needed, and only as much as is consumed. Generators use lazy evaluation to process arbitrarily large streams while holding almost nothing in memory.
- Lazy formatting Day 97
- Passing the template and the arguments separately — log.info("saw %s", n) — so that the joining happens inside the handler only if a record will actually be emitted. Measured here: a thousand suppressed DEBUG calls render the argument zero times this way and a thousand times with an f-string. The second and better reason applies even when the record IS emitted — the unformatted template survives as record.msg, so a structured backend can group every occurrence of one event.
- Lazy loading Day 93
- The default strategy for a relationship: the related rows are not fetched until the attribute is touched, and touching it issues a SELECT then and there. It makes member.loans look like a list attribute when it is a query in disguise, which is convenient exactly until it is inside a loop.
- LBYL Day 66
- "Look before you leap" — test a precondition before acting. Genuinely better when the check is cheap and the failure common in a hot loop, or when a value must be validated for policy reasons rather than mechanical ones.
- Leaf Node Day 162
- A terminal node in a decision tree that contains no child branches and assigns a final class prediction (or continuous average) to all arriving samples.
- Leaf Tensor Day 204
- A tensor created directly by the user (such as model weights or inputs) that is not the output of a tracked operation.
- Leaf-Wise (Best-First) Growth Day 165
- A tree growth strategy that greedily splits the leaf node with the highest loss reduction across the entire tree, resulting in asymmetric depth.
- leakage Day 137
- Information reaching the model that will not be available at the moment a prediction is actually needed. It is invisible from the inside because it makes results look better rather than worse, which is why the only reliable symptom is a score that is better than the problem allows.
- leakage audit Day 137
- A reusable check over a feature table and a target. The version in this lesson has three named rules: correlation above a threshold, perfect separability by a single threshold, and a non-numeric column whose every category maps to one target value. It caught both planted leaks and flagged no honest column -- and the numeric leak was caught by separability, not correlation, because its correlation of 0.8468 was under the 0.90 threshold. It cannot see contamination, unavailability at prediction time, or a value backfilled from the future.
- Leaked feature Day 140
- A variable whose value could not have been known at the moment the prediction or comparison is meant to apply to -- for example, a "days since last login" measured up to the moment an account closed. The resulting chart or model is accurate about the past and useless about the future.
- Leaky ReLU Day 198
- A variant of ReLU that introduces a small positive slope alpha (e.g., 0.01) for negative inputs to prevent gradient starvation.
- Leaky selection Day 147
- Choosing a winning configuration by fitting every candidate and scoring each one directly against the test set, instead of selecting on cross-validated training rows. Measured here at a mean gap of +0.0096 over 20 seeds, and never negative at any seed tried.
- Leaky selection Day 154
- Choosing a winning configuration by fitting every candidate and scoring each one directly against the test set, keeping the lowest RMSE, instead of selecting on cross-validated training rows. Measured here at a mean gap of +0.5279 RMSE points over 20 seeds, and never negative at any seed tried.
- Leap second Day 95
- An extra second inserted into UTC to keep it in step with the Earth's rotation, which is neither constant nor predictable. During one, a UTC minute genuinely contains sixty-one seconds and is labelled 23:59:60. Python's datetime cannot represent it — datetime(2016, 12, 31, 23, 59, 60) raises ValueError — because it implements an idealised time in which every day has exactly 86400 seconds. Many large operators now smear the extra second across a day so no clock ever shows :60.
- Learning curve Day 145
- Training and test error plotted against training-set size. It tells you what more data would buy before you buy it: converged curves sitting high mean bias-limited and no amount of data will help.
- Learning Curve Day 177
- A plot of model training error and validation error as a function of the training dataset sample size.
- Learning rate Day 111
- The scalar eta that decides how far one gradient-descent step actually moves, written x <- x - eta*grad(x). It never changes the direction of the step, only its length. Too small wastes steps converging correctly; too large overshoots, and past a sharp boundary the run diverges outright.
- Learning Rate Schedule Day 201
- A predefined policy that dynamically reduces the learning rate alpha across training epochs to ensure fine convergence near the minimum.
- Learning Rate Schedule Day 207
- A predetermined or metric-driven policy that adjusts the optimizer learning rate dynamically across training epochs or steps.
- Learning-rate sweep Day 112
- Running the same optimization, from the same start, for the same number of steps, once per learning rate across a range of values, then plotting the final loss against the rate. Its characteristic shape is slow convergence at the low end, a broad basin of good rates, and a sharp cliff at the stability threshold beyond which every run diverges.
- least privilege Day 25
- The practice of giving a credential the narrowest access that still does the job (read-only, one project, limited spend) so that a leak has the smallest possible blast radius.
- Leave-One-Out (LOOCV) Day 167
- An extreme form of K-Fold where k = N, training on N-1 instances and testing on the single remaining instance.
- left_on / right_on Day 124
- merge() keywords naming the join column on the left frame and the right frame separately, used when the two frames' key columns have different names. on= is shorthand for the common case where both sides share the same column name.
- Leftmost prefix Day 89
- The rule that a composite index on (a, b, c) can seek on a, on (a, b) and on (a, b, c), and cannot seek on b, on c, or on (b, c). The order in which conditions appear in a WHERE clause is irrelevant — the planner reorders them freely; the order of columns in the index is what decides.
- LEGB rule Day 58
- The order in which Python resolves a name: Local, then Enclosing, then Global, then Built-in, taking the first scope that defines the name. If no scope has it, Python raises NameError.
- Level band Day 112
- A range of values shaded with one character or colour. This lesson's ASCII and Pillow contour renderers both shade by level band: every grid cell is assigned to a band by where its value falls between the grid's own minimum and maximum, and the boundary between two bands is wherever two adjacent cells happen to land in different bands.
- Level inflation Day 97
- The failure mode where routine events are logged at WARNING because they felt important while being written, until the warnings stop being read and the one that mattered is invisible. A level is a promise to the reader about what it costs them to ignore the line; break it often enough and the levels carry no information at all.
- Level set Day 109
- The general name for the set of points where a function takes one fixed value, of which a contour line is the two-input case. For a function of three inputs it is a surface rather than a curve — Wikipedia notes that "a level surface in three-dimensional space is defined by an equation of the form F(x, y, z) = c" and that "the gradient of F is then normal to the surface". The perpendicularity result survives every increase in dimension; only the picture stops being drawable.
- Level-Wise (Depth-First) Growth Day 165
- A tree growth strategy that splits all nodes at the current depth simultaneously before moving to the next level, producing balanced trees.
- Leverage Day 116
- In a fitted regression line, a measure of how much a single point's X-VALUE ALONE (before its y-value is even considered) could determine the line. Depends only on the x-values, so datasets sharing an x-column share identical leverage; in Anscombe's quartet, set IV's one non-repeated x-value carries almost all the leverage.
- Leverage Day 148
- A measure of a point's potential to pull a fitted line toward itself, computed from its predictor value alone -- before its target value is even considered. Measured at 0.8048 for one added point against a mean of 0.0299 for forty ordinary points, a ratio of nearly 27.
- LibLinear Day 169
- An open-source C++ library for large-scale linear classification and regression, serving as the backend for scikit-learn LinearSVC.
- Lie factor Day 132
- Edward Tufte's measure of graphical distortion, from The Visual Display of Quantitative Information (1983): the size of the effect shown in the graphic divided by the size of the effect in the data. It is unitless -- a ratio of two ratios -- and equals 1.0 when the picture faithfully reproduces the data's effect. Tufte's rule of thumb treats anything outside roughly 0.95 to 1.05 as a distortion. Its value is that it turns "this chart is misleading" from an opinion into arithmetic.
- Lie factor Day 140
- Edward Tufte's ratio of the size of an effect as shown in a graphic to the size of the effect in the data. A truncated baseline on a ratio quantity inflates it; a chart designed to be honest keeps it at or near 1. Day 132's measure, applied here to the worked study's figures.
- LightGBM Day 165
- A Microsoft open-source gradient boosting framework optimized for high speed and low memory using histogram binning, leaf-wise growth, GOSS, and EFB.
- Likelihood Day 115
- P(evidence | hypothesis), how probable the observed evidence is, assuming the hypothesis is true. In the opening scenario, the likelihood of a positive test given the condition is the sensitivity, 99/100.
- Likelihood ratio Day 115
- For a positive result, LR+ = P(positive | hypothesis) / P(positive | not hypothesis) -- sensitivity divided by the false-positive rate. A likelihood ratio greater than 1 means the evidence favours the hypothesis; a likelihood ratio of exactly 1 means the evidence is worthless for distinguishing the hypothesis from its negation.
- Limit Day 108
- The single value a sequence or an expression gets arbitrarily close to, without necessarily ever reaching it. The secant slopes over [3, 3 + h] for h = 1, 0.1, 0.01, 0.001 are 7, 6.1, 6.01 and 6.001, and their limit as h goes to zero is 6. The limit is not "what you get when h equals zero" — at h = 0 the expression is 0 ÷ 0 and means nothing. It is what the values settle on as h approaches zero, from both directions.
- Line coverage Day 77
- The fraction of executable lines that ran at least once during a test run. The cheapest coverage measure and the least informative: a line containing a condition counts as covered as soon as it runs, whichever way the condition went.
- Linear combination Day 101
- A weighted sum of a set of vectors — so many copies of the first, plus so many of the second, and so on. The key to matrix-vector multiplication: A @ v is a linear combination of A COLUMNS, with the entries of v as the weights. This picture explains at once why the output has as many entries as A has rows, why v must have one entry per column, and why the answer can never land outside the space A columns reach.
- Linear convergence Day 112
- A convergence pattern where the error shrinks by roughly the same multiplicative ratio r at every step: loss_n is approximately c times r to the n. Its defining signature is a straight line on a log-scaled loss-against-iteration plot.
- Linear in the parameters Day 150
- The defining property of a linear model: the prediction is a linear combination of the coefficients, regardless of what nonlinear functions of the raw inputs feed into it. A curve in x can still be a straight fit in the coefficients, which is what lets a polynomial model use ordinary least squares.
- Linear Pre-Activation (Z) Day 199
- The intermediate affine transformation Z = W * A_prev + b computed at each neuron before applying the non-linear activation function.
- Linear Separability Day 197
- A geometric property where two classes of data points can be completely divided in N-dimensional space by a single (N-1)-dimensional hyperplane.
- Linear transformation Day 102
- A function taking a vector and returning a vector that satisfies exactly two conditions: it preserves addition, so f(u + v) equals f(u) + f(v), and it preserves scalar multiplication, so f(cu) equals c f(u). Nothing else is in the definition. Every geometric fact about them — that the origin never moves, that straight lines stay straight, that evenly spaced points stay evenly spaced — is a consequence of those two lines rather than an addition to them. In two dimensions every such function can be written as a 2 by 2 matrix, and every 2 by 2 matrix is one.
- Linear Warmup Day 207
- Gradually increasing the learning rate from near zero to the peak target learning rate over the initial training iterations.
- Linearity assumption Day 148
- The claim that the true relationship between predictor and target is a straight line. Broken by construction in this lesson's curved dataset, where an R-squared of 0.852 gave no warning and only the binned residual means -- +4.2216, -1.9594, -3.6829, -2.3803, +3.8010 -- revealed the missed curve.
- Linearly Separable Day 156
- A dataset property where two classes can be divided with 100% accuracy by a single flat hyperplane without any misclassifications.
- Linkage Criterion Day 184
- The metric function determining the distance between two sets of observations as a function of pairwise distances between points.
- linter Day 37
- A static-analysis tool that reads source code without running it and reports likely bugs and bad patterns, such as unused variables or unquoted values, each with a file, line, and message.
- linter Day 61
- A tool that analyses source code without running it and reports likely problems and style violations — unused imports, undefined names, shadowed variables, lines that break PEP 8. In Python, Ruff and flake8 are popular linters; a linter finds issues but generally does not rewrite your code.
- Linter Day 76
- A program that reads your source code without running it and reports patterns that are usually mistakes — an unused import, a variable assigned and never read, a mutable default argument. Named after Stephen Johnson's `lint` for C in 1978, itself named after the fluff a dryer's lint trap catches. A linter recognises shapes; it does not understand your problem.
- Linux distribution Day 6
- A complete product (Ubuntu, Debian, Fedora, Arch) that packages the Linux kernel with installers, a package manager, default tools, and an update policy.
- list Day 52
- An ordered, mutable sequence of items written with square brackets, e.g. `[10, 20, 30]`; Python's default container for holding several things in order, implemented under the hood as a dynamic array of references.
- list comprehension Day 55
- A single expression in square brackets `[...]` that builds a list by mapping and optionally filtering an existing iterable — for example `[n * n for n in numbers if n % 2 == 0]`.
- list method Day 52
- A function attached to a list object and called with dot notation, such as `a.append()`, `a.sort()`, or `a.pop()`. Most list methods mutate the list in place; the ones that are not retrievals return None.
- listening Day 17
- The state of a server socket that has claimed a port and is waiting for incoming connections addressed to it.
- Listwise Deletion (Complete Case Analysis) Day 174
- Discarding any observation that contains one or more missing values across any feature column.
- literal Day 38
- A character in a pattern that matches itself, such as the a, b, and c in the pattern abc.
- Literal Day 69
- An annotation restricting a value to a fixed set of constants, such as `Literal["train", "test"]`. It lets a checker catch a misspelled mode string that a plain `str` annotation would wave through.
- Literal Day 75
- An annotation restricting a value to a fixed set of constants, such as `Literal["semantic", "keyword"]`. It turns a misspelled mode string from a shrug at runtime into an error before you run, and it expresses a constraint a plain `str` cannot communicate to anybody.
- literate programming Day 133
- Donald Knuth's 1984 idea that a program should be written as a document for humans with the code embedded in the explanation. It reached statistics through Sweave (Friedrich Leisch, 2002), then knitr (Yihui Xie, 2012) and R Markdown, and then Quarto (Posit, 2022) -- the lineage behind every tool that renders prose and computed output from one source.
- Liveness Probe Day 194
- A health check endpoint verifying that a container process is running and has not deadlocked or hung.
- Lloyd Algorithm Day 183
- An alternating optimization heuristic that iterates between assigning points to nearest centroids (E-step) and updating centroids to cluster means (M-step).
- loc Day 94
- A tuple locating one error inside the input: ("humidity_pct",) for a top-level field, ("station", "code") for a field of a nested model, (1, "station") for the second element of a validated list. It uses the alias when the field has one, because the report has to name the key the caller actually sent. Together with type it forms the part of a ValidationError that is safe to write tests against.
- local (scope) Day 58
- The innermost scope: the names inside the function currently running, including its parameters and any variables it assigns. Assigning to a name inside a function creates a local by default, keeping the function's bookkeeping private.
- Local derivative Day 110
- The derivative of a single operation with respect to one of its own inputs, evaluated at the value that actually arrives at that operation. For a product the local derivative with respect to one factor is the other factor; for tanh it is 1 minus tanh squared; for an addition it is 1. The chain rule multiplies local derivatives, so getting the evaluation point wrong corrupts the whole product.
- Local Interpretability Day 178
- Explaining the exact contribution of each feature towards a single specific individual prediction.
- Local Outlier Factor (LOF) Day 187
- A density-based algorithm measuring the local deviation of a given data point with respect to its neighbors.
- locality of reference Day 3
- The tendency of programs to reuse recently touched data (temporal locality) and to touch data near recently touched data (spatial locality) — the property that makes caching work.
- Lock Day 96
- A mutual-exclusion primitive that makes a critical section indivisible: only one thread may be inside it at a time. threading.Lock, used as a context manager, is the direct fix for a lost-update race. It is also a claim you have to maintain everywhere and forever, because a single code path that touches the shared state without taking the lock reintroduces the bug silently — which is why a queue is usually the better answer.
- lock file Day 13
- A file written by the manager recording the exact versions of every package actually installed, so another machine can rebuild the identical environment.
- Lock file Day 81
- A file used to ensure only one copy of a job runs at a time. Done properly with fcntl.flock and LOCK_NB, which is atomic to acquire and is released by the kernel when the process exits however it exits. Done naively as "if the file exists, exit", it has a race between check and create and leaves a stale file that blocks every future run.
- Lock file Day 84
- A file created with the O_CREAT and O_EXCL flags, which the operating system guarantees will succeed for exactly one caller, used to stop two runs of the same job overlapping. It holds the process id so a human can distinguish a live run from a lock left behind by a crash. It is reliable on one machine and one local filesystem, and it is not a distributed lock.
- log Day 40
- A timestamped record of a single event that happened in a system, such as a request completing or an error occurring — the diary of the system, one line per event.
- Log level Day 84
- The severity attached to a record, deciding what is shown and what is stored. Debug reconstructs one specific run; info records the beginning, the per-item outcomes and the end of every run; warning marks a retry or a skipped item; error marks an item that failed after every attempt; critical marks a run that cannot continue at all.
- Log level Day 97
- A severity, both a name and a number: DEBUG 10, INFO 20, WARNING 30, ERROR 40, CRITICAL 50, with NOTSET at 0 meaning "ask my parent". The numbers rise in tens so a custom level can be inserted between two of them. Note that syslog, where the idea comes from, numbers them the other way round: there a lower number is more severe.
- Log rotation Day 97
- Bounding a log file so it cannot fill the disk. RotatingFileHandler renames by size — app.log becomes app.log.1, .1 becomes .2, and the file that would have become .4 is DELETED, because backupCount is how much history you keep. TimedRotatingFileHandler does the same on the clock, naming the rolled file by date. Size-based rotation bounds your disk; time-based rotation bounds your search.
- log scale Day 128
- An axis scale (set with set_yscale('log') or set_xscale('log')) where equal steps represent equal ratios rather than equal differences. It has no representation for zero or negative values -- matplotlib does not raise an error over this, it silently narrows the rendered range to exclude non-positive values, leaving the underlying data untouched but the affected points undrawn.
- log scale Day 130
- An axis on which equal visual distances represent equal multiplicative factors (each step is a times-ten, or a doubling) rather than equal additive amounts. It compresses a long right tail and makes proportional differences comparable across orders of magnitude, at the cost that zero and negative values have no position on the axis at all (Day 128).
- Log Transformation Day 189
- Applying y = log(1 + x) to compress exponential right-skewed feature ranges into symmetrical bell-shaped distributions.
- Log-Likelihood Day 158
- The natural logarithm of a likelihood function, transforming fragile multiplication of small probabilities into stable numerical addition.
- log-scaled axis Day 131
- An axis on which equal visual distances represent equal multiplicative (percentage) changes rather than equal additive changes. A series growing by a constant percentage every period is collinear (a straight line) on a log-scaled axis, while constant additive (linear) growth is not; Day 128 additionally established that a zero value has no logarithm and silently vanishes from a log axis.
- Log-space underflow Day 115
- The failure that occurs when multiplying many small probabilities together as plain float64 numbers: the true product can be far smaller than float64's smallest representable positive value (about 5e-324), and the computed result becomes exactly 0.0. Multiplying 500 factors of 0.01 demonstrates this directly. The fix is summing the logarithms of the factors instead, which stays finite.
- Logged policy data Day 142
- A record of the actions a policy took and the rewards they earned. It is not a supervised dataset, because the alternatives were never observed and the missing rows correlate exactly with the question you want answered.
- Logger Day 97
- The object you call. It has a dotted name, so myapp.loader is a child of myapp which is a child of the root, and configuring an ancestor configures everything beneath it. It has a level, which is the FIRST of two gates a record must pass. Always obtained with logging.getLogger(name), never constructed: getLogger returns the same object for the same name from a module-level registry, which is what makes the hierarchy work at all.
- logging Day 14
- Writing a record of what a program did — usually timestamped lines appended to a file — which is essential for unattended jobs that have no screen to watch.
- logging.exception Day 66
- The logging call that records a message plus the full chained traceback at ERROR level. It reads the exception currently being handled, so it is only ever called from inside an except block.
- logic gate Day 1
- A small circuit built from transistors that computes a simple rule, such as AND (output on only if both inputs are on), OR, or NOT.
- Logical evaluation order Day 86
- The order the engine conceptually runs the clauses: FROM, WHERE, GROUP BY, HAVING, SELECT, DISTINCT, ORDER BY, LIMIT and OFFSET. It is deliberately not the order you write them, and almost every confusing rule in SQL is a consequence of the gap. A query optimiser may reorder the physical work, but it must produce the result this order describes.
- logical operator (and / or / not) Day 50
- The operators that combine booleans: `A and B` is true only when both are true, `A or B` is true when at least one is, and `not A` flips true to false. In Python `and`/`or` return one of their operands, not a fresh boolean.
- login shell Day 11
- The first shell of a session, such as the one an SSH connection or a new macOS Terminal tab starts; it reads profile files like ~/.bash_profile or ~/.zprofile.
- Logistic Regression Day 155
- A linear classification algorithm that models the probability of a binary outcome by applying the logistic sigmoid function to a linear combination of features.
- Logit (Log-Odds) Day 155
- The natural logarithm of the odds of an event: logit(p) = ln(p / (1 - p)). It serves as the link function in logistic regression.
- Logits Day 199
- The raw, unnormalized real-valued outputs of the final linear layer prior to probability calibration via Sigmoid or Softmax.
- LogRecord Day 97
- The object created when a call passes the logger's level: the unformatted template, the arguments, the level, the logger's name, the creation time, the file and line, the exception information, and anything supplied through extra=. Note what it is not — it is not a string yet. Nothing has been formatted.
- London school Day 73
- Also called mockist or outside-in TDD. You start at the entry point, replace every collaborator with a test double, and assert on interactions — which methods were called with which arguments. It applies strong design pressure to interfaces at the cost of tests coupled to how the code works.
- long format Day 124
- A table layout with one row per individual measurement, carrying a column naming which measurement it is and a column holding its value. The shape groupby, most aggregation functions, and most plotting libraries expect a categorical variable to be in.
- long-form (tidy) data Day 129
- A table shaped with one row per observation and one column per variable -- the shape seaborn's hue=, size=, style=, col= and row= arguments require, because each one names a column that must exist. Day 124's melt is the standard way to convert a wide table (one row per group, one column per condition) into long form.
- Lookahead Bias Day 167
- A temporal data leakage error where information from future timestamps is inadvertently used to train a model predicting past or present events.
- Lookahead Bias Day 180
- Temporal leakage where future timestamps or future aggregate statistics are used to predict past/current events.
- Lookahead Bias Day 192
- A form of data leakage where future information is inadvertently used to train a model predicting past or current events.
- loop Day 12
- A construct that repeats a block of commands: `for` iterates over a known list, while `while` (and `until`) repeats based on a command's exit code.
- loop else Day 51
- An optional else clause on a for or while loop that runs only if the loop finished without ever hitting a break — the natural home for a "searched everything and never found it" branch.
- loopback Day 16
- The special address 127.0.0.1, which always means "this very machine"; part of the 127.0.0.0/8 range.
- Loss Day 152
- What an algorithm minimises while fitting a model, established on Day 149. Distinct from a metric, which is what you report afterward to judge the result -- the two need not be the same function, and this lesson covers the reporting side.
- Loss curve Day 112
- A plot of a loss value against training iteration. Read on a linear axis it shows whether the loss is decreasing; read on a log axis, for a linearly convergent method, it becomes a straight line whose slope is the convergence rate itself.
- Loss function Day 108
- A single number measuring how wrong a model's predictions are on some data, built so that smaller is better. Training is the search for the settings that make it small, which turns the whole of machine learning into a minimisation problem — and makes the derivative, whose sign says which way is downhill, the object worth having. Day 111 writes the loop that follows it.
- Loss function Day 149
- A rule that turns one candidate line's residuals into a single number to minimise. Not a fixed property of "doing regression" -- a choice, made explicitly here between squared error, absolute error and a blend of the two.
- Loss versus metric Day 149
- A loss is the function an algorithm optimises during fitting; a metric is the function you report to judge the result. They need not be the same function -- a model can be fit with squared error and reported with mean absolute error, or fit with Huber and reported with R squared. Day 152 owns metrics as a subject.
- lossless compression Day 5
- Compression that lets the original data be reconstructed exactly (for example PNG or ZIP).
- lossy compression Day 5
- Compression that discards some detail to shrink data further, which cannot be perfectly reversed (for example JPEG or MP3).
- Low-rank adapter Day 101
- A way of adjusting a large layer by inserting a narrow detour: a wide input passes through one small matrix down to a few dimensions and back out through another. Its cost depends entirely on the association order — keeping the brackets so the batch meets the narrow matrices first costs 67 million multiplications on typical shapes, while multiplying the two small matrices together first builds a full wide matrix and costs 17.3 billion for the identical answer, a factor of 258.
- lru_cache Day 62
- A decorator from Python's functools module (functools.lru_cache) that memoizes a function's results automatically — "least-recently-used cache". Adding @lru_cache(maxsize=None) above a naive recursive Fibonacci makes each value compute once; fib.cache_info() reports the hits and misses.
- LSP Day 36
- The Language Server Protocol, a common language (introduced by Microsoft in 2016) that lets an editor talk to a separate language server, so many editors can share expert completion and error-checking for the same programming language.
- lstsq Day 153
- A least-squares solve that factors the design matrix X directly rather than forming and inverting X'X. Measured here to agree with sklearn to 1.1990e-12, because it never squares X's condition number the way the normal equations do.
- machine code Day 1
- The raw binary instructions a CPU executes directly, the lowest-level form of any program.
- machine code Day 2
- The raw binary instructions, encoded per an instruction set, that a CPU executes directly.
- Machine learning Day 141
- Function approximation from examples. You choose a family of candidate functions and a way of scoring a candidate against your examples, and a search returns the member of the family that scores best. Nothing else is required for the definition -- in particular, no understanding, no reasoning and no model of the world.
- MAE Day 152
- Mean absolute error -- the average of the absolute value of every residual. In the target's own units. Weighs every error equally, so it is dominated by the typical case rather than by a handful of large misses.
- magic bytes Day 5
- A short signature at the start of a file that identifies its true format regardless of the filename extension.
- Magnitude Day 99
- How long a vector is, written with bars around it as the magnitude of v. Also called the length or the norm. Unqualified, it always means the L2 norm. The zero vector has magnitude 0 and every other vector has a positive magnitude — a magnitude is never negative, because it comes out of a square root of a sum of squares.
- Mahalanobis distance Day 107
- Euclidean distance measured after accounting for how the data actually varies. Take the difference between two points and, instead of dotting it with itself, dot it with itself through the inverse covariance matrix. Published by Prasanta Chandra Mahalanobis in "On the generalised distance in statistics" in 1936, from the anthropometric problem of comparing populations across correlated measurements in different units. Substituting the identity matrix recovers ordinary Euclidean distance exactly, which is the cleanest statement of what the covariance contributes. It needs an invertible covariance, so it requires more rows than columns and no duplicated features, and each distance costs a matrix-vector product rather than a subtraction.
- Mahalanobis Distance Day 187
- A multi-dimensional generalization of measuring how many standard deviations away point x is from sample mean mu.
- main Day 31
- The conventional name of the default branch that holds the primary, shippable line of a project's history (older projects often call it master).
- main guard Day 49
- The line `if __name__ == "__main__":` at the bottom of a file, which runs the program's startup code only when the file is executed directly, not when it is imported.
- Majority Voting Day 163
- The ensemble aggregation rule where each base classifier casts one vote for a predicted class, and the class with the most votes is chosen.
- Majority-class baseline Day 141
- A predictor that ignores the input entirely and always answers with the most common class. It is the cheapest meaningful comparison for a classifier, and a model that cannot beat it has demonstrated nothing. Measured here at exactly 0.900 on a dataset where two trained models scored 0.821 and 0.817.
- Majority-class baseline Day 147
- The accuracy of predicting the most common class every time, with no model at all. Every model in this lesson has to clear it to be worth building -- here, 0.6316 -- and it is computed before any model is fitted, not after, as a check on whether the whole exercise is worth doing.
- man page Day 8
- A command's built-in reference manual, shown by the `man` command (for example `man ls`); you scroll with the arrow keys and press `q` to quit.
- man-in-the-middle attack Day 19
- An attack in which someone secretly sits between you and a server, reading or altering traffic while both sides believe the line is private; authentication in TLS is designed to prevent it.
- Manhattan distance Day 107
- The L1 distance: the sum of the absolute differences, feature by feature. Named for the street grid, with the phrase "taxicab geometry" popularised by Karl Menger in the 1950s. It is the correct and exact answer whenever movement is axis-by-axis rather than diagonal — for a warehouse picker walking aisles, six metres across and eight along really is fourteen metres, and the Euclidean answer of ten is a distance nobody can travel.
- Manhattan Distance (L1 Norm / Cityblock) Day 157
- The sum of absolute coordinate differences between two points: d(x, z) = sum |x_i - z_i|.
- manifest Day 13
- A file you write that lists the packages a project needs — its stated intent — turning "install everything this needs" into one shareable, repeatable command.
- manifest Day 126
- A small JSON record tying a pipeline's output back to its origin: the input's content hash, the configuration's hash, the step log, and the output's content hash. The only thing that makes "which data produced this number?" answerable months later without guessing.
- Manifest Day 140
- A file recording a cryptographic digest -- here SHA-256 -- for every output a pipeline generates. It turns "it reproduces" from a belief into a two-second check, and it fails loudly when a generated file is edited by hand, which is how most reproducible pipelines actually die.
- Manifest Day 143
- A set of content hashes over the pipeline's inputs and outputs, letting two runs be compared exactly. The same primitive as a package lock file or a container digest, answering the same question: is what I have now the thing I checked before?
- mantissa Day 4
- The significant-digits field of a floating-point number (also called the significand or fraction), which controls precision; float32 gives it 23 bits.
- mantissa Day 46
- The field of a floating-point number that holds its significant binary digits (also called the fraction); a 64-bit double has 52 mantissa bits, which set its precision.
- MAPE Day 152
- Mean absolute percentage error -- the average of each residual divided by its true value, expressed as a percentage. Undefined at a true value of zero; scikit-learn does not raise or warn there, it floors the denominator at machine epsilon and returns a huge, silently wrong number -- measured here at roughly 5.6e15.
- MAPE's structural asymmetry Day 152
- The verified, narrow claim about MAPE's directional bias: the worst possible systematic under-prediction (always guessing zero) caps out at 100 percent, while over-prediction has no ceiling -- measured here at 1.0 versus 10.0 for an eleven-times over-prediction. Narrower than the folklore claim that equal-magnitude errors are scored unequally, which does not hold under direct construction.
- Marching squares Day 112
- An algorithm that traces a level LINE rather than shading a level band: for one specific value, it finds exactly where that value's curve crosses each grid cell's edges by linear interpolation, then connects the crossings into a smooth line. matplotlib's contour function implements this; this lesson describes it but implements only the simpler level-band version.
- Margin Day 156
- The geometric distance between the decision boundary and the nearest training data points of any class.
- Marker Day 72
- A label attached to a test with @pytest.mark.<name>. A marker does nothing by itself; it exists so that -m can select or deselect the tests carrying it. Markers should be registered in configuration, and with --strict-markers a mistyped one becomes an error instead of a silent no-op.
- math.isclose Day 46
- A function in the math module that reports whether two floats are equal within a small tolerance; the correct way to compare computed floats instead of using ==.
- Matrix Day 100
- A rectangular grid of numbers arranged in rows and columns, every row the same length. The definition is almost useless on its own, because it says what a matrix is made of and nothing about what it means. In practice a matrix is at least three things at once — a table of data, a collection of vectors, and a transformation — and knowing which one is in play is the whole skill.
- Matrix Factorization Day 188
- Decomposing a sparse user-item interaction matrix into low-rank latent user and item embedding vectors.
- Matrix product Day 101
- The operation written A @ B, whose entry (i, j) is row i of A dotted with column j of B. The recipe is the coordinate form of something simpler: A @ B is the single transformation that does B and then does A. Cayley defined it this way in 1858 precisely because it was the operation corresponding to composing two linear substitutions, so composition is the definition and the recipe is the consequence, not the other way round.
- Matthews Correlation Coefficient (MCC) Day 159
- A balanced metric for binary classification quality ranging from -1 to +1, computed directly from all four confusion matrix quadrants.
- Matthews Correlation Coefficient (MCC) Day 176
- A balanced metric for binary classification that takes into account true/false positives and negatives, robust to severe class imbalance.
- Maximum Likelihood Estimation (MLE) Day 155
- A method of estimating model parameters by maximizing the likelihood function so that the observed data becomes most probable under the model.
- Mean Day 116
- The arithmetic average: the sum of every value divided by the count. It is the single value that minimises the sum of squared distances to every point in the dataset. Its breakdown point is exactly zero -- one arbitrarily extreme value can drag it to any value at all.
- Mean Decrease in Impurity (MDI) Day 163
- Feature importance computed by accumulating the total weighted impurity reduction brought by a feature across all nodes in all trees in the forest.
- Mean Decrease in Impurity (MDI) Day 178
- Tree-based feature importance measuring total reduction in split criterion, susceptible to inflating cardinality and in-sample overfitting.
- mean imputation Day 125
- Replacing a column's missing values with that column's own mean, computed over the non-missing values. Leaves the column's mean exactly unchanged by construction, while strictly shrinking its standard deviation and strictly attenuating (never inflating) its correlation with any untouched column -- because an imputed value's deviation from the mean is exactly zero.
- mean imputation Day 126
- Filling a missing value with the column's own mean (Day 125). Idempotent in a pipeline only if no later step can reintroduce a missing value into that column -- otherwise a second run can compute a different mean from an already-imputed column.
- Mean squared error Day 149
- Squared error divided by the row count. The per-row average of the loss actually minimised; distinct from root mean squared error, which is a metric reported in the target's own units -- Day 152's subject, not this lesson's.
- Mean-predictor baseline Day 154
- The RMSE and R2 of predicting the training mean for every test row, with no model at all. Every model in this lesson has to clear it to be worth building -- here, 70.4637 RMSE -- and it is computed before any model is fitted, not after, as a check on whether the whole exercise is worth doing.
- measurement bias Day 138
- Error introduced when what gets recorded is a proxy for what you actually care about, and the gap between proxy and target differs systematically between groups. Arrests are a proxy for offences, clicks for interest, billed diagnosis codes for disease, prior spending for need. Each correlates strongly with its target and each fails differently for different people.
- Median Day 116
- The middle value once the data is sorted -- the average of the two middle values for an even-length dataset. It depends only on the RANK of values, not their magnitude, which gives it a breakdown point near 50%: close to half the data must be corrupted before it can be forced to move.
- Median absolute deviation (MAD) Day 116
- The median of the absolute deviations of every value from the dataset's median -- a robust measure of spread built entirely from robust ingredients. Under 3% contamination in this lesson's lab, the MAD moved by about 1.00x (essentially unchanged) while the standard deviation inflated by about 15.10x.
- melt Day 124
- The DataFrame method that converts a table from wide format to long format, turning selected column names into values of a new "variable" column and their corresponding values into a new "value" column, while keeping any id_vars columns unchanged per row.
- membership Day 53
- Testing whether a key is present with the expression key in d, which returns True or False. It is itself an O(1) hash lookup and the safe way to check before reading with square brackets.
- membership test Day 52
- Checking whether a value is in a list with `x in a`. On a list it scans item by item and costs O(n); sets and dictionaries offer O(1) membership when you test often.
- memoization Day 62
- An optimization that stores the results of expensive function calls and returns the cached result when the same inputs recur, so repeated subproblems are computed only once. Named by Donald Michie in 1968, it turns exponential naive recursion (like Fibonacci) into linear work.
- memory hierarchy Day 1
- The layered arrangement of storage from registers through cache and RAM to disk, trading speed against size and cost per byte at each level.
- memory hierarchy Day 3
- The layered arrangement of all the places a computer keeps data — registers, caches, RAM, storage, network — with each level larger, slower, and cheaper per byte than the one above.
- memory hierarchy Day 42
- The layered arrangement of storage from fast, small registers and cache through RAM to slow, large disk, which explains why systems that outgrow fast memory slow down (day 3).
- memory wall Day 3
- The long-running growth gap between processor speed and memory speed, which makes data movement — not arithmetic — the bottleneck for much of modern computing.
- memory_usage(deep=True) Day 120
- A DataFrame method reporting the real byte cost per column. For the pandas-3.0 str dtype, deep=True and deep=False agree, because the underlying storage is already contiguous; for the legacy object dtype, deep=True reports substantially more, revealing the cost of the pointer indirection that deep=False cannot see.
- memory_usage(deep=True) Day 121
- A DataFrame method reporting the real byte cost per column, including the cost of the objects a pointer-based dtype refers to (deep=True) rather than only the pointers themselves (the default, deep=False). The only way to see the true cost of a text column's storage.
- Mercer Theorem Day 169
- A mathematical theorem stating that any continuous, symmetric, positive semi-definite kernel function corresponds to an inner product in some Hilbert space.
- merge Day 29
- Folding the changes from two branches back together into one; where both changed the same lines, the system flags a conflict for a human to resolve.
- merge Day 31
- Combining the commits of one branch into another so the target contains both lines of work; a three-way merge creates a new merge commit with two parents.
- merge Day 124
- The pandas operation that combines two DataFrames by matching rows on one or more shared key values, analogous to a SQL JOIN. Every left row is paired with every right row sharing its key, which is why a duplicated key on both sides produces a per-key Cartesian product rather than a one-to-one pairing.
- merge base Day 31
- The most recent commit two branches share — their common ancestor — which Git uses as the reference point when performing a three-way merge.
- merge commit Day 33
- A commit with two parents that joins a branch back into the target branch, preserving the branch's individual commits and recording where the merge happened.
- merge conflict Day 29
- The situation where two branches changed the same lines and the system cannot combine them automatically, so it asks a person to decide the correct result.
- merge conflict Day 31
- The situation where two branches changed the same lines differently, so Git stops the merge and asks you to choose, marking the disputed region with conflict markers.
- merge request Day 33
- GitLab's name for a pull request — the identical branch-based, reviewed-then-merged workflow; abbreviated MR.
- MergeError Day 124
- The exception pandas raises when a merge's validate= argument detects that the stated cardinality assumption does not hold -- for example, validate="one_to_one" on a key that is duplicated on either side.
- message queue Day 26
- Infrastructure that sits between producers and consumers, durably storing events so services can exchange them reliably with buffering, ordering, and replay.
- MessagePack Day 24
- A binary serialization format that keeps JSON's exact data model in a smaller, faster encoding, used when compactness or speed matters more than readability.
- meta Day 135
- The json_normalize argument, used together with record_path, that names parent-level fields to carry down onto every child row. meta columns are duplicated once per child record by design -- that duplication is what makes the child-grain frame usable, and it is also exactly what makes summing a meta column produce an inflated total.
- Meta-Learner Day 168
- The top-level model (often a regularized linear estimator) in a stacking ensemble trained to combine the predictions of base models.
- metacharacter Day 38
- A character with special meaning in a pattern rather than its literal value, such as . * + ? [ ] ( ) ^ $ | and \, which express classes, repetition, position, and structure.
- method Day 18
- The verb of a request that declares intent — GET to read, POST to send data for processing, PUT to replace, PATCH to partially update, DELETE to remove.
- method Day 45
- A named action called on a string with a dot, such as s.lower() or s.split(); because strings are immutable, transforming methods return a new string.
- method Day 67
- A function defined in a class body. It lives on the class as a single shared function object and receives the instance as its first argument when called through one.
- Method of least squares Day 148
- The fitting criterion `LinearRegression` uses: choose the slope and intercept that minimize the sum of squared residuals. Published by Legendre in 1805 and by Gauss in 1809, who claimed prior use from 1795; Day 149 derives why squared error specifically.
- method resolution order (MRO) Day 68
- The fixed, ordered list of classes Python searches when looking up an attribute on an instance. Readable as `SomeClass.__mro__`. Attribute lookup checks the instance first, then walks this list until it finds the name.
- metric Day 40
- A numeric measurement sampled over time, forming a time-series of (timestamp, value) pairs that can be charted and aggregated across many events.
- Metric Day 103
- A distance function satisfying four conditions: never negative, zero exactly when the two things are the same, symmetric, and obeying the triangle inequality. Euclidean distance is a metric; cosine distance is not, failing two of the four. This is not pedantry — a great deal of fast-search machinery prunes whole branches using the triangle inequality, and given a function that fails it, such an index still returns answers, some of them wrong, and nothing says so.
- Metric Day 107
- A distance function of two arguments satisfying four axioms: non-negativity; zero exactly when the two arguments are equal; symmetry; and the triangle inequality. Not a compliment but a checklist, and the reason to care is entirely practical — ball trees, KD-trees, cover trees and every metric-space pruning scheme are built on the fourth axiom. The framework was extracted rather than invented: Maurice Fréchet stripped distance down to these properties in his 1906 doctoral thesis, and Felix Hausdorff gave the resulting object its name in Grundzüge der Mengenlehre in 1914.
- Metric Day 152
- What you report after fitting, to judge a model's result. RMSE, MAE, MAPE, R-squared and adjusted R-squared are all metrics, and none of them is required to be the function the model was fitted to minimise.
- Metric ranking inversion Day 152
- When two metrics disagree about which of two models is better, because each weighs the same residuals differently. Measured here directly: RMSE preferred a model with many small errors, MAE preferred a model with a few large ones -- the regression counterpart of Day 143's accuracy-versus- recall inversion on classification.
- Metric selection Day 143
- Choosing what a score measures, which determines which model you ship. Not a reporting decision made at the end: on this lesson's table, accuracy and recall pick different winners with nothing else changing.
- middleware Day 82
- Code that wraps every request and response and sees them as raw HTTP — the right place for request logging, compression or CORS headers. Contrast a dependency, which runs only for the routes that ask for it and sees typed Python. Inspecting paths inside middleware to decide whether to act usually means you wanted a dependency.
- Migration Day 88
- A numbered file of schema changes, applied in order, inside a transaction, and recorded so it is never applied twice. The artefact that lets the same change reach your laptop, a colleague's and a server identically. The governing discipline: an applied migration is history, so you change it by adding the next one, never by editing it.
- Min-max normalisation Day 107
- Rescaling each column so its minimum becomes 0 and its maximum becomes 1. The alternative to standardisation, and the trade-off is worth stating rather than defaulting. Min-max pins the range exactly, which is what an image pipeline usually wants, but one outlier then decides the whole scale and any value outside the training range comes out above 1 or below 0. Standardisation assumes nothing about the range and handles unbounded features, but an outlier stretches the standard deviation and squashes everything else toward zero.
- Mini-Batch K-Means Day 183
- A streaming variant of K-Means that updates centroids using small random sub-samples, reducing computational complexity to linear time.
- Mini-Batch SGD Day 201
- An optimization method computing parameter gradients and updating weights on small random subsets (e.g., 32, 64, 128 samples) of the training dataset.
- Mini-Batch Vectorization Day 199
- Stacking m training examples into a single multi-dimensional matrix to execute matrix-matrix multiplications in parallel on CPU/GPU hardware.
- Minimum-norm solution Day 145
- What least squares returns when there are more features than rows and the system is under-determined. Quietly a form of regularisation, which is why the degree-24 model behaved better at 15 rows than at 25.
- Minimum-norm solution Day 153
- Among the infinitely many coefficient vectors that fit an under-determined or near-collinear problem almost equally well, the one with the smallest overall magnitude. sklearn's default LinearRegression solver returns this one, splitting a shared true coefficient of 1 into 2.5 and 2.5 on this lesson's near-duplicate-column dataset rather than exploding.
- MinMaxScaler Day 170
- A linear transformation scaling features to a fixed closed interval, typically [0, 1].
- MinPts Day 184
- The minimum number of data points required within an epsilon-radius neighborhood for a point to qualify as a core point.
- mirror Day 13
- A synchronized duplicate of a repository hosted elsewhere, providing faster and more reliable downloads and redundancy.
- missing at random (MAR) Day 125
- A missingness mechanism in which the probability a value is missing depends on OTHER observed columns, but not on the missing value itself once those other columns are accounted for. Imputation that uses the related observed columns (rather than a single unconditional mean) can partially correct for MAR missingness.
- Missing at Random (MAR) Day 174
- A missing data mechanism where missingness depends systematically on observed features but not on the unobserved missing value itself.
- missing completely at random (MCAR) Day 125
- A missingness mechanism in which the probability a value is missing does not depend on any observed or unobserved value in the dataset -- the closest thing to "pure accident." The easiest case to handle honestly, and the least common in real data.
- Missing Completely at Random (MCAR) Day 174
- A missing data mechanism where the probability of missingness is completely independent of both observed and unobserved data.
- missing indicator Day 125
- A boolean column recording, before imputation erases the evidence, which rows originally had a missing value in a given column. Lets a downstream model or analysis use "this value was imputed" as a signal in its own right, rather than losing that information the moment fillna runs.
- missing not at random (MNAR) Day 125
- A missingness mechanism in which the probability a value is missing depends on the value itself -- a sensor that fails specifically at extreme readings, or an income field left blank specifically by the highest earners. No imputation strategy repairs MNAR missingness, because the information needed to correct it was never recorded, and more data does not help (Day 117).
- Missing Not at Random (MNAR) Day 174
- A missing data mechanism where the probability of missingness depends directly on the unobserved value itself, carrying informative signal.
- MissingIndicator Day 174
- A binary transformation that outputs boolean indicator features marking the exact coordinates of missing data in the original matrix.
- mixin Day 68
- A small class providing one orthogonal capability, never instantiated on its own, added to unrelated classes through multiple inheritance. If it starts holding state or growing methods, it wants to be a collaborator object instead.
- ML Project Lifecycle Day 190
- The end-to-end multi-stage process of designing, building, validating, deploying, and maintaining production machine learning systems.
- MLOps Day 190
- Machine Learning Operations: the set of practices and tooling uniting ML development and IT operations for automated, reliable deployments.
- MNIST Benchmark Day 203
- The canonical machine learning dataset consisting of 70,000 28x28 grayscale images of handwritten digits from 0 to 9.
- Mock Day 74
- Strictly, a test double that carries an expectation and fails the test when the expectation is not met — in Python, any unittest.mock object you finish with assert_called_once_with. Colloquially the word is used for all five kinds of double, which is why conversations about mocking so often go wrong.
- Mode Day 116
- The most frequently occurring value or values in a dataset. A distribution can be multimodal; Python's statistics.mode() (singular) silently returns just one tied value, while statistics.multimode() returns every one.
- mode string Day 64
- The short string passed to `open()` declaring intent: `r` read, `w` write (truncating at open time), `a` append, `x` exclusive creation (fails if the file exists), plus `+` to add the other capability and `b` for bytes instead of text.
- Model Benchmarking Day 161
- The rigorous comparison of diverse algorithmic families (linear, instance-based, probabilistic) on identical cross-validation splits.
- Model capacity Day 145
- How much a model class can represent. Not a single dial from worse to better -- degree 2 contains every degree-1 model and measured more bias AND more variance, because the true function is odd so the extra term buys nothing and still costs.
- model card Day 133
- A short structured document describing a machine-learning model's intended use, evaluation and limitations, introduced by Margaret Mitchell and colleagues at the FAT* conference in 2019. Structurally it is this lesson's report with a different subject, and it fails the same way: pages of metrics with no stated claim, so a reader cannot tell whether the model is fit for their purpose.
- Model Card Day 182
- A standardized short document providing key benchmarked evaluation, intended usage, and ethical considerations for an ML model.
- Model class Day 141
- The family of functions a training procedure is allowed to search through: straight lines, decision trees up to a given depth, nearest-neighbour lookups, neural networks of a given shape. You never search all possible functions; you always choose a family first, and that choice is yours to defend.
- Model Details Day 182
- Basic metadata including architecture, version, developers, release date, and license.
- Model Diversity Day 168
- The degree of statistical independence between the prediction errors of base models in an ensemble, serving as the primary driver of ensembling success.
- Model Observability Day 195
- The capability to infer the internal health, accuracy, and data consistency of production ML systems from external telemetry metrics.
- Model Registry Day 193
- A centralized catalog storing versioned model artifacts, cryptographic hashes, metadata, and lifecycle stages.
- Model Serialization Day 193
- The process of converting an in-memory trained model object into a persistent byte stream or file for storage and serving.
- Model Serving Day 194
- The operational process of hosting a trained machine learning model behind an API to provide predictions for incoming queries.
- Model Slicing Day 190
- The practice of evaluating model accuracy across distinct demographic or behavioral sub-populations rather than global aggregates alone.
- Model validator Day 94
- A function attached to the whole model with @model_validator, for a rule no single field can express — the record is valid only if two fields agree, or if one is present when another has a particular value. In mode="after" it receives the built object and returns it; in mode="before" it receives the raw input. Its errors carry an empty loc, because no one field is at fault.
- model.eval() Day 208
- A PyTorch method setting the module and all submodules into evaluation mode, deactivating Dropout and freezing BatchNorm running stats.
- module Day 49
- A single Python `.py` file, which can be run as a program or imported by other files to reuse its functions and variables.
- module Day 59
- A single .py file of Python code, importable by other files; its name is the filename without the extension. Importing a module runs it once and gives you an object through which you reach the functions, classes, and variables it defined.
- module Day 60
- A file of Python code you import to reuse its functions and classes; the standard library is a vast, pre-installed set of such modules, and you import only the specific ones you need (import json, from pathlib import Path).
- Module Day 83
- A single Python file that can be imported — `core.py`, imported as `wordtally.core`. The smallest unit Python's import system deals in, and the first of the three things the word "package" gets confused with.
- module boundary Day 63
- The line between two parts of a program (often two files) across which they communicate only through a defined interface, each hiding its internal details from the other. Rooted in David Parnas's 1972 idea of information hiding.
- module cache Day 59
- The dictionary sys.modules holding every module already imported in the current process. Python checks it before searching sys.path, so a module is imported (and its top-level code run) only once no matter how many files import it; later imports reuse the cached object.
- ModuleNotFoundError Day 48
- An error raised when Python cannot find a module you tried to import, commonly because it is not installed in the current environment.
- modulo Day 46
- The % operator, which returns the remainder left over after floor division; 7 % 2 is 1, and (a // b) * b + (a % b) always reconstructs a.
- mojibake Day 5
- Garbled text that appears when bytes are decoded with the wrong character encoding.
- mojibake Day 121
- Text that decodes without error under the wrong encoding, producing visibly garbled but syntactically valid characters -- the silent failure mode of an encoding mismatch, as opposed to UnicodeDecodeError, which is the loud one.
- Momentum Day 111
- An update that substitutes an exponentially weighted running average of the gradient, v <- beta*v + grad(x), for the raw gradient in the descent step: x <- x - eta*v. It is not a separate algorithm -- it is the same update rule with a smoothed direction, and it helps on an ill-conditioned bowl because averaging cancels an oscillating component while a consistent component survives.
- Momentum Day 201
- An optimization enhancement that adds a fraction beta of the previous parameter update vector to the current step to dampen oscillations.
- monkeypatch Day 72
- A built-in pytest fixture that changes something about the environment — an environment variable, an attribute, a dictionary entry — for the duration of one test and undoes it afterwards. The automatic undo is containment, not tidiness: a hand-rolled patch survives the test that made it and can silently change what a later test talks to.
- Monkeypatch Day 74
- pytest's fixture for setting and deleting environment variables, object attributes, the working directory and the import path, with every change undone automatically when the test ends. Smaller than unittest.mock — it sets values rather than building recording doubles — and safer where it fits.
- monorepo Day 35
- A single repository that holds many projects together, making cross-project changes atomic and shared tooling simpler; contrast with a polyrepo, which gives each project its own repository.
- Monotonic clock Day 95
- A clock that only ever moves forward and is never adjusted, exposed as time.monotonic(). It has no relationship to any calendar and cannot tell you the date, which is the entire design. Use it for every duration, timeout and retry window, because the wall clock is adjustable and can move — or go backwards — between two readings of it.
- Monte Carlo simulation Day 113
- Estimating a probability by running a large number of random trials and counting how often an event occurs, rather than computing it exactly. Converges to the true probability as the trial count grows, but its error shrinks only as 1/sqrt(n) — a hundred times the trials buys ten times less error, not a hundred times less.
- Multi-armed bandit Day 142
- The smallest honest reinforcement problem: several actions, each paying from an unknown distribution, and a fixed budget of pulls. There are no states, so credit assignment does not arise and the exploration-exploitation trade-off can be studied on its own.
- multi-cursor Day 36
- An editing feature that places several cursors at once so you can type or edit in many places simultaneously — for example renaming a name everywhere it appears.
- Multi-index OR Day 89
- The plan SQLite uses when every branch of an OR has its own usable index: it seeks each branch separately and merges the results. It is the reason the folklore that OR always defeats an index is wrong. One unindexed branch collapses the whole condition to a scan, because a row failing the indexed test might still pass the other one — an OR is only as indexed as its worst branch.
- multi-key grouping Day 123
- Grouping by more than one column at once (groupby(["region", "rep"])). The combined result carries a pandas.MultiIndex with one level per grouping key, unless as_index=False is passed, in which case the same values are returned as ordinary columns in a flat DataFrame.
- Multi-Layer Perceptron (MLP) Day 197
- A feedforward artificial neural network consisting of an input layer, one or more hidden layers, and an output layer with non-linear activations.
- Multicollinearity Day 150
- Two or more predictors carrying overlapping information about each other, not just about the target. Measured here at a correlation of 0.8967 between two serum measurements. It destabilises coefficients without necessarily hurting predictions.
- Multicollinearity Day 153
- Two or more predictor columns carrying overlapping information about each other, first introduced structurally on Day 150. This lesson measures its numerical consequence directly: a near-duplicate column sends closed-form coefficients past 196,000 in magnitude while the true coefficients are 1 and 4.
- MultiIndex Day 123
- A pandas index with more than one level, produced by multi-key grouping (one level per key) or by the list/dict forms of .agg() on a multi-column selection (one level for the source column, one for the applied function).
- Multinomial Naive Bayes Day 158
- A Naive Bayes variant tailored for discrete count data, commonly used for text classification with Bag-of-Words representations.
- Multiple comparisons Day 118
- The problem created by running many hypothesis tests and evaluating each at the same alpha without correction. The family-wise false-positive rate for m independent tests is 1 - (1-alpha)^m, not alpha -- 0.6415 for 20 tests at alpha=0.05, confirmed by simulation in this lesson.
- Multiple comparisons problem Day 136
- The fact that running several independent hypothesis tests at a fixed significance level alpha raises the chance that at least one comes back "significant" by chance alone, well above alpha itself -- exactly 1 - (1 - alpha)^k for k independent tests.
- Multiple regression Day 150
- A linear model with more than one predictor: y = b0 + b1*x1 + b2*x2 + ... + bp*xp. Each coefficient is fitted jointly with every other, which is what makes its meaning conditional rather than standalone.
- Multiplication count Day 101
- How many multiplications a product costs: m times n times p for an (m, n) @ (n, p), one per row, column and inner step. Not an estimate — it is exactly how many times the innermost line of the loop runs. Since training compute is dominated by these products, the multiplication count is effectively the bill, which is why choosing the cheaper association of a chain is a free and exact optimisation.
- Multiplication rule Day 113
- P(A and B) = P(A) x P(B | A), the rearranged form of the conditional-probability definition. When A and B are independent, P(B | A) = P(B), and the rule collapses to P(A and B) = P(A) x P(B), which is exactly what makes de Méré's (5/6)^4 valid: four independent rolls, each missing with the same unconditioned probability.
- Multiplicity Day 106
- How many times an eigenvalue counts, in two different senses that can disagree. ALGEBRAIC multiplicity is how many times it appears as a root of the characteristic equation. GEOMETRIC multiplicity is how many independent eigenvectors it actually has. Geometric is never greater than algebraic, and when they are equal for every eigenvalue the matrix diagonalises. The shear [[1, 1], [0, 1]] is the canonical example of them disagreeing: its eigenvalue 1 has algebraic multiplicity 2 and geometric multiplicity 1, because only the x-axis survives. This matters practically because numpy.linalg.eig must return a square array of eigenvectors regardless, so it returns two columns for the shear whose absolute cosine is 1.0 — the same line twice. Counting the columns a library returns is not counting eigendirections.
- mutability Day 52
- The property of being changeable after creation. Lists are mutable — you can add, remove, replace, or reorder items in place — which is powerful but also the source of aliasing and mutation-surprise bugs.
- mutable Day 44
- Describes an object that can be changed in place after creation, keeping the same identity. list, dict, and set are mutable.
- mutable default trap Day 69
- The bug where a mutable default value is created once and silently shared. In a plain function signature (`def f(bucket=[])`) Python permits it and the sharing goes unnoticed; in a dataclass it is refused outright with a `ValueError` at class creation that names `default_factory` as the fix.
- Mutation testing Day 73
- Deliberately changing the code to see whether the suite notices — the general form of "watch it fail". A mutation the suite catches is a behaviour the suite pins down; a mutation that survives marks a behaviour no test has decided. The Day 73 lab performs four mutations automatically.
- Mutual exclusivity Day 113
- Two events A and B are mutually exclusive when they cannot both occur: P(A and B) = 0. Mutually exclusive events with non-zero individual probabilities are necessarily DEPENDENT, not unrelated — knowing one occurred tells you the other definitely did not, collapsing its conditional probability to exactly 0.
- Mutual Information Day 172
- A non-parametric measure of the mutual dependence between two variables that captures both linear and non-linear relationships.
- Mutually exclusive group Day 80
- A set of options of which at most one may be given, created with `add_mutually_exclusive_group()`. argparse both enforces it — passing two is exit 2 with a message naming both — and documents it, showing `-v | -q` in the usage line, neither of which a hand-written check would do.
- MX record Day 16
- A DNS mail-exchange record specifying which server receives email for a domain, with a priority number.
- mypy cache Day 75
- The `.mypy_cache/` directory holding a processed representation of each module, so repeated runs rebuild only what changed. It appears wherever you ran mypy, belongs outside version control, and can be deleted at any time at the cost of one slower run.
- N+1 problem Day 93
- Issuing one query to fetch N parent rows and then one more per parent to fetch its children — 1 + N queries where two would do. It is not a bug in the ORM; it is the direct consequence of a relationship attribute being a query in disguise. Nothing in the Python source hints at the cost, which is why you count statements rather than read code. It is also a denial-of-service vector: if a client controls the page size, a client controls how many queries your database runs.
- N+1 queries Day 87
- The pattern where a program runs one query to fetch a list and then one more query per item, where a single join would have answered the whole question. The penalty depends entirely on deployment: measured on an embedded database, 501 queries against 1 cost 0.79 ms against 0.44 ms, because a query is a function call in the same process. Across a network each of those queries is a round trip, and the same pattern becomes unusable.
- na_values Day 121
- The list of literal strings read_csv() treats as a missing value by default, including "NA", "N/A", "null", "NaN" and several others. Any cell whose text matches one of these entries becomes a missing value on read, whether or not that was the intent -- the country code "NA" for Namibia is the textbook case.
- Nabla Day 109
- The symbol ∇, "written as an upside-down triangle and pronounced del", which denotes the vector differential operator. It is an operator rather than a number or a vector: ∇ on its own means "take the partial derivative with respect to each coordinate and stack the results", and ∇f is what you get when it is applied to a particular function. The gradient is also commonly written grad f.
- Naive Bayes Day 115
- A classifier that applies Bayes' theorem to a document by treating every word as a separate, conditionally independent piece of evidence given the document's class -- an assumption known to be false (word choice is not independent of context) that the classifier remains useful despite, because it only needs the relative class ranking to be correct, not the individual probabilities.
- Naive Bayes Day 158
- A family of generative probabilistic classifiers based on Bayes Theorem with the strong assumption of conditional feature independence given the class label.
- Naive datetime Day 95
- A datetime whose tzinfo is None, or whose tzinfo returns None from utcoffset(). It carries year, month, day, hour, minute, second and microsecond and no offset, so it names a wall-clock reading rather than an instant. The standard library allows it because plenty of times genuinely have no zone — an alarm at 07:00 wherever you wake up, a shop that opens at 09:00 in every branch — and forbidding it would make those unrepresentable. The cost is that a naive value converted, compared or stored as though it were an instant is silently wrong.
- name mangling Day 67
- The rewriting of a double-underscore attribute name inside a class body: `__pin` in `class Vault` is stored as `_Vault__pin`. It prevents accidental collisions between classes; it is not access control, since anyone can type the mangled name.
- named aggregation Day 123
- The agg(result=(column, function)) syntax, added in pandas 0.25, that names each output column explicitly and produces a flat column index rather than the MultiIndex the list and dict forms of .agg() typically produce on a multi-column selection.
- namedtuple Day 54
- A tuple with named fields, created via `collections.namedtuple`, so you can read an item by name (`city.name`) instead of by position (`city[0]`) while it stays an immutable, hashable tuple underneath.
- namedtuple Day 67
- An immutable record with named fields that is still a tuple, so it indexes, unpacks, and compares by value. `collections.namedtuple` is the factory form; `typing.NamedTuple` is the readable class form that also accepts methods.
- NameError Day 48
- An error raised when you use a name that does not exist, usually because of a typo or because the name was used before it was defined.
- naming convention Day 61
- An agreed pattern for choosing identifiers so their form signals their role: in Python, snake_case for variables and functions, CapWords (PascalCase) for classes, and UPPER_CASE for module-level constants. Following the convention lets a reader guess what a name is before reading its definition.
- nan Day 104
- Not a Number: the IEEE-754 value produced by 0/0, by the square root of a negative, by infinity minus infinity, and used to mark a reading that was never taken. Its defining oddity is that it compares unequal to everything including itself, so a == np.nan is always False and a filter written that way finds nothing while reporting success; np.isnan asks about the bit pattern instead. It propagates through every plain aggregation on purpose — one nan makes a whole mean nan — which is a loud report of a missing value rather than a bug. np.nanmean, np.nansum and np.nanmax skip them, and choosing one should be a decision rather than a reflex.
- NaN Day 120
- "Not a Number", the IEEE 754 floating-point value used to represent a missing entry in a float64 column. By the IEEE 754 standard, NaN is never equal to anything, including itself, so series == np.nan can never find it; .isna() is the reliable test.
- NaN-Euclidean Distance Day 174
- A modified Euclidean distance metric that calculates pairwise distances across mutually observed coordinates and scales by total dimension ratio.
- narrowing Day 75
- The checker's tracking of what a name can be as control flow proceeds. `if x is None: return`, `if not isinstance(x, dict): raise`, and `assert isinstance(x, str)` each remove a possibility, so on the lines below only the remaining members of the union are considered. The guard is not written for the checker — it is the case you forgot, and the checker noticed.
- Natural key Day 91
- A value that already identifies the row in the world: an ISBN, an email address. Genuinely useful and still the wrong primary key, because natural keys change, are sometimes absent — a book printed in 1818 has no ISBN, and a primary key cannot be NULL — and are sometimes mistyped. The resolution is to keep it as a UNIQUE constraint alongside a surrogate primary key, which gets the integrity guarantee without the coupling.
- nbclient Day 139
- The library that executes a notebook against a real Jupyter kernel without opening any user interface. It is what nbconvert's --execute flag and Jupyter's own "Run All" ultimately call, and it is the library this lesson uses to turn "does this notebook still work" into an assertion a test suite can make.
- nbconvert Day 139
- The library and command-line tool that converts an executed notebook into another format: Markdown or HTML for a report, or a plain .py script for code review. Conversion reads the notebook's stored outputs; it does not re-execute cells unless told to with its own --execute flag.
- nbformat Day 139
- The Python library and JSON schema that define what a .ipynb file actually is: a list of cells, each with a source, a cell type, and -- for code cells -- an execution_count and a list of outputs. Building a notebook with nbformat produces the identical structure Jupyter itself would save.
- ndarray Day 104
- NumPy's array type: a fixed-size, homogeneous, N-dimensional block of values described by a small header. NumPy's own beginner's guide states all three constraints — it "represents an N-dimensional array", "all elements of the array must be of the same type of data", and "once created, the total size of the array can't change". Those constraints are not tolerated limitations; they are the entire source of the speed and memory advantage, because they are what allow the values to be packed in one block and read without a per-element type check.
- NDCG@k Day 176
- Normalized Discounted Cumulative Gain at rank k, measuring ranking quality where items placed higher carry logarithmically greater weight.
- NDCG@K Day 188
- Normalized Discounted Cumulative Gain at rank K, measuring ranking quality with logarithmic position penalties.
- Near-duplicate instability Day 150
- What happens once an exact tie is broken by a small amount of noise: the split becomes unique but effectively arbitrary, swinging with a standard deviation above 4.4 across ten seeds here while the sum of the two coefficients stays within 0.0144.
- Near-duplicate predictors Day 151
- Two columns correlated at 0.999918 in this lesson's measurement, used to show ridge splitting a true combined coefficient of 6.0 almost evenly (3.048 and 2.9742) while lasso concentrates nearly all of it on one (5.0848) and zeros the other.
- Nearest neighbour Day 105
- The interpolation rule that takes the value of the pixel whose square CONTAINS the sampled position — that is, floor of each coordinate, not rounding. Produces hard, stair-stepped edges, and its defining property is that every value in the output was already in the input. That makes it correct for images whose pixel values are categories rather than quantities: segmentation masks, label maps, indexed palettes. Blending class 3 and class 7 into class 5 is a silent data-corruption bug, and nearest neighbour cannot commit it.
- Nearest-neighbour search Day 99
- Finding the item in a collection whose vector is closest to a query vector under a chosen metric. This is what semantic search is: embed the query the same way the items were embedded, measure the distance to each, return the smallest. Everything harder about it in production is either getting better vectors or avoiding the need to measure every single item.
- Negative gap Day 145
- Test error below training error, measured here at -1.4942. Not a broken split: a model too rigid to chase noise has none to be flattered by, so its training score carries no optimism. The signature of underfitting, and the one most often mistaken for a bug.
- negative index Day 52
- An index counted from the end of the list rather than the start: `-1` is the last item, `-2` the second-to-last, and so on — a convenient way to reach the back without knowing the length.
- Nested cross-validation Day 144
- An inner loop that selects and an outer loop that scores, so the outer estimate is not contaminated by the selection. The correct fix for the optimism this lesson measures, at the product of the two loops in compute.
- Nested Cross-Validation Day 167
- A hierarchical validation framework with an outer loop estimating model generalization error and an inner loop performing hyperparameter tuning.
- nested dict Day 53
- A dictionary whose values are themselves dictionaries, used to model structured records with named fields — the shape of a JSON payload, a config object, or a feature record.
- nested loop Day 51
- A loop placed inside another loop; the inner body runs the product of the two loop counts (outer x inner), which is the most common source of code that is fast on small input and slow on large.
- Nested-loop join Day 87
- The straightforward join algorithm: for every row on the left, scan every row on the right. Its cost is the product of the two table sizes — six rows against five is thirty comparisons. When the inner scan is replaced by an index lookup it becomes an indexed nested loop, which SQLite reports in EXPLAIN QUERY PLAN as a SCAN of one table and a SEARCH of the other.
- Network tab Day 21
- The Developer Tools panel that records every request a page makes, showing each one's status, type, size, timing, and full headers and body.
- Newton-Raphson Step Day 164
- A second-order optimization update that divides the first derivative (gradient) by the second derivative (Hessian) to optimize leaf values for non-quadratic loss functions.
- NewType Day 75
- A way of making a distinct type out of an existing one, so that two values which are both strings at runtime stop being interchangeable to the checker. It catches the argument-order mistake that a plain `(str, str)` signature can never see.
- nibble Day 4
- Half a byte — 4 bits — which is exactly the amount of information one hexadecimal digit represents.
- no-auth API Day 28
- A public API that requires no key or token to call — anyone can send an anonymous request and get a response, as with Open-Meteo, Open Notify, and JSONPlaceholder.
- Node Day 110
- One value in a computation graph, together with the record of which values it was computed from. In the engine built in this lab a node is a Value object holding a number, a gradient, a tuple of children, and a small function that hands its gradient back to those children.
- nominal typing Day 75
- Deciding type compatibility by declared identity: a value fits because its class inherits from, or is, the named type. Ordinary Python class annotations are nominal; `Protocol` is the structural alternative, and the choice between them is really a choice about whether the two sides must know about each other.
- nominal, ordinal, quantitative, temporal Day 127
- The four data types that constrain encoding. Nominal is names with no order; ordinal has order but no meaningful arithmetic; quantitative has both; temporal is quantitative with a structure readers already know. Nominal data on a magnitude channel invents an order that is not there; ordinal data on a categorical colour palette destroys an order that is.
- Non-convex function Day 111
- A function with more than one local minimum (or a mix of minima, maxima and saddle points). Gradient descent on a non-convex function converges to whichever minimum is downhill from its starting point, so the initialisation is a real decision with a real effect on the answer, not an implementation detail.
- None Day 57
- Python's special "nothing" value, returned by a function that has no return statement (or a bare return). Mistaking it for a real result — for example after forgetting to return — is a common source of bugs.
- NoneType Day 44
- The type of the single object None, which represents the deliberate absence of a value — distinct from 0, "", and False.
- Nonexistent time Day 95
- A wall-clock reading that never occurred, because the clocks jumped over it. 01:30 on 29 March 2026 in Europe/London is one: no clock in the country showed it. Python builds the object without complaining, because a wall reading plus a zone is a request rather than a fact; the failure shows in the round trip, where converting to UTC and back does not return the value you started with.
- nonlocal Day 58
- A statement (nonlocal name) inside a nested function declaring that a name refers to a variable in the nearest enclosing function, so the inner function can rebind that captured variable instead of shadowing it with a new local. Central to stateful closures.
- Norm Day 107
- A function that takes one vector and returns its size. To earn the name it must satisfy four requirements: it is never negative; it is zero only for the zero vector; scaling a vector by k scales its size by the absolute value of k (absolute homogeneity); and the size of a sum is never more than the sum of the sizes (the triangle inequality). Squared Euclidean distance fails the third of those and is therefore not a norm, whatever it is called in the paper you are reading.
- Normal distribution Day 114
- The bell-shaped distribution with parameters mean mu and variance sigma^2, that arises as the limiting shape of sums of many small, independent effects — the subject of Day 117's central limit theorem. Not derived numerically in this lesson beyond its description in the named-distributions table.
- Normal equations Day 149
- The closed-form solution to squared-error linear regression, `(X^T X) beta = X^T y`, obtained by setting the loss's derivative to zero and solving. Measured here to match `LinearRegression` to within 6e-14.
- Normal equations Day 153
- The closed-form solution to ordinary least squares, obtained by solving X'X beta = X'y directly. Textbook-simple, and measured here to agree with sklearn's LinearRegression to only 1.2153e-10 on well-conditioned data -- about a hundred times looser than a direct solve of X.
- Normal-probability (Q-Q) correlation Day 154
- A from-scratch check correlating sorted, standardised residuals against the quantiles a perfectly normal distribution would produce. 1.0 is a straight line; this lesson measures 0.9901, close to normal even on 111 real test rows.
- Normalisation Day 99
- Scaling a vector to magnitude 1 by dividing every component by its magnitude, which keeps the direction and discards the length. It is done constantly in practice because length is very often an artefact — a longer document has bigger counts without being about anything different — while direction is the part that carries the meaning. The zero vector cannot be normalised: it has magnitude 0 and no direction, so the division is undefined.
- Normalisation Day 103
- Rescaling a vector to length 1 by dividing every component by its length. In this lesson it is not a tidying step done out of habit; it is the step that makes cosine similarity and Euclidean distance interchangeable. On normalised vectors the two rank identically, so the choice between them becomes a performance decision. Skip it, and which one you picked changes the answers.
- Normalization Day 87
- Organising tables so that each is about one kind of thing and every fact is written down in exactly one place, eliminating the update, insertion and deletion anomalies. Developed by E. F. Codd through 1971 and 1972 as the first three normal forms. It moves cost from writes to reads: you store each fact once and pay a join to reassemble it.
- Normalization Day 88
- Arranging data so each fact is stated exactly once, introduced by Edgar F. Codd in the early 1970s. First normal form gives one value per cell; second removes dependencies on part of a composite key; third removes dependencies between non-key columns. Every anomaly the forms prevent is the same anomaly: two copies of one fact, disagreeing.
- NoSQL Day 39
- A family of non-relational databases — key-value, document, wide-column, and graph — that trade some of the relational model's strict rules for scale, flexibility, or specialized query shapes.
- NoSQL Day 92
- A label attached to four largely unrelated families of database — key-value, document, wide-column and graph — whose only shared property is not being the relational model. Carlo Strozzi used the name in 1998 for a database that was still relational but exposed no SQL interface; Johan Oskarsson reintroduced it in early 2009 for an event about open-source distributed non-relational databases. Because the word covers such different things, "should we use NoSQL?" is not a question that can be answered.
- Notebook/module split Day 139
- The discipline of keeping exploration in a notebook's cells while moving any logic other code depends on into an imported, separately tested module. A notebook cell is structurally unreachable by Python's import system -- pytest can test a module directly and cannot reach a cell, with or without a kernel running.
- NotFittedError Day 146
- The exception raised when predict(), transform() or similar is called before fit() has run. Measured with an identical message pattern on a library estimator and a hand-built one -- "is not fitted yet. Call 'fit'..."
- NotImplemented Day 68
- A special value RETURNED from a comparison dunder to mean "I do not know how to compare against this type — ask the other operand." Distinct from `NotImplementedError`, which is an exception you RAISE from an unfinished method. Returning `False` instead is how comparisons become silently wrong.
- Novelty effect Day 119
- A metric movement caused by a change being new and attracting curiosity, rather than by the change being genuinely better -- one that typically fades over days or weeks. A treatment that looks strong on day one and weaker by day fourteen may indicate the effect was never real beyond curiosity, not that "the effect wore off."
- null Day 24
- The JSON literal for a value that is deliberately empty — a present slot whose contents are intentionally nothing.
- NULL Day 85
- The absence of a value — not zero, not an empty string, and not equal to anything including itself. That last property is why you write IS NULL rather than = NULL, and why sorting has to decide where NULLs go: SQLite places them first in an ascending sort, and a hand-written sort must choose deliberately.
- NULL Day 86
- A marker meaning there is no value here — not zero, not the empty string, not False. Two absences are not equal to each other because there is nothing to compare, which is why NULL = NULL is UNKNOWN and IS NULL is the only test for absence. Codd introduced it into the relational model; C. J. Date argued for decades that it was a mistake. The argument was never settled, and the traps you meet are the faithful behaviour of that unresolved design decision.
- Null hypothesis (H0) Day 118
- The default assumption a hypothesis test holds until the evidence overwhelms it -- typically "no difference" or "no effect." A test never proves the null true; it only asks how surprising the observed data would be if the null were true, and rejects the null when the answer is "very surprising."
- Nullable column Day 91
- A column that may hold NULL, which should always be a decision with a stated meaning rather than an accident. The lesson's four NULLs each mean something different: unknown (an unpublished birth year), does not apply (a book printed before ISBNs), a positive fact about the world (a top-level category has no parent), and not yet (an unreturned loan). Adding a boolean alongside a date that already encodes the same fact gives you two columns that can disagree.
- num_workers Day 205
- The number of subprocesses spawned by DataLoader to load data asynchronously in parallel.
- Numeric overflow (in a learning-rate sweep) Day 112
- The point at which a diverging run's value grows past the largest number a float64 can represent (about 1.8e308) and becomes float('inf'). This lesson's sweep catches it deliberately with numpy.errstate and an explicit isfinite check after every step, rather than letting a warning or an OverflowError interrupt the sweep.
- Numerical Gradient Checking Day 198
- A diagnostic technique comparing analytical backpropagation derivatives against finite-difference approximations (f(z+eps) - f(z-eps)) / (2*eps).
- Numerical Gradient Checking Day 200
- A debugging validation protocol comparing analytical backpropagation gradients against two-sided finite difference approximations.
- numpy.meshgrid Day 112
- A NumPy function that takes two 1D arrays of coordinates and expands them into two 2D arrays, X and Y, such that X[i, j] and Y[i, j] together give the coordinates of grid cell (i, j). Applying a function to both arrays at once, vectorized, produces a value array Z with the same shape.
- numpy.random.Generator Day 113
- NumPy's modern random-number API, constructed with numpy.random.default_rng(seed). It returns an independent, stateful object rather than mutating shared global state, so two Generators built from the same seed reproduce byte-identical results regardless of what else the program does — unlike the legacy numpy.random.seed() function, which mutates one process-wide generator that every unrelated call to numpy.random.* also draws from.
- OAuth Day 25
- An open standard (OAuth 2.0, RFC 6749) that lets an application act on a user's behalf at another service using a scoped, revocable token, without ever seeing the user's password.
- object Day 24
- A JSON value that is an unordered collection of "key": value pairs, where every key is a double-quoted string; it maps to a dictionary or map in most languages.
- object Day 44
- A thing in memory that carries a type, a value, and an identity. In Python everything — numbers, text, lists, even types — is an object.
- object Day 67
- A thing in memory with a type, an identity, and its own state. In Python everything is one, including functions, modules, and classes themselves.
- object API Day 128
- The fig, ax = plt.subplots() style, where every following instruction is a method call on that specific ax. Every example in this course uses this style, because it makes it structurally impossible for one call to silently draw into a different figure than the one you meant.
- object dtype Day 120
- The pre-pandas-3.0 default dtype for a column of strings (and the dtype still used for genuinely mixed-type columns on any pandas version): an array of pointers to separately allocated Python objects, with no contiguous storage benefit.
- Object states Day 93
- The four conditions a mapped object can be in. Transient: constructed, in no Session, no row. Pending: added to a Session, still no row. Persistent: has a row and a Session, the normal working state. Detached: has a row but no Session, so anything needing the database — including refreshing an expired attribute or loading a lazy relationship — will fail. inspect(obj) reports which.
- object storage Day 39
- A flat store of large, immutable blobs addressed by a key inside a bucket; cheap, highly durable, and effectively unlimited, and the natural home for datasets, media, backups, and model files.
- Object-relational impedance mismatch Day 93
- The collection of structural disagreements between the object model and the relational model. Identity: two objects with equal contents are two objects, while two rows with the same primary key are one row. Granularity: an object graph loaded in full may span a dozen tables. Associations: object references point one way and are directional, while a foreign key is a fact both sides can be queried through. Inheritance: the relational model has none, so a class hierarchy must be flattened into one table, split across several, or given a table per class. Lifecycle: an object exists when constructed, while a row exists when committed.
- Object-relational mapping (ORM) Day 93
- A technique for moving data between a relational database and objects in a programming language, so that rows become instances and columns become attributes. The mapping is never one-to-one, and every difficulty an ORM has comes from the two sides disagreeing about identity, about lifecycle, and about when work happens. An ORM is not a way to avoid learning SQL — it is a way to stop writing the boring ninety per cent of it, which only works if you can read the ten per cent that matters.
- Objective Day 141
- The score that ranks one candidate function above another during training, so that "better" means something specific. It is a number you chose, which is why a model optimises what you asked for rather than what you wanted.
- Oblivious (Symmetric) Tree Day 165
- A decision tree where every node at the same tree depth uses the exact same feature and split threshold, enabling ultra-fast SIMD evaluation.
- observability Day 40
- The extent to which you can understand what is happening inside a running system purely from the signals it emits, including questions you did not think to ask in advance.
- observability Day 42
- The practice of seeing what a running system is doing through logs, metrics, and traces, so you can find the layer where a problem lives instead of guessing (day 40).
- observed Day 123
- A groupby keyword for categorical group keys, default False, controlling whether every possible combination of declared categories appears in the result (False, including combinations never actually observed in the data) or only combinations that actually occur (True). With several categorical keys, observed=False's row count grows as the product of every key's category count.
- octal notation Day 9
- A three-digit way of writing permissions in which each digit is the sum, within one class, of read (4), write (2), and execute (1) — for example, 754.
- Odds Day 155
- The ratio of the probability that an event occurs to the probability that it does not occur: Odds = p / (1 - p).
- Odds form Day 115
- Bayes' theorem restated as posterior odds = prior odds x likelihood ratio, where odds = p / (1 - p). Mathematically equivalent to the probability form, but useful because the likelihood ratio isolates exactly how much a piece of evidence is worth, independent of the prior.
- Odds Ratio Day 155
- The ratio of odds between two conditions, equal to exp(w_j) for a unit increase in feature j in logistic regression.
- off-by-one error Day 51
- A mistake in which a loop runs one time too many or too few — often from hand-managed indices or boundary conditions — producing a wrong result that still looks plausible.
- offset Day 27
- A pagination parameter telling the server how many rows to skip before returning the next batch; simple and jumpable but can shift under inserts and slow down on deep pages.
- Offset Day 86
- The number of rows LIMIT skips before it starts returning any. Its cost is proportional to its size, because the engine must produce and discard every skipped row in order — so page 5,000 costs five thousand times what page 1 cost. Fine for the first few pages of a user interface, hopeless for walking a large table; the alternative is keyset pagination, which remembers the last key seen and asks for what comes after it.
- Offset Day 95
- The signed difference between a local wall clock and UTC at a given instant, returned by utcoffset() as a timedelta. Not a property of a zone but of a zone at a moment: Europe/London is +00:00 in January and +01:00 in July. Offsets are not always whole hours — Asia/Kolkata is +05:30 and Asia/Kathmandu +05:45 — which is why the type is a timedelta rather than an integer count of hours.
- One-Class SVM Day 187
- An unsupervised kernel method that learns a soft boundary enclosing nominal data points in high-dimensional feature space.
- one-hot encoding Day 137
- One 0/1 column per category, in an explicit category order derived from the training data. Honest about the absence of order, costs one column per level, and lets a category the training data never held become a row of zeros rather than a crash or a new column. Known in econometrics as dummy variables for most of a century.
- One-Hot Encoding Day 203
- Representing a categorical digit target k in {0..9} as a 10-dimensional binary vector with a 1 at index k and 0s elsewhere.
- One-Hot Encoding (OHE) Day 170
- A representation where categorical variables are converted into binary indicator vectors with mutually exclusive active bits.
- One-nearest-neighbour classifier Day 141
- A model whose fit step stores the training set and whose predict step returns the label of the closest stored point. Its training accuracy is exactly 1.000 by construction, because a training point's closest stored point is itself at distance zero -- unless two identical feature rows carry different labels, which is the sole exception and does occur in iris.
- One-over-root-n Day 144
- The rate at which a sampling error shrinks. Quadrupling a test set halves its interval rather than quartering it, so precision never becomes cheap -- going from 500 rows to 5000 buys a factor of 3.2.
- One-vs-Rest (OvR) Day 156
- A multiclass classification heuristic that trains K separate binary models, each predicting one class versus all other classes combined.
- OneCycleLR Day 207
- A super-convergence schedule that warms up learning rate to a peak while decreasing momentum, followed by long cosine decay.
- ONNX Day 193
- Open Neural Network Exchange: a cross-platform, open format for executing machine learning models across heterogeneous hardware.
- OpenAPI Day 82
- A specification format for describing an HTTP API in a machine-readable document. It began as Swagger, created by Tony Tam at Wordnik around 2010, and was donated to the Linux Foundation in 2015, forming the OpenAPI Initiative. FastAPI generates the document from your routes and models and serves it at `/openapi.json`; the lab's reports itself as version 3.1.0.
- operating system Day 1
- The master program that manages the hardware, shares the CPU and memory among running programs, and handles all input and output.
- operating system Day 6
- The software layer that manages a computer's hardware and provides common services to programs — a manager of resources, an illusionist providing private-machine fictions, and a guard enforcing protection.
- Operation count Day 153
- Multiply-add operations computed by formula rather than timed on a clock, so the comparison survives a different machine unchanged. 54,813 for the closed form on the diabetes shape against 64,452,440 for gradient descent to reach 9-decimal agreement -- about 1176 times more.
- OperationalError Day 90
- The exception raised when the database could not do the thing at all: no such table, no such column, a syntax error, a locked file, a full disk. It sits between IntegrityError, which is about the data, and ProgrammingError, which is about your code.
- operator precedence trap Day 122
- The fact that `&` binds more tightly than comparison operators (`>`, `<`, `==`) in Python, so `df.a > 1 & df.b < 2` does not group as `(df.a > 1) & (df.b < 2)` the way it visually reads. Every comparison combined with `&`, `|` or `~` must be individually parenthesised.
- Optimism Day 144
- The gap between a score measured on data that influenced a choice and the score on data that did not. In this lesson it has a sign, a size, a formula and a control -- which is what distinguishes it from a warning.
- Optimization Leakage Day 166
- The phenomenon where hyperparameter tuning overfits a specific validation fold due to excessive trials, necessitating an untouched external test set for final audit.
- Option Day 80
- An argument identified by name, so it can appear in any order: `--store notes.json`. Conventionally offered in a long form (`--store`) and often a short one (`-s`). The long form is for scripts, where readability matters six months later; the short form is for typing.
- option (flag) Day 56
- A named command-line argument that starts with dashes, such as `--email ada@example.com` or a boolean switch like `--force`; options can be required or optional and may take a value or stand alone.
- Optional Day 75
- The type of a value that is either an `X` or nothing, written `Optional[X]` in older code and `X | None` in modern code — the same type, two spellings. Writing it down is what forces every use site to handle absence, and the missing check is the single most valuable thing a checker catches, because tests routinely miss it.
- Orchestrator Day 98
- A system that runs pipelines rather than being one: it schedules tasks, tracks dependencies between them, retries individual tasks, records the history of every run, and gives you a user interface to inspect and rerun. Airflow, Dagster and Prefect are the widely used open-source ones. An orchestrator supplies none of the five promises in this lesson — it would run this same program — and it starts earning its keep when you have dependencies between tasks, per-task retry, backfill as a first-class operation, or more than one machine.
- order dependence Day 126
- The fact that some pipeline steps produce different, equally defensible results depending on which order they run in -- normalising string casing before deduplicating catches variant-cased duplicates that deduplicating first would miss. A pipeline should declare its required order and the reason, rather than leaving it to whichever order someone happened to write the calls in.
- ordinal encoding Day 137
- Replacing each category with its position in a list. Correct when the order is real -- small, medium, large -- and a trap when it is not, because the code is a number and the model will read the gap between two categories as a quantity. Measured here on six unordered paint colours, the ordinal model could only produce a monotone climb from 0.252 to 0.415 and was out by 0.383 on the worst colour, where one-hot reproduced every observed rate to within 0.0000002.
- Orientation Day 102
- Which way round a shape is wound — anticlockwise or clockwise. A positive determinant preserves it and a negative one reverses it, meaning the plane was turned over. No rotation undoes a reversal, in the same way no amount of turning a left glove makes it a right one. Measured by the sign of a polygon area computed with the shoelace formula.
- origin Day 32
- The conventional default name Git gives the remote a repository was cloned from; it means "the place this repository came from."
- orphan figure Day 133
- An image file written into a report's output directory that the report's text never links to. It is either a figure you meant to discuss and forgot, or a leftover from an earlier run that will mislead whoever opens the directory next. The lab detects one by comparing the image links in the rendered Markdown against the files actually on disk.
- Orphan row Day 87
- A child row whose foreign key points at a parent that does not exist. In SQLite these accumulate silently in any database written to by an application that never enabled foreign-key enforcement, because the insert that creates one succeeds with no error and no warning.
- Orthogonal Day 103
- At right angles: the dot product is exactly 0 and the cosine similarity is exactly 0. The word to reach for is unrelated, not opposed — opposed is a cosine of -1. In the lesson's table, roast-chicken and storm-bulletin are orthogonal because wherever one has a count the other has none, so every product in the sum is 0. They share no vocabulary at all, and nothing you learn about one tells you anything about the other.
- Orthogonal Day 106
- At right angles — two vectors are orthogonal when their dot product is zero, which Day 103 established means a cosine similarity of zero and no shared component at all. For a set of vectors it means every pair is mutually perpendicular. Symmetry of a matrix guarantees its eigenvectors are orthogonal, which is what gives PCA its second useful property beyond finding the best directions: the projections of the data onto different principal components are UNCORRELATED, measured at 6.420e-16 in this lesson. It is also the hidden condition on the textbook claim that the Rayleigh quotient converges quadratically — measured, that holds for a symmetric matrix and fails for a non-symmetric one whose eigen-lines meet at 71.5651 degrees rather than 90.
- Out-of-Bag (OOB) Sample Day 163
- The ~36.8% of training observations omitted from a given bootstrap sample, used for internal cross-validation and unbiased error estimation.
- Out-of-Fold (OOF) Predictions Day 168
- Predictions generated on validation folds during cross-validation, creating a leak-free meta-dataset representing true model generalization.
- Out-of-Fold (OOF) Target Encoding Day 170
- Computing target encodings strictly on complementary cross-validation folds to eliminate target leakage.
- out-of-fold encoding Day 137
- Computing a target encoding for each training fold from the means of the other folds, so a row's own target never contributes to its own feature value. It is a refinement inside the training half, not a licence to fit on the test set. Worth a further 1.2 points over naive encoding on the training rows in this lesson's measurement.
- Out-of-fold residual Day 154
- A residual computed on a training row while that row was held out of the fold used to fit the model -- via cross_val_predict -- so the residual reflects genuine held-out error rather than a fitted value the model has already seen. Used here to size the prediction interval without touching test rows at all.
- Out-of-Scope Use Day 182
- Explicit declarations of applications, populations, and contexts where the model is strictly prohibited from being used.
- Outer join Day 87
- A join that keeps rows which matched nothing. LEFT keeps every row from the left table, filling the right-hand columns with NULL when there was no match; RIGHT is its mirror image and is rarely needed, since swapping the table order and using LEFT is easier to read; FULL keeps unmatched rows from both sides. The NULL an outer join produces is not stored in any table — the join manufactures it to fill columns that had no matching row.
- Outlier sensitivity Day 149
- How far an estimator's fit moves in response to one extreme point. Measured directly here: moving a single point 80 units off the line moved OLS's slope by 0.7545, Huber's by 0.0437 and the median fit's by 0.0104.
- output contract Day 126
- A check, run after a pipeline's last step, that the result meets the promises the pipeline is supposed to keep (no missing values in a required column, no value above a configured ceiling, a required derived column present). Proven meaningful only by demonstrating it can genuinely fail when a step is sabotaged, not merely that it passes on correct input.
- Output stripping Day 139
- Clearing a notebook's outputs, execution_count and per-cell execution timestamps before it is committed to version control, typically via an nbstripout-style pre-commit hook. It removes the noisy part of a notebook's diff at the cost of removing the evidence the notebook was ever actually run.
- over-engineering Day 63
- Adding more structure, configurability, or abstraction than the problem needs — the opposite failure from tangled code, and just as costly, because the extra machinery must be built, understood, and maintained forever. YAGNI is the habit that prevents it.
- Overfitting Day 145
- A model having enough freedom to fit the noise in this particular training set, so that what it learned includes things that will not be true next time. It is the variance term of the decomposition, not a synonym for complexity: a complicated model on enough data does not overfit, and a simple model on three points can.
- overflow Day 4
- What happens when an arithmetic result exceeds what a fixed-width register can hold: the value silently wraps around, as when an unsigned byte computes 255 + 1 = 0.
- Overflow to inf, then nan Day 111
- What a diverging gradient-descent run looks like numerically in IEEE-754 floating point: the tracked value grows without bound until it exceeds the largest representable float and becomes inf, after which the next arithmetic operation (inf minus a finite multiple of inf, for instance) produces nan. Neither raises an exception by default -- a training loop must check its own loss for finiteness to catch this.
- Overlapping run Day 81
- A second copy of a job started by the scheduler while the first is still working, which happens the first time a job takes longer than its interval. Two copies reading and writing the same data is how a scheduled job corrupts its own output. Neither cron nor launchd prevents it by default.
- overplotting Day 127
- Marks landing on top of each other so that the picture stops representing how many there are. Measured here as 10,000 unclipped points painting only 6,349 distinct pixels, in an image containing exactly two grey levels -- the density is not faint, it is absent.
- overplotting Day 130
- What happens to a scatter plot once there are enough points that many of them land on, or very near, the same pixel -- the plot stops showing individual observations and starts showing a silhouette of density with no indication of how many points are stacked at any location. Transparency (alpha), hexbin, and 2-D density estimates are three different fixes, each trading away something different.
- overriding Day 68
- Defining a method in a subclass that replaces the parent's version entirely. The parent's implementation does not run.
- p-norm Day 107
- The single formula that generates the whole family: raise every absolute component to the power p, add them, and take the p-th root. p = 1 gives L1, p = 2 gives L2, and letting p run to infinity gives L-infinity. The value falls as p rises and never falls below the largest single component. Below p = 1 the formula still returns a number, but the triangle inequality fails and it is no longer a norm — which is why a careful implementation refuses it rather than answering. Also called the Minkowski norm, after Hermann Minkowski, whose Geometrie der Zahlen of 1896 studied the geometry that results from replacing the round unit circle with a different convex shape.
- p-value Day 118
- P(data at least this extreme | the null hypothesis is true). Not the probability the null hypothesis is true, and not the probability the observed effect is real -- both of those require a prior probability the p-value never supplies, exactly the ingredient Day 115's Bayes' theorem needs and a p-value alone does not have.
- package Day 13
- A bundle of a program's files together with metadata describing what it is, its version, and what other software it depends on — the unit a package manager installs, updates, and removes.
- package Day 43
- A reusable library of Python code, published on PyPI and installed with pip, that adds functionality beyond the standard library.
- package Day 59
- A directory of modules that Python treats as one importable name, marked by an __init__.py file. A package groups related modules under a shared name — for example wordstats/ containing tokens.py and stats.py, imported as wordstats.tokens.
- Package Day 83
- In the import sense, a directory of modules with an `__init__.py`, importable as one unit. This is what you write `import` in front of. It is not the same thing as a distribution package, and the two are not required to share a name.
- package manager Day 13
- A program whose job is to install, upgrade, and remove software from curated repositories, automatically resolving dependencies and keeping a local record of everything it has done.
- packet Day 15
- A small, individually addressed chunk of data that the network routes independently; messages are split into packets and reassembled at the destination.
- packet Day 17
- A small, individually addressed unit of data sent across a network; TCP and UDP wrap application data into packets carrying source and destination ports.
- page Day 3
- The fixed-size unit (commonly 4 or 16 KB) in which virtual memory is mapped, protected, and, when necessary, moved between RAM and disk.
- Page Day 85
- The fixed-size unit a database engine reads and writes — 4,096 bytes on both SQLite builds used for this lesson. A row lives inside a page and a page usually holds many rows, which is why changing one field rewrites four kilobytes rather than the whole file. Bytes 16 and 17 of the file header record the size.
- page cache Day 3
- The OS's use of otherwise-free RAM to keep copies of recently read disk contents, so repeated file reads are served at RAM speed instead of storage speed.
- Pager Day 85
- The SQLite layer that caches pages in memory, takes locks, decides what is written when, and implements rollback. Every ACID guarantee is made here; nothing above it knows what a transaction is. It is also where SQLite's concurrency model lives: many readers at once, one writer at a time.
- pagination Day 27
- Splitting a large result set into ordered, individually requestable chunks (pages) so no single response has to carry all of it.
- Pagination Day 79
- Splitting a long listing across several pages. The robust way to follow it is to follow the next link until there is not one, because the last page typically renders the control as disabled text rather than an anchor. Stopping on a fixed page count or a fixed item count works today and silently misses tomorrow's new page.
- pagination to exhaustion Day 134
- Fetching every page of a paginated API response by following the source's own stopping signal (such as a has_more flag or the absence of a next link) rather than a page count computed in advance, which can silently drift out of sync with how much data the source actually holds.
- paint Day 20
- The final rendering step, in which the browser fills in the pixels — text, colors, borders, and images — for the laid-out elements.
- pandas.json_normalize Day 135
- A pandas function that flattens nested JSON (a list of dicts, possibly with nested lists and dicts) into a DataFrame. Called with no record_path, it produces one row per top-level record, leaving nested lists untouched inside each cell. Called with record_path, it produces one row per element of the named nested list instead.
- pandas.read_json Day 135
- A pandas function that reads JSON directly into a DataFrame, appropriate when the source JSON is already close to tabular. Pointed at a genuinely nested payload, it does not flatten nested structures and does not raise an error either -- it leaves them as raw Python objects inside each cell, which is why this lesson calls it too blunt for the customers-with-orders shape it is built around.
- pandera Day 126
- A Python library for declaring a DataFrame's expected schema -- column names, dtypes, value ranges and custom checks -- as data rather than as hand-written if-statements, raising a structured error when a frame fails to conform. Not installed in this lesson's environment; described from its documentation only.
- Papermill Day 139
- A tool that executes a parameterised notebook from the command line or a script, producing one output notebook per set of parameter values. This lesson describes and reproduces its parameter-injection mechanism from documentation; papermill itself is not installed or run in this lesson's lab.
- parallelism Day 7
- Executing more than one task at the same physical instant, which requires multiple execution units such as several CPU cores or a GPU's thousands of cores.
- Parallelism Day 96
- A property of the hardware: several pieces of work are executing at the same instant, which requires several execution units. Two cooks at two boards. In CPython you get it from processes and not from threads, because a thread must hold the interpreter lock to execute Python bytecode. Concurrency without parallelism is normal and often ideal; an event loop is exactly that, by design.
- parameter Day 22
- A value that refines a request, most often a query parameter appended after the path (such as ?userId=1) to filter or configure what the API returns.
- parameter Day 57
- A name listed in a function definition that stands for a value the function will receive; for example numbers in def mean(numbers):. Parameters live in the definition, arguments in the call.
- Parameter binding Day 90
- Attaching values to a statement that has already been compiled. Because compilation happens before any value exists, a bound value cannot change what the statement means: it arrives at the engine as a value of a storage class and is compared to a column. This is the entire defence against SQL injection, and it costs one character.
- Parameter Groups Day 206
- A PyTorch optimizer feature allowing different learning rates, weight decays, and hyperparameters for distinct subsets of model parameters.
- Parameterised query Day 85
- A statement compiled with placeholders — ? in Python's sqlite3 module — to which values are bound afterwards. Because the statement is compiled before any value is present, a value cannot become part of the statement. This is the whole of SQL injection defence; it applies to values only, never to table or column names.
- Parameters cell Day 139
- A cell tagged "parameters" (by convention, in the cell's metadata) that holds a notebook's default inputs. A parameterisation tool such as papermill locates this cell and inserts a new "injected-parameters" cell immediately after it for each run, overriding the defaults without editing the original cell.
- Parametrization Day 72
- Supplying one test function with several sets of arguments via @pytest.mark.parametrize, so that pytest expands it at collection time into one independent test item per set. It is not a loop: N cases become N items that each run to completion and each report separately.
- parent Day 30
- The commit that came just before a given commit; the parent reference is what links commits into a chain reaching back to the first commit.
- Parquet Day 121
- A typed, columnar binary file format from the Apache Arrow project. Unlike CSV, a Parquet file stores each column's dtype explicitly, so reading it back is a lookup rather than a re-inference -- the reason a Parquet round-trip preserves dtypes exactly where a CSV round-trip does not.
- parse_dates Day 121
- A read_csv() argument naming which columns to parse as datetime64 rather than leaving them as plain text. Without it, a date column is the pandas-3.0 str dtype and sorts lexicographically, which silently disagrees with chronological order the moment date formatting is inconsistent.
- parsing Day 24
- The reverse of serialization: reading a string and reconstructing an equivalent in-memory value from it. Also called deserializing.
- Partial Dependence Plot (PDP) Day 178
- A visual tool showing the marginal average effect of one or two features on predicted outcomes while integrating over other features.
- Partial derivative Day 109
- The derivative of a function of several variables with respect to one of them, with all the others held constant — Wikipedia's definition is exactly that. Written with a rounded d, as ∂f/∂x. It is not a different kind of derivative with different rules: freezing the other inputs turns a function of several variables into a function of one, and every rule from Day 108 then applies unchanged. The rounded symbol is a note to the reader that other inputs exist and are being held still, nothing more. For f = x² + 3y², freezing y leaves x² plus a constant, so ∂f/∂x = 2x.
- Partial index Day 89
- An index with its own WHERE clause, covering only the rows that satisfy it. Far smaller — in this lesson's lab, 186 pages against 1,857 for the equivalent full index — and usable only for queries the planner can prove fall inside that clause. A query without the matching condition will not use it, and that is correct behaviour rather than a disappointment.
- Partial success Day 84
- A run in which some items succeeded and some failed. It is the normal case for a batch job rather than an exception, and it needs its own exit code: returning 0 because most of it worked is the most common way an automation lies to the person who owns it, and the lie can go undetected for months.
- Partial success Day 98
- A run that did its job for some of its inputs and not for others: four sources answered and one did not, or 9,996 records were good and four were not. It is a third outcome, not a rounding error on the other two, and it needs its own exit code. Reporting it as success is how a source goes dark for a month unnoticed; reporting it as failure trains everyone to ignore the alert.
- Partition Day 91
- The set of rows a window function computes over, named by PARTITION BY — the tier, the book, the source document. It resembles a GROUP BY grouping except that the rows survive: each row in the partition still comes back, now carrying the computed value.
- partition invariant Day 122
- The check that a set of filters, taken together, accounts for every row of the original frame exactly once. A naive two-way split of a column with missing values (score > 50, score <= 50) fails this invariant, because rows where the column is NaN satisfy neither comparison and are silently missing from both halves.
- Partition tolerance Day 92
- The property that a system continues to operate despite an arbitrary number of messages being dropped or delayed by the network. It is not a design option you select — cables are cut and switches reboot whether or not you agreed to it — which is why it is a condition of the problem rather than one of three things to choose between.
- Patching Day 74
- Temporarily rebinding a name inside another module so it points at your double, and putting it back afterwards. `patch("a.b.c")` splits at the last dot, imports `a.b`, and does the equivalent of setattr — it is setattr with an undo, and nothing more.
- path Day 9
- A sequence of directory names separated by slashes that spells out the route to a file or directory in the filesystem tree.
- Path Day 110
- One route from a node to the output through the computation graph. A variable used more than once has more than one path, and its gradient is the sum of the path products. Reverse-mode differentiation never enumerates paths — it gets the same answer in one sweep, which is what makes it affordable on a graph where the number of paths grows exponentially with depth.
- PATH Day 8
- The list of directories a shell searches to find the program named by a command, so that typing `ls` locates and runs the `ls` program wherever it is installed.
- PATH Day 11
- An environment variable holding a colon-separated list of directories the shell searches, in order, to find the executable for a bare command name, running the first match.
- Path length Day 112
- The total Euclidean distance travelled along an optimization path: the sum of the step sizes between every pair of consecutive points. Two runs can reach nearly identical final losses with path lengths differing by an order of magnitude or more, which is exactly what happened in this lesson's opening comparison.
- Path Length h(x) Day 187
- The number of edges traversed from the root node to a terminating leaf node in an Isolation Tree.
- path operation Day 82
- FastAPI's name for one route: the decorator, the path string, and the function beneath it. The decorator carries everything about the contract that is not in the signature — the status code, the response model, the tags and the documented alternative responses.
- path parameter Day 82
- A named piece of the URL path, written `/items/{item_id}` and received as a function argument. The URL carries text, always; the annotation `item_id: int` is what converts it, and text that cannot be converted produces a 422 with `"loc": ["path", "item_id"]` before the handler is entered.
- pathlib Day 60
- The standard-library module for filesystem paths as objects rather than strings: Path("data") / "file.json" joins correctly on any operating system, and .glob / .rglob walk folders for matching files. The modern replacement for os.path.
- pathlib Day 64
- The standard-library module, added in Python 3.4 through PEP 428, that represents paths as objects rather than strings. `Path` joins with the `/` operator using the correct separator for the platform, and offers `exists`, `mkdir`, `read_text`, `iterdir`, `glob`, and `rglob`.
- patience Day 207
- The number of non-improving epochs allowed by ReduceLROnPlateau before triggering a learning rate reduction.
- Patience Day 145
- Waiting a fixed number of non-improving epochs before stopping, and restoring the best weights rather than the last. Necessary because a test curve wanders -- this one rose to 7.1435 and partly recovered without ever beating its epoch-14 value.
- Patience Day 210
- The number of consecutive validation checks allowed without metric improvement before early stopping is triggered.
- payload Day 21
- The body of a request or response — the actual data being sent or returned — as distinct from the headers that describe it.
- payload Day 22
- The data carried in the body of a request or response — for example the JSON describing a thing to create in a POST, or the data returned in a response.
- payload Day 26
- The body of a webhook delivery — a small JSON document describing the event, including its type, an identifier, a timestamp, and the relevant data.
- PCRE Day 38
- Perl Compatible Regular Expressions, a widely used C library from 1997 that spread Perl's rich regex syntax to many tools and languages, shaping the modern PCRE-style flavor.
- pd.NA Day 120
- pandas' newer, dtype-agnostic missing-value marker, used by nullable extension dtypes such as Int64, distinct from the float-only NaN.
- pdb Day 48
- Python's built-in interactive debugger, which lets you pause a running program at a prompt and inspect variables, step line by line, and continue.
- Pearson correlation Day 116
- A measure of LINEAR association between two variables, on a scale from -1 to +1. Blind to any non-linear relationship: a perfect, symmetric parabola (y = x^2) has a Pearson correlation of essentially zero despite y being exactly determined by x.
- Pearson correlation Day 130
- A number from -1 to 1 measuring the strength of a LINEAR relationship between two variables (Day 116). It is close to zero for a strong relationship of any other shape -- including a perfectly deterministic parabola -- because Pearson correlation has no way to represent curvature, only a straight-line trend.
- Peeking Day 118
- Checking a hypothesis test's p-value repeatedly as data arrives and stopping at the first significant result. Inflates the true false-positive rate well past the nominal alpha, even though every individual p-value along the way was computed correctly -- measured in this lesson at nearly 4x the nominal rate under a true null.
- Peeking (optional stopping) Day 119
- Checking an experiment's significance repeatedly during data collection and stopping the moment a threshold is crossed. Inflates the true false-positive rate well above the nominal alpha, because the analyst is effectively running many correlated tests and taking the most favorable one. Demonstrated in this lesson on real data: a genuinely significant experiment's running p-value dips below 0.05, rises back above it, and only stabilizes much later.
- Pegasos Algorithm Day 169
- Primal Estimated sub-GrAdient Solver for SVM, an efficient stochastic subgradient descent algorithm for linear SVM optimization.
- PEP 20 (the Zen of Python) Day 61
- A short list of guiding aphorisms for Python design — "Readability counts", "Explicit is better than implicit", "Simple is better than complex", "There should be one obvious way to do it" — printed by running `import this`. It is a set of tie-breakers for choosing between competing designs.
- PEP 257 Day 61
- Python's Docstring Conventions: how to write the triple-quoted string that documents a module, function, class, or method — a one-line summary in the imperative, a blank line, then any detail — describing what the object does and why, not a line-by-line account of how.
- PEP 8 Day 49
- The official style guide for Python code, which codifies conventions such as `lower_case_with_underscores` names, four-space indentation, and short lines to keep code readable and consistent.
- PEP 8 Day 61
- Python's official Style Guide for Python Code: conventions for naming (snake_case for functions and variables, CapWords for classes, UPPER_CASE for constants), indentation (4 spaces), spacing around operators, line length, and import order. It is guidance for readability, applied with judgement rather than pedantry.
- PEP 8 Day 76
- The Style Guide for Python Code, introduced in 2001 and authored by Guido van Rossum, Barry Warsaw and Nick Coghlan. It gives Python its naming conventions (`snake_case`, `CapWords`, `UPPER_CASE`), four-space indentation, spacing and import-grouping rules — and it explicitly instructs you to break its own rules when following them would hurt readability. The `E` and `W` rule codes descend from a checker written against it.
- Per-file ignore Day 76
- A configuration entry that relaxes specific rules for a pattern of files, written under `[tool.ruff.lint.per-file-ignores]`. The classic case is `"test_*.py" = ["S101"]`: `assert` is the mechanism of a test, so the security rule distrusting it is noise there and only there. Preferred to a global ignore, which stops the rule protecting the code where it still applied.
- per-module override Day 75
- A `[[tool.mypy.overrides]]` block applying different settings to named modules. It is the mechanism for incremental adoption: strict everywhere, with a checked-in list of named exceptions that is visible to everyone and shrinks over time — a work queue that cannot be forgotten.
- percentile Day 40
- A value below which a given fraction of measurements fall; the p95 latency is the value below which 95% of requests finished, describing the slow tail that averages hide.
- Percentile Day 116
- The value below which a given percentage of the data falls. When the target percentile does not land exactly on a data point -- the ordinary case -- the result depends on an interpolation convention; numpy.percentile() documents nine of them (method=), and they can genuinely disagree on the same data.
- percentile bootstrap interval Day 133
- An interval built by resampling the observed data with replacement many times, recomputing the statistic on each resample, and taking the 2.5th and 97.5th percentiles of the resulting distribution. Day 118's confidence interval obtained by simulation rather than by formula, which is what you reach for when the statistic has no tidy standard error -- a ratio of two window means, for instance.
- Perceptron Convergence Theorem Day 197
- A mathematical theorem proving that the perceptron learning algorithm will converge in finite steps if the data is linearly separable.
- Perceptron Learning Rule Day 197
- An iterative online optimization algorithm that updates weights proportional to the classification error and input feature values.
- permission Day 6
- A rule attached to a file or resource stating which users may read, write, or execute it; the kernel checks permissions during system calls, producing "Permission denied" on failure.
- permission Day 9
- A rule recording whether a class of user (owner, group, or other) may read, write, or execute a given file or directory.
- Permutation Feature Importance Day 163
- A model-agnostic feature importance metric that measures the drop in model score when values of a single feature are randomly shuffled.
- Permutation Feature Importance Day 168
- A model-agnostic feature evaluation technique that measures the performance decrease after randomly shuffling the values of a specific feature column.
- Permutation Feature Importance Day 178
- Model-agnostic importance measuring validation score drop when values of a single feature column are randomly shuffled.
- Permutation test Day 118
- A hypothesis test built by shuffling group labels on pooled data thousands of times, recomputing the statistic each time, and reading the p-value off how often a shuffle produced something at least as extreme as what was actually observed. Requires no assumption about the population's distributional shape.
- Perplexity Day 186
- A hyperparameter in t-SNE controlling the effective number of nearest neighbors considered when building Gaussian affinity distributions.
- persistence Day 56
- Keeping data beyond a single run of a program by writing it to durable storage such as a file; a tool that persists its records to JSON remembers them the next time it is launched, unlike data held only in memory.
- personal access token Day 32
- A long, random, revocable secret used in place of an account password when authenticating to a hosting platform over HTTPS; it can be scoped to specific permissions and given an expiry date.
- Personal data Day 79
- Information about identifiable people — names, photographs, profiles, reviews, posts, addresses. The rule to hold onto is that publicly visible is not the same as free to collect, store and republish, because those are three separate acts that data-protection regimes treat separately. Aggregation changes the character of the data: a hundred unremarkable public facts about one person become a profile.
- Perspective distortion Day 132
- The effect of a 3D projection on a comparison the chart exists to support: under perspective the drawn size of a mark depends on its depth, so identical data drawn at different depths draws at different sizes. Measured here, two bars with a data ratio of 2.000 draw at 2.341 or 4.204 depending only on which one stands nearer, while flat bars reproduce 2.000 exactly. The third dimension in such a chart carries no data at all.
- Pickle Vulnerability Day 193
- A critical security flaw where unpickling untrusted files allows arbitrary code execution via Python object reconstruction.
- Pickling (in the concurrency sense) Day 96
- The serialisation that every value crossing a process boundary must undergo. It has two practical consequences that catch people. Functions are pickled by module and qualified name rather than by code, so a process pool target must be a module-level function — a lambda, a closure or a nested function raises. And arguments and results are COPIED, so sending large data to a worker and getting large data back can cost more than the computation you were parallelising.
- PID Day 7
- Process identifier — the unique number the operating system assigns to each process, used to observe it (ps -p) and signal it (kill).
- pin_memory Day 205
- A boolean flag allocating CPU tensors in page-locked host memory for accelerated DMA transfers to accelerator devices.
- pip Day 43
- Python's package installer: the tool that downloads and installs libraries into whichever environment is active, by default from PyPI.
- pipe Day 10
- The `|` operator, which connects one command's standard output directly to the next command's standard input so data flows between programs without any intermediate file.
- pipeline Day 2
- The assembly-line organization of the instruction cycle in which the fetch, decode, execute, and write-back stages of consecutive instructions overlap, so one instruction can finish every cycle.
- pipeline Day 41
- A task broken into ordered stages where each stage must pass before the next begins, typically lint then test then build then deploy.
- Pipeline Day 77
- The ordered sequence of stages a change passes through on its way to being merged or deployed. In this lesson the pipeline is the five stages inside check.sh; in a larger system it also includes packaging, deployment and smoke tests. The ordering principle is the same at every scale: cheapest feedback first.
- Pipeline Day 80
- Several programs joined so that each one's standard output becomes the next one's standard input, as in `notes export --format json | python3 -m json.tool`. A tool composes in a pipeline only if its result is machine-readable and its diagnostics are somewhere else.
- Pipeline Day 98
- A program that moves data from where it is produced to where it is asked questions, in stages. The word is misleading if you hear it as plumbing: the code that moves the data is the easy half. A pipeline is defined by its behaviour when a stage fails — which is why it is more useful to think of it as a set of promises about what happens when something goes wrong than as a sequence of transformations.
- pipeline (data) Day 126
- A named sequence of pure, frame-to-frame functions applied in a declared order, with contracts checked at both ends, so the same input and configuration always produce the same output -- as opposed to an ad hoc sequence of notebook cells run in whatever order they happen to be clicked.
- Pipeline as an estimator Day 146
- A Pipeline implements fit/predict/score/get_params/set_params itself; it is not merely a container. Measured to refit a wrapped preprocessing step exactly once per cross-validation fold, on that fold's training rows only.
- pivot Day 124
- The DataFrame method that converts long format back to wide format by placing one column's values into the row index, another column's values into the column labels, and a third column's values into the resulting cells. Raises ValueError if any index/column pair repeats, since it has nowhere to place two values in one cell.
- pivot_table Day 123
- A DataFrame method built on groupby that reshapes an aggregation into a cross-tabulation, with one grouping key sent to the row index and another to the columns, filling combinations that were never observed with a chosen fill_value rather than omitting them silently.
- pivot_table Day 124
- pivot's aggregating cousin: reshapes long format into wide format the same way pivot does, but resolves a duplicate index/column pair by applying an aggregation function (aggfunc, "mean" by default) instead of raising an error.
- pixel Day 5
- The smallest element of a raster image, holding a single color value.
- Pixel Day 105
- One sample of a raster image: a single position and the value stored there. The word is a contraction of "picture element", coined at NASA's Jet Propulsion Laboratory in the 1960s. For the purposes of transformation, a pixel is not a point — it is a little SQUARE. Pixel (x, y) covers the region from (x, y) to (x + 1, y + 1), and the point that represents it is its centre at (x + 0.5, y + 0.5). Treating it as a point at its corner instead is the half-pixel error that displaces an entire image.
- Pixel Normalization Day 203
- Rescaling raw integer pixel intensities from [0, 255] to floating-point values in [0.0, 1.0].
- place value Day 4
- The worth of a digit position in a positional numeral system: powers of 10 in decimal, powers of 2 in binary, powers of 16 in hexadecimal.
- Placeholder Day 90
- The marker in a SQL statement where a value will go: ? in qmark style, which takes a sequence, or :name in named style, which takes a mapping. Python's sqlite3 module declares qmark in sqlite3.paramstyle. A placeholder can stand in for a value only — never for a table or column name.
- plain text editor Day 36
- A basic editor that stores characters and nothing more, with no awareness that the text might be code — the Notepad-style app that ships with an operating system.
- Plateau Day 111
- A region of a loss surface where the function value changes very little from step to step even though the gradient has not vanished -- distinct from a true flat region where the gradient itself is near zero. A stopping rule that only watches the loss cannot tell the two apart, and can declare victory on a plateau that is nowhere near a minimum.
- Plurality Voting Day 157
- A decision rule where the class receiving the most votes among the k nearest neighbors is selected as the predicted label.
- point estimate Day 133
- A single computed number with no statement of how firm it is -- "revenue fell 8.6%". Reported alone it is an assertion rather than a finding, because a reader cannot tell whether it would survive a different sample. In this lesson's generator a point estimate must be accompanied by an interval or by an explicit note saying why no interval is available.
- Point of means Day 148
- The point (mean of x, mean of y). A least-squares line fitted with an intercept passes through this point exactly, on any dataset -- a guarantee that follows from the fit, not a coincidence.
- point-in-time correctness Day 137
- Retrieving, for each training example, the feature values as they stood at that example's timestamp rather than as they stand now. It is temporal-leakage prevention turned into infrastructure, and it is the hardest part to build by hand across dozens of features.
- Poisson distribution Day 114
- The distribution of the count of rare, independent events in a fixed interval, with rate parameter lambda. Mean lambda, variance lambda — the only common distribution whose mean and variance are the same number. Arises as the n-to-infinity limit of Binomial(n, lambda/n).
- polars Day 120
- A DataFrame library for Python, written in Rust, built around multi-threaded execution. Unlike pandas, polars DataFrames have no implicit row index at all; every operation is positional by design, trading pandas' automatic label-alignment safety net for a simpler model and, on large data, faster execution.
- polling Day 26
- Repeatedly asking a server "has anything changed?" — the pull alternative to push, simple but wasteful because most requests return nothing and updates lag by the polling interval.
- Polyak Momentum Day 206
- An optimization technique that adds an exponentially decaying moving average of past gradients to the parameter update vector.
- Polynomial Feature Expansion Day 156
- A non-linear feature transformation that generates interaction terms and powers of original features, enabling linear models to separate curved manifolds.
- Polynomial regression Day 150
- Ordinary linear regression fitted to a design matrix that includes powers of a predictor (x, x^2, x^3, ...). Linear in its parameters throughout -- verified here by matching PolynomialFeatures plus LinearRegression against a direct normal-equations solve to thirteen decimal places.
- Population Day 117
- The complete set of things you would measure if you could measure everything -- every user, every possible model output, every unit that could ever be produced. Almost always too large, too expensive, or too undefined (still growing, still being generated) to measure directly, which is the entire reason sampling exists.
- Population Stability Index (PSI) Day 195
- A metric measuring the degree of divergence between two probability distributions, based on symmetric Kullback-Leibler divergence.
- port Day 17
- A number from 0 to 65535 in a packet header that identifies which service or program on a host the data is for.
- position on a common scale Day 127
- The top-ranked channel: two or more marks placed against one shared axis with one shared zero, so their values can be compared directly. A sorted bar chart and a dot plot both use it, which is why they win so often.
- position on non-aligned scales Day 127
- The second-ranked channel: the same kind of reading, but split across separate panels each with its own axis, so the reader must carry a value from one panel to the next. The cost of small multiples, and usually worth paying.
- positional argument Day 56
- A command-line argument identified by its position rather than a name, such as the FILE in `tool FILE` — the first value is understood to be the file because of where it sits.
- positional argument Day 57
- An argument matched to a parameter by its position in the call, in the order the parameters are listed — for example the "Ada" in greet("Ada", "Welcome") fills the first parameter.
- Positional argument Day 80
- An argument identified by where it appears rather than by a name. In `cp source.txt backup.txt` the first path is the source because it is first. Usually required, and there should be very few — a user cannot reliably remember an order longer than about two.
- positional parameter Day 12
- The numbered inputs a script receives on the command line — `$1`, `$2`, and so on — with `$#` giving their count and `$@` expanding to all of them.
- POSIX time Day 95
- The time model Python's datetime implements: every day contains exactly 86400 seconds, by definition rather than by observation. It is why leap seconds are unrepresentable, and why an epoch count silently repeats or stretches a second when one occurs. Accurate enough for everything except metrology and the very highest-precision reconciliation.
- POST Day 18
- The method for sending a body to be processed, often creating a resource; it is neither safe nor idempotent, so repeating it may duplicate a side effect. Every hosted-model call is a POST.
- Posterior Day 115
- P(hypothesis | evidence), the updated probability of the hypothesis after the evidence is taken into account -- what Bayes' theorem solves for. In the opening scenario, the posterior is P(condition | positive test) = 99/1098, about 9.02%.
- Power method Day 106
- An algorithm for finding the dominant eigenvector in three lines: multiply by the matrix, rescale to unit length, repeat until successive vectors stop moving. Rescaling changes no direction and exists only to stop the length running away — without it the vector grows by the eigenvalue every round and overflows float64 to infinity within a few hundred steps, destroying a direction that was already correct. Sign alignment is equally non-optional: when the dominant eigenvalue is negative the iterate flips end-for-end every step, so the convergence test never fires even though the answer settled on round three. Its convergence RATE is the ratio of the second eigenvalue to the first, measured at 0.399999 for a matrix with eigenvalues 5 and 2. It looks naive next to numpy.linalg.eig, and it is, for a small matrix — but it needs only the ability to compute A times v rather than the matrix itself, which is why every large-scale eigensolver is a refined descendant of it.
- Power-Law Distribution Day 189
- A heavy-tailed distribution where a small fraction of individuals accounts for the vast majority of total value (e.g. 80/20 rule).
- PR-AUC Day 176
- The Area Under the Precision-Recall Curve, reflecting model capability on rare positive classes without inflation from large true negative counts.
- PRAGMA foreign_keys Day 87
- The SQLite setting that turns foreign-key enforcement on. Enforcement arrived in version 3.6.19 (2009) and was disabled by default for backwards compatibility, so it must be issued for every connection. It cannot be stored in the database file, and it is documented as a no-op inside a transaction that returns no error and simply has no effect — which is why it is silently ignored in Python if issued after the first write, and why the habit is to issue it as the first statement after connecting.
- PRAGMA foreign_keys Day 88
- The per-connection setting that decides whether SQLite enforces foreign keys at all. It defaults to OFF and cannot be stored in the database file, so every program and every console session must set it for itself. Until it is set, a REFERENCES clause is decoration. PRAGMA foreign_key_check is the companion audit that finds damage already done.
- PRAGMA foreign_keys Day 90
- The per-connection switch that decides whether REFERENCES clauses are enforced. It is OFF by default in SQLite for backward compatibility, it is not a property of the file, and — the trap that catches people twice — setting it inside an open transaction is a silent no-op with no error and no warning. Run it in the connection factory, the instant the connection exists.
- pre-attentive attribute Day 127
- A visual property processed before conscious attention -- colour, size, orientation, motion, enclosure. One red dot among two hundred grey ones is found in roughly constant time; one labelled dot is found by reading. This is why highlighting one thing is powerful and highlighting five things is worthless.
- pre-commit hook Day 35
- A script git runs automatically before a commit is recorded, able to reject the commit — commonly used to run formatters, linters, or secret scanners.
- pre-commit hook Day 41
- A git hook that runs before a commit is recorded and can reject the commit by exiting with a non-zero status, acting as a local quality gate.
- Pre-commit hook Day 76
- A program git runs before a commit is created, which can refuse the commit. The `pre-commit` framework manages these from a `.pre-commit-config.yaml` file naming hook repositories and the revisions they are pinned to. It is what makes "we run the formatter" true rather than aspirational — and because it downloads and executes those repositories, the pinned revision is a security decision.
- Pre-commit hook Day 77
- A script Git runs before a commit is created, which can refuse the commit by exiting non-zero. Fast checks belong in one: formatting, linting, whitespace. The full test suite does not, because a hook that makes committing take twenty seconds gets bypassed with git commit --no-verify within a week.
- Pre-Pruning (Early Stopping) Day 162
- Regularizing a decision tree by halting recursive growth when predefined stopping thresholds (max_depth, min_samples_split) are met.
- Pre-registration Day 119
- Writing down the primary metric, the significance level, the sample size, and the stopping rule before the experiment's data exists, so none of them can be adjusted after the fact to make a result look better. The direct defense against metric shopping and segment fishing alike.
- Pre-registration Day 140
- Depositing an analysis plan with a third party before collecting or examining data, so that the ordering is attested by someone other than the analyst. Stronger than a locally written question file, because the timestamp is not yours to edit; the question file is its cheap local cousin, and it catches drift rather than fraud.
- precedence-safe expression engine Day 122
- A design, exemplified by polars' pl.col('a') > 1 syntax and pandas' own .query() strings, where comparisons and boolean combinators are composed inside one expression object or parsed string rather than through Python's own operator-precedence table applied to Series objects -- removing the `&`-binds-tighter-than-comparisons trap by construction rather than by convention.
- Precision (Positive Predictive Value) Day 159
- The proportion of predicted positive instances that are truly positive: Precision = TP / (TP + FP).
- precision loss (integer-to-float) Day 121
- The silent rounding that occurs when an integer larger than 2**53 is represented as a float64, because float64's 53-bit mantissa cannot address every integer beyond that boundary exactly. A column read as int64 is exact; the same column cast to float64 is not.
- Precision-Recall (PR) Curve Day 159
- A graphical plot showing the trade-off between Precision and Recall across all classification thresholds, especially informative for imbalanced datasets.
- Predicate Day 86
- An expression that evaluates to TRUE, FALSE or UNKNOWN — the thing a WHERE or HAVING clause tests. The rule that catches everyone is that these clauses keep a row or a group only when the predicate is TRUE, so UNKNOWN is discarded exactly like FALSE and nothing anywhere records that it happened.
- predict_proba() and predict() agreement Day 146
- predict(X) is defined as classes_[argmax(predict_proba(X), axis=1)] for any classifier implementing both -- measured to hold on every row of a fitted multiclass LogisticRegression, never independently computed.
- Prediction Drift Day 195
- A shift in the distribution of model output probabilities or predicted class labels over time.
- Prediction interval Day 154
- A range around a point prediction meant to contain the true value with some stated probability -- distinct from a confidence interval, which describes uncertainty about a parameter rather than about one future observation. Built here with a constant half-width of 105.8797 from training out-of-fold residuals.
- Predictor Day 146
- An estimator that additionally implements predict(), and usually predict_proba() and/or decision_function(). 119 of 210 discovered estimators, measured here.
- preemption Day 7
- The scheduler forcibly interrupting a running thread when its time slice expires or something more urgent arrives — the thread is not asked, it is stopped.
- Preprocessing Contamination Day 180
- Fitting transformers (imputers, scalers, encoders) on the combined dataset before splitting train and test sets.
- Primary key Day 85
- The column or columns chosen to identify each row. It guarantees two things on every write: no two rows share the value, and no row leaves it empty. It is a statement of identity rather than merely a uniqueness rule, and a good one names something that never needs to change.
- Primary key Day 87
- The column, or set of columns, that identifies a row uniquely within its table. In a junction table it is the pair of foreign keys together, which is what makes it impossible to record the same relationship twice.
- Primary metric Day 119
- The single, pre-declared number an experiment is judged by. Every other metric is either a guardrail (must not worsen) or exploratory (reported, never concluded from). Choosing the primary metric after seeing the data converts a legitimate analysis into an undisclosed multiple-comparisons problem.
- Primitive obsession Day 70
- Representing domain concepts with built-in types — a float for money, a string for a date or a category — so there is nowhere to put validation and wrong values pass silently. The fix is one meaningful type per concept.
- Principal component Day 106
- An eigenvector of a covariance matrix. The FIRST principal component is the one with the largest eigenvalue, and it is the direction along which the data varies most; each subsequent one is the direction of greatest remaining variance perpendicular to all the earlier ones. Principal component analysis is nothing more than computing these and keeping the ones whose eigenvalues are large — in this lesson the top component of a 400-point cloud came back at 30.101134 degrees against a true elongation of 30.0 that the code was never told. The eigenvalue IS the variance along its own component, so its square root is a standard deviation, and the proportions of the total are the explained-variance ratios behind every claim that 768 dimensions were reduced to 50. Because a component is an eigenvector it names an AXIS rather than an arrow: sign flips between library versions are routine and are not errors. Published by Karl Pearson in 1901 and independently named by Harold Hotelling in 1933.
- Principal Component Analysis (PCA) Day 185
- An unsupervised linear dimensionality reduction technique that transforms correlated features into orthogonal maximal-variance components.
- print Day 47
- The built-in function that writes its arguments to an output stream (standard output by default), converting each to text and adding a newline; its sep, end, file, and flush arguments control separators, line endings, destination, and buffering.
- print-debugging Day 48
- The practice of adding temporary print() calls to reveal a program's values and control flow; fast for a quick, specific question but requires editing and re-running.
- Prior Day 115
- P(hypothesis), what you believed about a hypothesis before seeing the evidence currently under consideration. In the opening scenario, the prior is the disease prevalence, 1/1000, before any test result is known.
- Prior Calibration (Logit Adjustment) Day 160
- A post-processing adjustment that shifts model logits to correct for differences between training sampling rates and true real-world class prevalence.
- private IP Day 16
- An address in a reserved range (10.0.0.0/8, 172.16.0.0/12, or 192.168.0.0/16) that works only inside a local network and is never routed on the public internet.
- Probability Day 113
- A number between 0 and 1 assigned to an event, satisfying three axioms: non-negativity, the whole sample space has probability 1, and disjoint events' probabilities add. For a finite space of equally likely outcomes, it reduces to |event| / |space|, computed in this lesson with fractions.Fraction for exactness.
- Probability Calibration Day 155
- The degree to which predicted probabilities match real-world empirical frequencies (e.g. among events predicted with 80% confidence, 80% actually occur).
- Probability density function (pdf) Day 114
- For a continuous random variable, the function whose integral over an interval gives the probability of landing in that interval. A pdf value is not itself a probability and can exceed 1 — Uniform(0, 0.5) has density 2 everywhere on its support and still integrates to exactly 1.
- Probability mass function (pmf) Day 114
- For a discrete random variable, the function that gives P(X = k) for every value k the variable can take. The pmf of a two-dice sum gives P(Y=7) = 1/6 and P(Y=2) = 1/36 — a shape, not a flat line, since 7 is exactly six times as likely as 2.
- process Day 6
- A program in execution: the running instance of a program file, with its own virtual address space, identity, and entry in the scheduler's ledger.
- process Day 7
- A running instance of a program: the program's instructions loaded into private memory, plus the PID, file handles, owner, parent, and state the operating system tracks to run and clean up after it.
- Process Day 96
- An independent program image with its own memory, its own interpreter and — the point — its own interpreter lock. Two processes share nothing by default, so anything passed between them is serialised with pickle and copied. That isolation is the source of both its value (true parallelism) and its costs (start-up time, copying, and targets that must be importable by name).
- producer Day 26
- In event-driven architecture, a service that emits events (for example, the system where a payment settles) for others to consume.
- program Day 49
- A complete piece of software that does one useful job end to end: it reads input, processes it, produces clear output, handles bad input gracefully, and is organized so it can be read and tested.
- program counter Day 2
- The special register holding the memory address of the next instruction; it advances at fetch time, and instructions that overwrite it create jumps and loops.
- ProgrammingError Day 90
- The exception raised when your code misused the module: the wrong number of bindings, named placeholders given a sequence, two statements in one execute, a connection used after close. It is always a bug and should never be caught and ignored. The most common instance by far is a missing comma — (value) is not a tuple, (value,) is.
- Projection Day 86
- What the SELECT list does: choosing which columns and computed values come out of the query. It is stage five of the evaluation, which is why an alias created in the projection is unavailable to WHERE, and why DISTINCT — which runs after it — de-duplicates the projected rows rather than the underlying ones.
- Projection Day 103
- How much of one vector lies along another — the length of the shadow b casts on a's direction when the light shines straight down. The scalar projection is (a dot b) divided by the length of a; the vector projection is that length pointed along a. On the lesson's 3-4-5 example, b of length 10 casts a shadow of length 6 on a. Note the asymmetry: projecting a onto b instead gives 3, because you have chosen a different surface to cast the shadow on, even though the dot product itself is the same either way.
- Projective transformation Day 105
- The next family up from affine: a 3 by 3 matrix whose bottom row is NOT (0, 0, 1), so the third coordinate does not come out as 1 and the first two must be divided by it. That division is what makes distant things smaller, and it is why parallel lines can converge. This is what perspective needs and what no affine transformation can produce. It is about five lines more code than the affine case.
- prompt Day 8
- The short piece of text a shell prints to signal it is ready for your input, such as `you@laptop %`; its exact look is set by the prompt string.
- prompt Day 47
- The text passed to input() and shown to the user before reading their reply, such as input("Your name: ").
- Propagation Day 97
- The record's journey up the dotted hierarchy after the logger it was created on has handled it — myapp.loader, then myapp, then root — with every handler it passes emitting it. Two things surprise people: the ancestors' levels are not re-checked, and the ancestors' filters are not applied at all. It is why one call can produce two lines, and it is also the mechanism that lets an application collect a library's records without knowing the library exists.
- property Day 67
- An attribute backed by functions. `@property` makes reads call a getter and `@name.setter` makes writes call a setter, so a rule can be added to an existing attribute without changing a single caller.
- Prosecutor's fallacy Day 115
- The specific, legally consequential instance of confusing P(evidence | innocent) with P(innocent | evidence). A small P(evidence | innocent) does not by itself imply a small P(innocent | evidence); the correct relationship between the two requires the prior probability of guilt and the size of the pool of people who could plausibly have produced the evidence, which is exactly what Bayes' theorem supplies and the fallacy skips.
- protected branch Day 33
- A branch the hosting platform refuses to let anyone push to directly; changes may enter it only through a pull request that satisfies its rules.
- protocol Day 15
- An agreed set of rules two computers follow to communicate, such as HTTP, TCP, IP, or TLS.
- protocol Day 68
- An informal interface defined by which methods an object has rather than by what it inherits from. Implementing a protocol is what lets builtins and library code written years earlier — `sorted`, `max`, a DataLoader — operate on a class you wrote this afternoon.
- Protocol Day 69
- The typing form of duck typing: a declaration that any object with the right methods satisfies the type, with no inheritance and no registration. Structural typing — the shape is the type — as against the nominal typing of a base class.
- Protocol Day 75
- A declaration of a required shape — a set of methods and their signatures — that any object satisfies by having them, with no inheritance and no registration. It is how you type an injected dependency such as a clock or a repository, so a test double satisfies the same annotation as the real thing without sharing a base class.
- Protocol Buffers Day 24
- A schema-first binary serialization format from Google, designed for compact, fast data exchange between high-volume internal services.
- Protocol, not magic Day 146
- The claim this lesson tests directly: five methods, implemented by hand with zero inheritance, reproduce library output exactly when called directly -- and, in this library version, stop being sufficient for interoperability with Pipeline and cross_val_score without also inheriting BaseEstimator.
- provenance Day 134
- Who published a dataset, when, and how to verify you are looking at the version they actually published. A source with no named publisher cannot be cited and cannot be safely re-fetched, because there is no way to confirm today's copy matches what was originally released.
- provenance Day 138
- Who collected a dataset, when, why, under what definitions, with what inclusion criteria, and what changed between versions. A dataset without it cannot be cited, re-fetched or compared across releases. In this lesson's version-drift example the provenance record is the only artifact in which the change exists at all, because every summary statistic is identical between the two releases.
- Provenance Day 79
- The record of where a piece of data came from: the source URL, the date it was fetched, and the rules in force at the time. Cheap to record while scraping and impossible to reconstruct afterwards. It is the same question that reappears later as dataset governance, when a training corpus or a retrieval index has to answer for its contents.
- Provenance Day 84
- A record of which configuration layer supplied each setting, printable on demand. It turns "why is it doing that?" from an afternoon of reading code into a five-second question, and it is the part of a configuration system almost nobody builds.
- Provenance Day 97
- The record of WHICH layer supplied a value, carried alongside the value itself and printable as a table. It exists because the expensive failure is not "the value is wrong", which you notice quickly, but "the value is not what I set it to and I have four places to look". It also makes a validation message actionable: "batch_size: 0 is below the minimum of 1 (from flag:--batch-size)" names the fault and the one place to fix it.
- Provenance Day 140
- The record of where data came from and under what terms: a URL, a retrieval date, a licence, a data dictionary and a cryptographic digest of the file as retrieved. Without it a result cannot be re-obtained by anyone, including its own author six months later.
- Provenance (of configuration) Day 98
- The record of which layer supplied each resolved setting — a default, a file, an environment variable or a command-line flag. Knowing that the timeout is three seconds is half an answer at three in the morning; knowing it is three seconds *because the deployment config file says so, and nobody overrode it* is the whole answer. A configuration system that cannot print its own provenance is a configuration system you debug by guessing.
- Provenance / Lineage Day 193
- The complete historical audit trail linking a model artifact to its training dataset, code commit SHA, and hyperparameters.
- provenance record Day 134
- A structured record of exactly three facts about a retrieved dataset -- the URL it came from, the timestamp it was retrieved, and its checksum -- built to be regenerated identically from the same fixture provided the timestamp is held fixed, since the real clock is the one part expected to vary.
- proxy Day 21
- An intermediary that sits between a client and a server and relays their traffic; a debugging proxy such as mitmproxy records every request that passes through it, revealing what an application is sending.
- proxy Day 138
- A recorded quantity standing in for an unrecorded one. The procedural discipline this lesson asks for is to name the proxy and the thing it stands in for, in writing, before optimising it -- because once the pair is written down, the question of whether the gap varies by group becomes askable and is frequently answerable from data already in hand.
- Proxy Feature Day 179
- An unprotected feature that correlates strongly with a protected attribute (e.g. zip code with race).
- Pseudo-Residual Day 164
- The negative gradient of the loss function with respect to model predictions (-dL/dF), serving as the training target for each subsequent boosting iteration.
- pseudonymisation Day 138
- Replacing a direct identifier with a stable substitute. It removes the name and preserves the ability to link rows across releases, which is often exactly what was wanted and is also exactly what makes re-identification tractable. Distinct from anonymisation, which is a claim that no individual can be singled out at all -- a claim that has to be substantiated by measurement rather than asserted by having deleted a column.
- public-key cryptography Day 19
- Encryption using a matched public/private key pair so two strangers can establish a secret without pre-sharing one; also called asymmetric encryption, and slower than symmetric.
- pull Day 32
- The command that fetches from a remote and then merges the downloaded commits into your current branch; equivalent to a fetch followed by a merge.
- pull request Day 33
- A formal proposal to merge the commits on one branch into another, presented with a diff, a description, a review discussion, and merge gates; abbreviated PR.
- Pure domain core Day 70
- The module holding the types and rules, importing nothing that performs input or output — no json, pathlib, open, print or input. Because it cannot touch the world, its rules can be tested from an empty directory.
- pure function Day 57
- A function whose output depends only on its arguments and which affects the world only through its return value (no side effects). Pure functions are deterministic, easy to test, and safe to cache.
- purpose limitation Day 138
- The principle that data collected for a specified purpose should not be further processed in a way incompatible with that purpose. Set out as a research ethics principle in the Belmont Report in 1979 and given an enforcement mechanism in the GDPR, which became applicable on 25 May 2018. The practical form is the datasheet's purpose field: a dataset built for national estimates is not thereby a dataset for small-area estimates.
- push Day 32
- The command that uploads your local commits to a remote so other copies of the repository can receive them.
- py.typed Day 75
- A marker file a third-party package includes, per PEP 561, to declare that its own inline annotations are complete enough to be used by type checkers. Its presence is the difference between a dependency you get checking for and one that arrives as `Any`.
- pydantic Day 69
- A free, open-source library that reads the same annotated declarations as a dataclass but validates and coerces values against them at runtime, raising when input does not match. In one line: dataclasses plus the clerk built in — which is why it underpins most structured-output and tool-calling interfaces.
- pydantic model Day 82
- A class deriving from `BaseModel` whose annotations are compiled into a validator at import time and executed against real data at runtime. It looks like a dataclass and behaves completely differently: a dataclass performs no checking at all, while constructing a pydantic model either produces a checked object or raises.
- Pydantic Schema Day 194
- A strongly typed Python data contract defining validation rules, boundaries, and types for API request and response bodies.
- pyenv Day 43
- A tool that installs and switches between multiple versions of Python on one machine; it manages Python versions and pairs with venv, which manages packages.
- pyjanitor Day 125
- A pandas extension library offering a verb-style, chainable cleaning API (.clean_names(), .remove_empty(), and similar methods) built on top of the same pandas primitives this lesson covers directly, aimed at making a cleaning pipeline read as a readable sequence of named steps.
- PyPI Day 43
- The Python Package Index, the public online repository of open-source Python libraries that pip downloads from by default.
- pyplot state machine Day 128
- The plt.plot / plt.xlabel / plt.title style of calling matplotlib, where every function operates on whichever Figure and Axes are currently "current" (plt.gcf() and plt.gca()) rather than on an object you named yourself. Convenient for a single quick plot in a notebook; the source of the two-APIs bug the moment a drawing routine gets called more than once.
- PyTorch Tensor Day 202
- A multi-dimensional array with hardware acceleration support (CUDA/MPS) and automatic differentiation tracking via Autograd.
- Q-learning Day 142
- A tabular reinforcement algorithm that stores an estimated value for every state-action pair and updates each toward the reward plus the discounted best value of where it landed. That bootstrap is the mechanism by which a terminal reward walks backwards through a world.
- Quadratic-fit-to-residuals diagnostic Day 148
- Fitting a quadratic curve to a set of residuals (not to the original data) and reading how much of the residuals' own variance it explains. Near zero on genuinely linear data (0.0002, measured on the real BMI model) and substantial where curvature was missed (0.3558, measured on deliberately curved data).
- Quality gate Day 77
- A single, reproducible command that runs an ordered set of automated checks over a change and returns one exit code meaning "safe to merge" or "not safe to merge". Three properties make a set of checks into a gate: it is one command, it returns one exit code, and it runs identically everywhere. Everything else — which checks, how strict — is negotiable.
- Quality Gate Day 190
- A mandatory statistical or operational condition that a candidate model must pass before being promoted to live production traffic.
- quantifier Day 38
- A symbol that says how many times the preceding item may repeat: * (zero or more), + (one or more), ? (zero or one), and {n,m} (between n and m times).
- Quantile regression Day 149
- Regression that minimises a loss asymmetric around one target quantile. At quantile 0.5 it minimises absolute error and estimates the conditional median; scikit-learn's `QuantileRegressor(quantile=0.5, alpha=0.0)` is what this lesson used for that case.
- Quantitative Analysis Day 182
- Disaggregated metric evaluation across demographic, environmental, and temporal slices.
- quantization Day 4
- Reducing the bits used per number — for example mapping float32 model weights onto 256 int8 levels plus a scale factor — shrinking memory and data movement at a small cost in precision.
- quantization Day 46
- Storing numbers with fewer bits (for example a model's parameters in 8 bits instead of 32) to save memory and bandwidth, at the cost of coarser precision.
- Quarantine Day 94
- Writing rejected records somewhere durable rather than discarding them, so the source can be repaired and the batch re-run. The counterpart of the reject report: the report says what was wrong, the quarantine holds what was wrong with it. Both raise a disclosure question, because a rejected record's contents are exactly the data you were not able to vet.
- Quarto Day 139
- A publishing system, successor to R Markdown, that renders notebooks and plain-text documents with embedded code into reports, books, slides and websites across multiple languages. Free and open source; described from documentation only in this lesson, not run.
- quasi-identifier Day 138
- A field that is not an identifier on its own but combines with others to single someone out: birth year, postcode, sex, occupation, employer. In this lesson's 5,000-row table with no names at all, 2,723 rows were uniquely determined by exactly three of them.
- query parameter Day 28
- A name=value pair carried in the URL after a ?, joined by &, that specifies the details of your request (for example latitude=52.52).
- query parameter Day 82
- A name and value after the `?` in a URL. In FastAPI, any parameter that is not part of the path and is not a model becomes one; a default makes it optional and its absence means the default is used. Constraints attach through `Annotated[int, Query(ge=1, le=100)]`, so the type stays readable to a static checker and the metadata sits beside it.
- Query plan Day 89
- The engine's chosen strategy for answering a statement, printed by EXPLAIN QUERY PLAN. Read the first word of each step: SCAN means something is being walked end to end, SEARCH means a descent to the matching rows. SCAN naming an index is still a scan — of the index rather than the table — and misreading that line is the most common mistake in the whole topic.
- Query planner Day 85
- The part of the engine that turns a parsed statement into a strategy — which index to use, which order to join, whether to sort with a temporary structure. EXPLAIN QUERY PLAN prints the choice it made. Its output is a description for humans, not an interface, and it may legitimately change between versions.
- Query planner Day 87
- The part of the database that decides how to answer a query — which join algorithm to use, which table to read first, which index to use. EXPLAIN QUERY PLAN shows what it chose: SCAN means read every row, SEARCH means jump to matching rows through an index, and two bare SCANs with nothing between them is a cartesian product you can see before you run it.
- Query planner Day 89
- The part of the engine that decides how to answer a declarative statement: which index to use, in which order to test conditions, whether to sort. Cost-based planning was established by Patricia Selinger and colleagues at IBM in 1979 for System R. The planner may choose differently tomorrow for the identical query, and returning the same rows regardless is the promise that makes that acceptable.
- Query string Day 78
- The part of a URL after the question mark, carrying parameters as name=value pairs separated by ampersands. Because those characters are delimiters, any that appear inside a value must be percent-encoded — which is why you pass params= and let the library encode, rather than building the string with an f-string and silently changing what you asked for.
- QUIC Day 17
- A modern transport protocol (RFC 9000, 2021) that provides TCP-like reliability on top of UDP with fewer setup round-trips, and is the foundation of HTTP/3.
- quoting Day 12
- Wrapping a value in double quotes, as in `"$file"`, to stop the shell from word-splitting it at spaces and expanding glob characters like `*` — the single most important habit for correct scripts.
- quoting Day 65
- Wrapping a field in double quotes so that characters which would otherwise be structural — a delimiter, a newline — are treated as data. RFC 4180 requires it for any field containing a comma, a quote, or a line break.
- R-squared Day 148
- The proportion of the target's variance a fitted line explains, from 0 to 1. Measured at 0.3439 for BMI predicting disease progression, and at a respectable-looking 0.852 on data with real, substantial curvature the line was the wrong shape to capture -- the standing warning of this lesson.
- R-squared Day 152
- One minus the ratio of a model's sum of squared errors to a constant-mean predictor's sum of squared errors. Not bounded below by zero: a deliberately bad predictor measured here scored -4.7009. Dimensionless, unlike RMSE and MAE.
- R2 monotonicity Day 150
- The fact that R2 on the training data can never decrease when a predictor is added, because ordinary least squares always has the option of setting the new coefficient to zero. Measured here climbing from 0.5177 to 0.5325 as ten columns of pure noise were added.
- race condition Day 7
- A bug in which the result depends on the timing of threads touching shared data — for example two threads both incrementing a counter and silently losing one update.
- race condition Day 66
- A bug caused by time passing between two operations that were assumed to be simultaneous. It is the concrete argument against exists-then-open: the file can be deleted or made unreadable in the gap, so the handler is required regardless.
- Race condition Day 96
- A bug whose outcome depends on the relative timing of concurrent operations. The classic instance is a lost update: two threads read a counter, both add one, one write overwrites the other. Its defining and dangerous property is that its VISIBILITY is a timing matter rather than a correctness one — this lesson unprotected counter lost nothing in 20 trials at the interpreter default switch interval and roughly 70% of its increments at a shorter one, with not one character of the code changed. You cannot test your way to confidence about one.
- Radian Day 102
- An angle measured as the distance walked around the rim of a circle of radius 1. The whole circumference is 2 pi, so a full turn is 2 pi radians, a half turn is pi and a quarter turn is pi over 2. Every trigonometric function in Python takes radians; math.radians converts from degrees.
- Radius versus area encoding Day 132
- The error of setting a circle's radius from a value when a reader decodes its area. Because area goes as the square of the radius, a data ratio of 4 draws an area ratio of 16 -- so the shown area ratio is the square of the data ratio, which makes the lie factor equal the data ratio itself. The distortion therefore grows with the real difference. matplotlib's scatter takes s as marker area in points squared, so the correct encoding is the one that appears to do less.
- ragged row Day 65
- A record supplying fewer fields than the header declares. It is valid CSV, so nothing raises; the missing values arrive as None and flow onward into your arithmetic unless you check for them.
- raise Day 66
- The statement that starts an exception on its journey. A bare raise inside a handler re-raises the exception currently being handled, with its traceback completely intact.
- RAM Day 1
- Random-access memory, the computer's fast temporary workspace that holds running programs and their data and is emptied when power is cut.
- random Day 60
- The standard-library module for pseudo-random choices: random.choice, random.shuffle, and random.sample draw from data, and random.seed(n) fixes the sequence so a "random" result becomes reproducible across runs and machines.
- Random Feature Subspace Day 163
- The random selection of a subset of features (typically sqrt(D)) considered at each candidate split in a tree to reduce inter-tree correlation.
- Random Forest Day 163
- An ensemble learning method that constructs a multitude of decorrelated decision trees using bootstrap aggregation and random feature subspace selection.
- Random Oversampling Day 160
- A data-level technique that balances class distribution by randomly duplicating instances from the minority class.
- Random Search Day 166
- A hyperparameter optimization method that samples parameter configurations randomly from specified statistical distributions, providing superior coverage of continuous spaces.
- Random Undersampling Day 160
- A data-level technique that balances class distribution by randomly discarding instances from the majority class.
- Random variable Day 114
- A function that maps every outcome in a sample space to a real number. "Two dice sum to 7" is not itself a random variable; the function Y(outcome) = outcome[0] + outcome[1] is. The randomness lives in which outcome occurs; the variable is the fixed, deterministic rule that turns whichever outcome happened into a number.
- random_state Day 146
- A parameter controlling reproducibility for estimators with internal randomness. Measured: a fixed integer gives byte-identical predictions across five independent fits; random_state=None draws fresh OS entropy every call and produced 5 of 5 distinct prediction vectors in this lesson's measurement.
- range Day 51
- A built-in that lazily produces a sequence of whole numbers — range(stop) gives 0 to stop-1 — used to repeat a fixed number of times or to generate numeric sequences without building a list in memory.
- RangeIndex Day 120
- The default index pandas assigns when nothing else is specified: the integers 0, 1, 2, ... in order. It offers no protection against index-alignment surprises, because it is positional by construction rather than meaningfully labelled.
- Rank Day 102
- How many dimensions survive the transformation. Feed the whole plane in: if the output still fills the plane the rank is 2, if it is squashed onto a line the rank is 1, if everything lands on the origin the rank is 0. For a 2 by 2 matrix it reads off the columns — two columns pointing in genuinely different directions give rank 2, one column being a multiple of the other gives rank 1. numpy.linalg.matrix_rank computes it, and it is the more useful word than "determinant" once matrices stop being square.
- Rank Averaging Day 168
- An ensembling strategy where predicted probabilities are converted to fractional ranks before averaging, neutralizing calibration disparities for rank-based metrics (ROC-AUC).
- Ranking Day 103
- The ordered list a search returns, best first. Two facts about it carry through the day: on normalised vectors, ranking by cosine and ranking by Euclidean distance produce the identical order, so the choice is about speed rather than meaning; and ties must be broken by something deterministic, or the same query returns different orders on different runs and a test suite starts failing at random.
- raster image Day 5
- An image stored as a grid of pixels (for example PNG or JPEG), as opposed to a vector image.
- raster image Day 128
- An image format (PNG, JPEG) stored as a fixed grid of pixel colour values. Text and lines in a raster image are rendered into pixels at save time and cannot be searched, selected, or resized without quality loss -- the string that produced a label does not appear anywhere in the file's bytes.
- Raster image Day 105
- A picture stored as a rectangular grid of individual samples, one per position, rather than as a description of shapes. Every image in this lesson is a raster image, which is why it is a matrix. The alternative is a vector image, which stores instructions — a line from here to there, a circle of this radius — and is resolution-independent because it is redrawn rather than resampled. Transforming a vector image is exact and lossless; transforming a raster image always involves the resampling question this day is about.
- rate limit Day 22
- A cap a service places on how many requests a caller may make per period; exceeding it returns HTTP 429 so that no single caller can overwhelm the shared service.
- rate limit Day 27
- A cap a server sets on how many requests a client may make in a window of time, protecting the shared service from overload and enforcing fair (or metered) access.
- rate limit Day 28
- A cap a service places on how many requests you may send in a period; a polite client stays within it, spacing requests and honoring any Retry-After header.
- rate limit backoff Day 134
- A client's response to receiving a 429 status: wait, using a growing delay, and retry up to a bounded number of attempts before giving up loudly. A client that retries with no upper bound is, from the server's perspective, indistinguishable from the abusive traffic a rate limit exists to stop.
- Rate limiting Day 78
- A server restricting how often a client may ask. Signalled with status 429 and usually a Retry-After header giving the delay in seconds or as a date. Honouring it is both polite and the fastest route back to being served; ignoring it typically escalates to a longer block. Model APIs rate-limit tightly, so this is the status code you will meet most in Course 07.
- Rate limiting Day 79
- Deliberately restricting how fast your program makes requests, so that a shared server keeps working for everybody else using it. In practice: a delay between requests, one request at a time per host, and backing off when the server answers 429 Too Many Requests or sends a Retry-After header.
- Rate of change Day 108
- How much one quantity changes for a given change in another: the difference in the output divided by the difference in the input. Metres per second, dollars per unit, loss per unit of weight. Everything in this lesson is one idea applied at different interval widths, and this is the idea. Note that a rate is always attached to an interval or to a point; a rate with neither attached is not a claim about anything.
- raw string Day 45
- A string literal prefixed with r in which backslashes are treated literally rather than as escapes, useful for file paths and regular-expression patterns.
- raw-then-transform Day 135
- The discipline of persisting every raw API response (as JSONL or Parquet) before running any parsing or flattening logic on it. A bug found later in the transformation step can be fixed and re-run against the stored raw copy, touching the network zero additional times, rather than requiring the API to be re-fetched.
- RBF Kernel (Radial Basis Function) Day 169
- A stationary kernel function K(x, z) = exp(-gamma * ||x - z||^2) corresponding to an infinite-dimensional feature mapping.
- rcParams Day 128
- matplotlib's global dictionary of default settings -- figure size, font size, line width, colour cycle, and hundreds more -- read from matplotlib.rcParams or set in bulk from a named style sheet with plt.style.use(). Setting defaults once through rcParams, rather than repeating the same keyword argument on every plot call across a report, is what keeps a multi-chart document visually consistent.
- rcParams (global theme state) Day 129
- matplotlib's global dictionary of default plotting settings (colors, grid visibility, font family, and more). sns.set_theme() (and the lower-level set_style()/set_context()) work by mutating this dictionary directly, so the change persists for every plot drawn afterward in the same process -- seaborn or plain matplotlib -- until it is explicitly reset.
- read_sql Day 121
- A pandas function that runs a SQL query against a database connection (here, a sqlite3 connection) and returns the result as a DataFrame. The filtering happens inside the database, not in pandas, so only the matching rows are ever loaded.
- read-eval-print loop (REPL) Day 8
- The repeating cycle a shell runs for every command: read the line you type, evaluate it, print the result, and loop back to the prompt to wait for the next line.
- readability Day 61
- The quality of code that lets a human understand what it does and why with the least effort — driven by clear names, small functions, consistent layout, and explanations of intent. Code is read far more often than it is written, so readability is a first-class goal, not a finishing touch.
- Readiness Probe Day 194
- A health check endpoint verifying that a microservice has finished initial startup and model loading before receiving traffic.
- readiness report Day 42
- The output of the toolkit-check lab: a summary of which core Course 1 tools and cross-section skills are present on your machine, mapping each to the day that taught it.
- Realised coverage Day 154
- The fraction of test targets that actually fall inside a prediction interval, checked against the interval's nominal (stated) rate. Measured here at 0.9459 against a 0.95 nominal rate on 111 test rows.
- rebase Day 31
- Replaying a branch's commits on top of another branch as new commits, producing a straight linear history with no merge commit; it rewrites the commits, so it must never be used on shared history.
- Recall (Sensitivity / True Positive Rate) Day 159
- The proportion of actual positive instances that were successfully identified: Recall = TP / (TP + FN).
- Receiver Operating Characteristic (ROC) Day 159
- A graphical plot illustrating binary classifier diagnostic ability as its discrimination threshold tau is varied, plotting TPR against FPR.
- Receptive Field Filter Day 203
- Visualizing a neuron 784 weights as a 28x28 spatial image to observe the learned visual pattern it detects.
- Recommender System Day 188
- An algorithmic system that predicts user preference ratings or ranks items to deliver personalized suggestions.
- reconciliation invariant Day 123
- The check that the sum of a groupby aggregation's per-group results equals the corresponding aggregation over the whole, ungrouped column -- true under dropna=False, false under dropna=True whenever any key is missing, in which case the gap equals exactly the missing-key rows' own total.
- Reconstruction Error Day 185
- The mean squared Euclidean distance between the original high-dimensional data X and its low-rank reconstruction X_hat.
- record (dict) Day 56
- One item in a data-driven tool's collection, modelled as a Python dictionary of named fields — for example {"id": 1, "name": "Ada", "email": "ada@example.com"} — with the whole collection held as a list of such dictionaries.
- record terminator Day 64
- The byte that marks the end of one record — a newline, in a line-oriented store. It is what makes a torn write recoverable: a record is only complete once its terminator is on disk, so a reader that stops at the first line without one can never half-parse a truncated record.
- record_path Day 135
- The json_normalize argument that names which nested list becomes the new row grain. Passing record_path="orders" tells json_normalize to produce one row per order rather than one row per customer. A customer whose orders list is empty contributes zero rows when record_path targets that list.
- Rectified Linear Unit (ReLU) Day 198
- An activation function defined as f(z) = max(0, z), possessing a constant unit derivative for positive inputs and zero upper saturation.
- recursion Day 62
- A problem-solving technique in which a function calls itself to solve a smaller version of the same problem; built from a base case that stops the process and a recursive case that shrinks the problem and combines results. Ideal for self-similar, nested data.
- recursion limit Day 62
- Python's configurable cap on how deep the call stack may go (about 1000 frames by default), readable with sys.getrecursionlimit() and adjustable with sys.setrecursionlimit(). It exists so runaway or maliciously deep recursion raises a catchable error instead of exhausting all memory.
- recursive case Day 62
- The part of a recursive function that reduces the problem to a smaller instance of the same problem, calls itself on that smaller instance, and combines the returned result with the current level (for example n * factorial(n - 1)). The input must move strictly closer to the base case each time.
- Recursive CTE Day 91
- A common table expression that refers to itself, written WITH RECURSIVE. An anchor query selects the starting rows; the recursive part joins the table back to the CTE to find the children of everything found so far; the process stops when a pass adds no rows. It answers hierarchical questions no fixed number of joins can, because the number of joins you would need is the depth of the tree and you do not know the depth of the tree. Carry a depth column by hand, and guard against cycles.
- Recursive Feature Elimination (RFE) Day 172
- A greedy backward selection algorithm that iteratively fits a model and prunes the least important feature until the target subset size is reached.
- Red-green-refactor Day 73
- The three-step loop of test-driven development: write one small failing test and watch it fail for the reason you predicted (red), write the least code that makes it pass (green), then improve the structure without changing behaviour and confirm the same tests still pass (refactor). Then repeat with the next behaviour.
- Redacting filter Day 97
- A filter that replaces known secret VALUES wherever they appear — in the message, in the arguments, in a field passed through extra=, in a value nested inside a dict. Redaction by value rather than by key name, because key-name redaction misses log.info("calling %s", url_with_token), which is how secrets actually escape. It belongs on each HANDLER, and it is a seatbelt rather than permission to log the secret.
- redirect Day 21
- A response (status 301 or 302) that points the client to a different URL via a location header rather than returning the content directly; `curl -L` follows it to the final destination.
- redirection Day 10
- Connecting a program's stream to a file: `>` overwrites a file with standard output, `>>` appends to it, `<` supplies standard input from a file, and `2>` sends standard error to a file.
- redistribution licence gate Day 134
- A check of what a stated data licence (CC0, CC-BY, ODbL, all rights reserved) actually permits for a specific intended use, returning a reason alongside an allowed/not-allowed verdict, because "you may analyse this" and "you may republish this" are different permissions a single boolean cannot express.
- ReduceLROnPlateau Day 207
- An adaptive scheduler that reduces learning rate when a monitored validation metric stops improving for a given patience.
- Redundant encoding Day 132
- Carrying a distinction on more than one visual channel at once -- colour plus marker shape, colour plus line style, colour plus a direct label -- so that a reader who cannot decode one channel still receives the information. The practical test is whether the chart still works printed in black and white.
- refactoring Day 61
- Changing the internal structure of code to make it clearer or simpler without changing its external behaviour. Done well, it proceeds in small steps, each verified by tests, so that improved readability never comes at the cost of a hidden bug.
- Refactoring Day 73
- Changing the structure of code without changing its behaviour — renaming, extracting a helper, removing duplication. The definition is operational, not aspirational: if the passing count or any output moves, it was not a refactor but an untested edit with a flattering name.
- Referential integrity Day 87
- The property that every foreign-key value actually points at a row that exists, so the database contains no references to nothing. It is an integrity control rather than a security control: it stops a loan pointing at a member who does not exist, and stops nothing else. PRAGMA foreign_key_check reports where it has already been violated.
- Reflection Day 102
- A mirroring of the plane in some line through the origin, with matrix [[1, 0], [0, -1]] for the x axis. Derived by noticing that a point ON the mirror line cannot move, so e1 stays put, while e2 goes from one step up to one step down. Its determinant is always -1: the size is preserved and the orientation is reversed, so a shape listed anticlockwise comes out listed clockwise.
- reflog Day 34
- Short for "reference log": a local, private record of every position HEAD has occupied, including commits that no branch points to anymore, making it Git's primary recovery mechanism.
- reflow Day 20
- Another name for layout; also used for the re-computation of geometry the browser must do when something changes an element's size or position after the page has loaded.
- refresh token Day 25
- A longer-lived OAuth credential used only to obtain new access tokens when they expire, so the user need not log in again; the more sensitive of the two tokens.
- regex engine Day 38
- The program that takes a pattern and some text and reports whether, and where, the text matches — scanning left to right and backtracking when a choice fails.
- register Day 1
- One of a small set of ultra-fast storage slots inside the CPU that hold the values being worked on at this instant.
- register Day 2
- One of a small, fixed set of ultra-fast storage slots inside the CPU that hold the values being worked on at this instant — the fastest memory in the machine.
- Regression Day 71
- Code that used to work and now does not, broken by a change made somewhere else. The expensive part is never the fix — it is the search. A regression test is a test written to reproduce a bug before it is fixed, so that the bug can never return unnoticed.
- Regression suite Day 73
- The accumulated body of tests re-run on every change, so that behaviour which used to work and no longer does is reported immediately rather than discovered later. In the loop it is the safety net the refactor step leans on, and it grows by exactly one test per cycle.
- RegressorMixin Day 153
- A scikit-learn mixin supplying a default score() method (R-squared) for any estimator that implements predict(). Paired with BaseEstimator on OLSRegressor so it behaves as a complete regressor rather than a bare fit/predict object.
- regular expression Day 10
- A compact notation for describing text patterns, where symbols such as ^ (start of line), $ (end of line), . (any character), and [0-9] (any digit) let a single expression match many strings.
- regular expression Day 38
- A compact string of characters that describes a pattern for matching text — a whole set of strings that share a shape, rather than one literal string.
- Regularisation Day 145
- Any penalty that discourages a fit from using the capacity it has. Buys variance reduction with bias, and the currency it pays in is training error: a ridge penalty of 1.0 improved test error here by a factor of 39,588 while raising training error from 1.0321 to 2.7461.
- Regularization Day 151
- A term added to a model's training objective that penalizes some measure of complexity -- here, the size of the coefficients -- pushing the fit toward simpler solutions even when a more complex one fits the training data slightly better.
- reindex Day 131
- A pandas operation that conforms a series or frame to a new, explicitly given index, introducing NaN for any position present in the new index but absent from the original. Reindexing a gapped time series to its full expected date range is what converts a silently missing row into an explicit, visible NaN.
- Reinforcement learning Day 142
- The setting in which a learner chooses actions, receives evaluative rewards, and -- decisively -- influences what data it will see next. That last property is what makes a problem reinforcement learning even when labels are abundant, because the resulting log records only what was chosen.
- Relation Day 85
- The formal name for a table: a set of tuples, each drawn from the same named columns. Two consequences follow from the word "set". A relation has no duplicate rows if a key is enforced, and it has no order — a table has no first row until a query supplies one with ORDER BY. "Relational" refers to this mathematical relation, not to tables relating to each other.
- relational database Day 39
- A database that stores data in tables of rows and typed columns under a fixed schema, queried with SQL and protected by ACID transactions; examples include PostgreSQL, MySQL, and SQLite.
- Relational model Day 85
- The way of organising data that Edgar F. Codd published in Communications of the ACM in June 1970: data held as relations rather than reached by following pointers, and queries expressed as operations on sets. Its central promise is data independence — you can change how data is stored without rewriting the programs that use it.
- relative import Day 59
- An import that uses a leading dot to name a module relative to the current package, such as `from .tokens import tokenize` ("the tokens module in this same package"). Used between siblings inside a package; it works only when the file is imported as part of a package.
- relative luminance Day 127
- The WCAG measure of a colour's perceived lightness, computed from linearised sRGB as 0.2126 R + 0.7152 G + 0.0722 B. It is the part of a colour that survives a greyscale photocopy, which is why a palette carrying order in luminance carries order robustly.
- Relative luminance Day 132
- The brightness of a colour as defined by WCAG: each sRGB channel is linearised, then weighted 0.2126, 0.7152 and 0.0722 and summed, giving a value from 0.0 for black to 1.0 for white. It is the channel that survives every form of colour-vision deficiency, every greyscale printer and every washed-out projector. It is one component of whether two colours can be distinguished, not the whole of it -- a full simulation needs a colour-appearance model.
- relative path Day 9
- A path that starts from the current working directory rather than from the root, so its meaning depends on where you currently are.
- relative path Day 64
- A path interpreted from the process's current working directory, such as `data/train.txt`. It means different things depending on where the program was launched, which is a leading cause of "where did my output go?".
- Relative Residual Feature Day 171
- The difference or ratio between an individual observation and its group aggregate baseline (e.g. x - Mean(x | group)).
- ReLU Day 108
- max(x, 0): the most widely used activation function in deep learning, met on Day 102 as a transformation. Its graph is flat to the left of zero and a 45-degree line to the right, so it has a corner at exactly zero and no derivative there — the one-sided slopes are 0 and 1. A framework must choose one of those two by convention to train through it. The central difference chooses neither: it returns their average, 0.5, which is why a numerical derivative disagrees with every framework at exactly that point.
- remote Day 32
- A named reference to another copy of a Git repository — on a server, a peer machine, or a local folder — that your repository can synchronise with.
- render tree Day 20
- The tree the browser builds by combining the DOM with the CSSOM, containing only the visible elements together with their computed styles — the list of things that will actually be drawn.
- render-blocking resource Day 20
- A file, typically CSS or an ordinary script, that the browser must finish processing before it can paint, delaying when the user first sees content.
- Repeated K-Fold Day 167
- Executing K-Fold cross-validation n times with different random partitions and averaging all scores to reduce the variance of the performance estimate.
- REPL Day 43
- The read-eval-print loop: Python's interactive prompt (>>>), where you type one line, it evaluates and prints the result, then waits for the next line.
- replace Day 69
- A `dataclasses` function returning a copy of an instance with some fields changed. It works by calling the class's `__init__`, so `__post_init__` runs and the new values are revalidated — which makes it the correct way to "modify" a frozen instance.
- Replication Day 92
- Keeping copies of the same data on several machines. It increases read capacity and survives the loss of a machine, and it is what creates the CAP choice, because two copies can disagree only if there are two copies. A single-machine database has no partitions and therefore no CAP trade-off at all.
- repository Day 13
- A curated online collection of packages, plus an index of their versions and dependencies, that a package manager knows how to reach and trust.
- repository Day 29
- The store of a project's complete history — in Git, a hidden database (often a `.git` folder) that lives alongside the files and holds every commit.
- repository Day 30
- A project folder that Git is tracking, together with the hidden .git directory that stores its complete history of committed snapshots.
- Repository Day 70
- The one object that knows how a model is stored, with save and load as its public surface plus private translators between domain shape and file shape. Swapping CSV for JSON or SQLite means writing one new repository class.
- Repository Day 90
- One class that owns every SQL statement about one kind of thing, taking a connection rather than a path so that a test can hand it a database in a temporary directory. Rows go in as bound values and come out as domain objects through a single mapping function, and storage errors are translated into domain errors at its edge — so nothing above it needs to import sqlite3 to find out that a title was taken.
- Repository pattern Day 91
- A class that owns the database connection and exposes one method per question, so that no other code holds a connection or writes SQL. Beyond tidiness it is a security property of the structure: the formatting code physically cannot build a query out of string concatenation, because it has no connection in scope to do it with.
- representation Day 23
- A serialized snapshot of a resource's state that is transferred between client and server, most commonly as JSON; distinct from the resource itself.
- Representation Learning Day 196
- A branch of machine learning where algorithms automatically discover optimal feature representations from raw input tensors.
- representation ratio Day 138
- A group's share of the sample divided by its share of the reference population. A ratio of 1.0 means the group appears exactly as often as it should; 0.104 means it appears at roughly a tenth of that rate. Reported per group and by name, which is what makes it more useful than a single distribution distance that can read as reassuring while one group is nearly absent.
- Representational Capacity Day 175
- The space of functional relationships that a machine learning model can express given a specific feature representation.
- reproducibility Day 41
- The property that the same inputs and environment produce the same output every time and everywhere, so an automated result can be trusted.
- reproducibility Day 126
- The property that a pipeline, run again later -- possibly by someone else, on a different machine -- produces the documented result. Requires idempotence, determinism, checkpointing and a manifest together; no single one of them is sufficient on its own.
- Reproducibility Day 83
- The property that a result can be rebuilt from a recorded description — the code at one commit, the exact dependency versions, the interpreter, the data. It is a packaging problem before it is a modelling problem: a machine-learning result nobody can rebuild because nobody recorded what produced it is an anecdote with a number attached. The rule that a published version can never be reused is what makes every lock file in the ecosystem mean anything.
- request Day 18
- The message a client sends to a server, made of a request line (method, path, version), headers, a blank line, and an optional body.
- request Day 22
- What a client sends to an API: a method (verb), a path/endpoint, optional query parameters, headers, and an optional body.
- Request Day 78
- The message a client sends: a request line naming the method, path and version; then headers; then a blank line; then a body if the method has one. The blank line is not decoration — it is the delimiter that tells the server the headers have finished.
- request body Day 82
- The payload sent with a POST, PUT or PATCH, usually JSON. Declared as a pydantic model, it is parsed and validated before your code runs, so the handler receives a real typed object rather than a dictionary of unknowns.
- request changes Day 33
- A reviewer's verdict that formally blocks the merge until the author addresses specific feedback; a normal step in iteration, not a rejection.
- request pipeline Day 28
- The six repeatable stages of any API client: read the docs, build the request, send it, parse the JSON, handle errors, and present the result.
- RequestException Day 78
- The base class of every exception requests raises for a failure at the transport layer — ConnectionError, Timeout with ConnectTimeout and ReadTimeout beneath it, SSLError, TooManyRedirects. Catching this one class catches the whole family. It is raised when NO response arrived, which is what distinguishes it from a response carrying a 500.
- requirements.txt Day 43
- A plain-text file listing a project's packages and their exact versions, used with pip install -r requirements.txt to recreate the same environment elsewhere.
- requires_grad Day 202
- A boolean flag on PyTorch tensors instructing Autograd to record operations for backward gradient calculation.
- requires_grad Day 204
- A boolean tensor flag instructing autograd whether to record operations on this tensor in the computational graph.
- resample Day 131
- A pandas method that groups a DatetimeIndex-ed series or frame into fixed time buckets (for example one bucket per calendar month) and then applies an aggregation to each bucket, extending Day 123's groupby from a fixed set of category labels to buckets defined purely by elapsed time.
- Resampling Day 105
- The act of reading an image at positions that are not its own pixel positions, which is what applying any transformation other than an exact quarter turn or flip involves. Every resampling pass quantises the result to whole pixel values and discards the sub-pixel remainder, and the loss is not recoverable by a later pass. Measured here: twelve separate 30 degree rotations lose 16 of 81 pixels, while the same full turn composed into one matrix and resampled once loses exactly zero. Compose the matrices; resample once.
- Research log Day 136
- A dated record of every question asked of a dataset, what was looked at to answer it, and what was found -- including outcomes of "nothing found." The log's own length is the true comparison count, which is what a multiple-comparisons correction needs to be honest.
- Research log Day 140
- An ordered record of every look taken during exploration, including the ones that found nothing, each with a timestamp, the split it used and its outcome. Its length is the true comparison count, and its ordering is the only evidence that a confirmation set was opened after a hypothesis rather than before.
- Researcher degrees of freedom Day 136
- The many small, often undeclared choices available during analysis -- which subset, which outcome, which cutoff, which transformation -- each of which is effectively a comparison, whether or not a formal test was run for it. Named by Simmons, Nelson and Simonsohn (2011).
- reset Day 34
- A command that moves the current branch pointer to a specified commit, optionally also updating the index and working tree depending on its mode (soft, mixed, or hard).
- Reshape Day 100
- Rewriting how a block of numbers is read as a grid, without changing the numbers or their order. Any shape whose dimensions multiply to the same total is allowed, and -1 means "work out this one". A reshape is usually a view, so writing through the result changes the original. The entries come out in row-major order — the whole of row 0, then row 1 — which is what NumPy calls C order and uses by default.
- Residual Day 148
- The leftover error at one row -- actual target value minus predicted value. Residuals are what a residual plot examines, and their pattern reveals what a single summary score like R-squared cannot.
- Residual Day 154
- The true target value minus the model's prediction, for one row. This lesson's centrepiece: reading the full set of residuals for patterns, not summarising them into a single RMSE and stopping there.
- Residual sum Day 148
- The total of all residuals across a dataset. Exactly zero, up to floating point, for any least-squares line fitted with an intercept -- measured at -1.67e-11 on 442 rows here.
- resolution Day 5
- The number of pixels in an image, usually given as width by height.
- resolver Day 16
- A recursive resolver is a server that performs the full DNS lookup on your behalf — walking root, TLD, and authoritative servers — and returns and caches the final answer.
- resource Day 23
- Any thing a service exposes and names, such as a user, order, or post; the noun that a REST URL addresses.
- resource Day 82
- A thing your API is about, addressed by a path: a bookmark, a model, a conversation. Resources are nouns and do not change; the HTTP method is the verb applied to them. `/bookmarks` is the collection and `/bookmarks/bm-0001` is one member of it.
- response Day 18
- The message a server sends back, made of a status line (version, status code, reason), headers, a blank line, and a body.
- response Day 22
- What the server sends back: a status code indicating the outcome, headers describing the answer, and a body carrying the data (usually JSON).
- Response Day 78
- The message a server sends back: a status line with the version, the three-digit status code and a human-readable reason phrase; then headers; then a blank line; then the body. Never parse the reason phrase — servers may write anything there. Parse the code.
- Response cache Day 79
- Storing fetched page bodies on your own disk, keyed by URL, so that re-running your parser makes no new requests. Primarily an ethical control rather than a performance one: it is what makes your twentieth parser fix cost the source nothing. The one response you never cache is robots.txt, because permission is a current intention rather than a fact.
- response model Day 82
- The model declared in `response_model=`, which filters whatever the handler returned down to those fields before serialization. It gives you a documented contract and — more importantly — the filter that stops an internal field leaving the process. One line, easy to omit, which is why you assert on the absence of the field rather than trusting the line to still be there.
- REST Day 22
- A widely used architectural style for web APIs, described by Roy Fielding in 2000, that maps operations onto HTTP methods and resource URLs (covered in depth on Day 23).
- REST Day 23
- Representational State Transfer — an architectural style for networked software that models a service as resources at addresses, acted on by a fixed set of standard verbs, with a stateless client-server exchange.
- REST Day 82
- An architectural style described by Roy Fielding in chapter 5 of his 2000 doctoral dissertation at the University of California, Irvine — a set of constraints including a uniform interface, statelessness between requests, and addressable resources. It is not a standard, has no specification and no compliance test, and what the industry calls a REST API is a loose family of conventions. "Loosely RESTful" is the honest description of almost every real API.
- REST API Day 42
- A style of interface where programs exchange data over HTTP using resources and verbs, most often carrying JSON; how programs talk to each other over the internet (days 22-24).
- Restart and run all Day 139
- The one operation that actually proves a notebook works: discard the current kernel, start a completely new one with an empty namespace, and execute every cell top to bottom in document order. Any claim a notebook makes without having survived this is unverified, however plausible its displayed outputs look.
- restore Day 34
- A command (added in Git 2.23) for undoing changes to files: git restore --staged un-stages a file, while git restore discards a file's uncommitted edits to match the last commit.
- Restrict Day 88
- The opposite foreign key rule, ON DELETE RESTRICT, which refuses to delete a parent that still has children. Correct when the child is evidence the parent is busy — a book that is out on loan. The right response to it is a person thinking, not a retry. A third option, SET NULL, suits a child that survives but loses a detail.
- retry Day 26
- The sender re-attempting a delivery (usually with growing gaps, called backoff) when it does not receive a 2xx acknowledgement, which is why the same event can arrive more than once.
- Retry Day 78
- Asking again after a failure that might not repeat. Worth doing for 429, 500, 502, 503 and 504, and for transport failures where no response arrived. Never worth doing for 400, 401, 403, 404, 409 or 422, because the answer will not change. A retry against a metered API is a second charge, which is a further reason to be strict about which statuses qualify.
- retry with backoff Day 66
- Attempting a failed operation again after a delay that grows with each attempt, capped at a fixed number of tries. Only worth doing for errors a later attempt might survive; retrying a deterministic failure just fails more slowly.
- Retry-After Day 27
- An HTTP header, often sent with a 429 or 503, telling the client exactly how long to wait before retrying — either a number of seconds or an HTTP date.
- Retryable failure Day 98
- A failure that describes a moment rather than a mistake, and might therefore not recur: a 500, a 502, a 503, a 504, a 429, a connection reset, a timeout. Retrying anything else — a 404, a 401, a 400 — spends round trips to learn what the first attempt already told you, and delays every source behind it. The distinction is a policy decision you write down, not something the HTTP library decides for you.
- return code Day 66
- The older error strategy, still used throughout C and the operating system interfaces beneath Python: a function signals failure with a sentinel value such as -1 or NULL. Its failure mode is that nothing forces the caller to look.
- return value Day 49
- The value a function hands back to its caller with the `return` statement; testing a function means calling it and checking that its return value is what you expected.
- return value Day 57
- The value a function hands back to its caller with a return statement; the caller can store, compose, or test it. A function with no explicit return hands back None.
- RETURNING Day 88
- A clause on INSERT, UPDATE and DELETE that hands back columns from the affected rows, added in SQLite 3.35.0. It is how you learn what the database decided — a generated id, a DEFAULT-filled timestamp — without a second SELECT that another connection could race you to.
- Reverse-Mode Automatic Differentiation Day 200
- A technique for computing gradients of a scalar objective with respect to many inputs in a single backward pass through a computational graph.
- Reverse-mode differentiation Day 110
- Applying the chain rule from the output backwards. One forward pass plus one backward pass yields the derivative of a single output with respect to every input at once, no matter how many inputs there are. It is what makes training practical, and it pays for that speed by keeping the forward pass values in memory.
- revert Day 29
- Bringing back the content of an earlier commit — recorded as a new step in the history rather than by erasing the commits in between.
- revert Day 34
- A command that undoes a commit by creating a new commit which applies its exact inverse, preserving history. The safe way to undo commits that have already been shared.
- reviewer Day 33
- A person asked to read a pull request and record a verdict — approve, comment, or request changes — on whether it should be merged.
- RFC 3339 Day 95
- The 2002 internet profile of ISO 8601 by Klyne and Newman, which narrows it to a date, a separator, a time and a mandatory offset to UTC. Z denotes a zero offset. Every RFC 3339 timestamp is valid ISO 8601 and the reverse is not true — 2026-W43-7 is ISO 8601 and is not a timestamp at all. RFC 3339 with a Z is the intersection that every parser reads, and it is what to write.
- RFC 4180 Day 65
- The 2005 memo by Yakov Shafranovich describing what most CSV implementations actually do. It is explicitly informational rather than a binding standard, which is exactly why real files still violate it.
- RFM Framework Day 189
- A marketing analysis framework evaluating customer Recency (last purchase), Frequency (purchase count), and Monetary value (total spend).
- RGB Day 5
- A color model that represents a pixel as red, green, and blue channel values, commonly 0-255 each.
- Ridge regression Day 145
- Least squares with an L2 penalty on the coefficients, published by Hoerl and Kennard in 1970 for exactly this reason. One hyper-parameter, alpha, whose test error has its own U-curve -- too much penalty is underfitting by another route.
- Ridge regression Day 151
- Linear regression with an L2 penalty: the sum of squared residuals plus alpha times the sum of the SQUARED coefficients. Measured here to zero zero of ten coefficients at every alpha tried, from 0.001 to 100.
- RMSE Day 152
- Root mean squared error -- the square root of the average squared residual. In the target's own units. Squares every error before averaging, so one very wrong prediction dominates it: measured here moving 11.39 times under a single outlier while MAE moved only 3.00 times.
- RMSNorm Day 208
- Root Mean Square Normalization, a streamlined variant of LayerNorm that scales by root mean square without subtracting the mean.
- RMSprop Day 206
- An adaptive learning rate algorithm that replaces AdaGrad monotonic sum with an exponentially decaying moving average of squared gradients.
- robots.txt Day 79
- A plain-text file at the root of a host, at the fixed path /robots.txt, in which the operator states which paths automated clients should not fetch, grouped by User-agent. Proposed by Martijn Koster in 1994 and formalised as RFC 9309 in 2022. It is a published preference honoured by clients that choose to, never an access control.
- Robust regression Day 148
- A family of fitting methods, such as scikit-learn's HuberRegressor and RANSACRegressor, designed to resist the influence of high-leverage points and outliers that an ordinary least-squares fit does not resist. Described here from documentation; not run in this lesson's lab.
- Robust regression Day 149
- Any regression method designed to bound the influence of extreme points, typically by using a loss that grows slower than squared for large residuals. Huber and quantile regression are both robust in this sense; ridge and lasso, covered on Day 151, are not -- they change the penalty, not the loss's shape.
- RobustScaler Day 170
- A scaling transformation using the median and Interquartile Range (IQR) that is robust against extreme numerical outliers.
- ROC AUC Day 159
- Area Under the ROC Curve: a threshold-independent metric measuring the probability that a classifier ranks a random positive instance higher than a random negative instance.
- ROC-AUC Day 176
- Area Under the Receiver Operating Characteristic curve measuring the probability that a random positive sample ranks higher than a random negative.
- Rollback Day 88
- Abandoning an open transaction so that none of its changes took effect. In SQLite the mechanism is literal: the original pages were copied into a rollback journal at BEGIN, and ROLLBACK copies them back. The lab verifies the consequence — the database file is byte for byte what it was, not merely equivalent.
- Rollback journal Day 85
- SQLite's default crash-recovery file, written beside the database as name-journal. Before changing a page, the engine copies the ORIGINAL page into the journal, so an interrupted commit can be undone. It is part of the database: copying the database file and leaving the journal behind can lose data.
- Rollback journal Day 88
- The file SQLite writes beside the database holding the ORIGINAL copies of every page a transaction is about to modify. COMMIT deletes it, because there is then nothing left to undo with; ROLLBACK copies its contents back. Undo is not a clever algorithm, it is putting the saved pages back.
- rolling window Day 131
- A computation (commonly a mean) applied to a sliding span of consecutive observations rather than to the whole series at once, smoothing short-term noise while preserving slower movement. pandas' rolling() method supports both trailing (the default) and centred windows.
- Rolling Window Day 192
- A moving window of fixed width w calculating aggregate statistics (mean, std, max) over recent historical time steps.
- Rolling Window Statistic Day 171
- A moving aggregate statistic (mean, standard deviation, max) computed over a sliding temporal window of past observations.
- root CA Day 19
- A self-signed Certificate Authority certificate that anchors the chain of trust; its public key is preloaded in the browser or operating system trust store and kept offline for safety.
- root directory Day 9
- The single directory at the top of the filesystem tree, written as a lone forward slash (/), under which everything else lives.
- rootdir Day 71
- The directory pytest treats as the base of the run, found by walking upward from the paths you named to the first `pytest.ini`, `pyproject.toml`, `tox.ini` or `setup.cfg`. Every path in the report is printed relative to it, and it is printed in the header of every run — the first thing to read when pytest behaves unexpectedly.
- Rotation matrix Day 102
- The matrix [[cos t, -sin t], [sin t, cos t]], which turns the whole plane anticlockwise by t radians about the origin. Derived from the unit circle in two steps: e1 walks around the rim to (cos t, sin t), which is the definition of those two functions, and e2 — already a quarter turn ahead — lands a quarter turn ahead of that, at (-sin t, cos t). Its determinant is cos squared plus sin squared, which is 1 by Pythagoras, so a rotation never changes area and never flips.
- round trip Day 65
- Writing data out and reading it back. A lossless round trip returns exactly what you put in; through JSON, tuples return as lists and non-string dict keys return as strings, so equality can fail even when nothing was lost.
- round-trip Day 121
- Writing data to a file and reading it back, then comparing the result to the original. A round-trip that preserves every dtype and value exactly is lossless; one that does not -- as CSV's is not, for a nullable Int64 column with a missing value -- silently changes the data's type on the way through.
- Round-trip asymmetry Day 94
- The fact that Model.model_validate(instance.model_dump()) is not guaranteed to work, for three ordinary reasons: computed fields are written on the way out but refused on the way in under extra="forbid"; aliases mean the default dump uses field names while validation expects wire names; and a validator that normalises a value means the object is not identical to what arrived. All three are correct behaviours; the bug is assuming they compose.
- round-trip property Day 24
- The contract that parsing a value you just serialized returns a value equal to the original, so no information is lost in the trip out and back.
- round-trip time Day 15
- The time for a signal to travel to the server and back again, abbreviated RTT; the basic unit of network delay.
- rounding Day 46
- Reducing a number to a chosen number of digits; Python's built-in round uses banker's rounding (round half to even), so round(2.5) is 2 and round(3.5) is 4.
- Rounding error Day 108
- The part of a numerical derivative's error that comes from the arithmetic: f(x + h) and f(x − h) are each stored to about 1e-16 relative precision, subtracting two nearly equal numbers destroys the digits they had in common, and dividing by a tiny h magnifies what is left, giving roughly EPSILON·|f(x)| ÷ h. It GROWS as h shrinks, which is the half that surprises people, and it is why a forward difference at h = 1e-300 returns exactly 0.0 with no warning at all.
- router Day 16
- A machine that forwards packets between networks, reading each packet's destination address and sending it to the best next hop from its routing table.
- Row Day 100
- One horizontal line of a matrix, selected by the first index. Under the table reading a row is one item; under the vector reading it is one point in feature-space; under the transformation reading it is the recipe for one entry of the output. In row-major storage a row's entries sit next to each other in memory, which is why reading a row is cheaper than reading a column.
- Row factory Day 90
- A callable taking (cursor, row) that decides what a row looks like in Python. The default is a tuple, addressed by position. sqlite3.Row gives access by column name as well, plus keys(). A three-line dict factory built over cursor.description returns real dicts, which is what you need when a row has to be serialised as JSON.
- ROW_NUMBER and RANK Day 91
- Two ranking window functions. ROW_NUMBER gives 1, 2, 3 with no gaps and breaks ties arbitrarily unless the ORDER BY makes them deterministic. RANK gives tied rows the same number and then skips — 1, 1, 3. Choose by what a tie should mean: a queue position must be unique, so ROW_NUMBER; a leaderboard should show a genuine tie, so RANK.
- Row-major and column-major order Day 100
- Two conventions for laying a grid out in linear memory. Row-major stores one row at a time and is what C, and NumPy after it, use by default; column-major stores one column at a time and is what Fortran uses. NumPy calls them C order and F order. Neither is more correct — they are historical accidents — but which one you have decides which reshapes are free and which require a copy.
- rowcount Day 90
- The number of rows a statement changed. After an UPDATE or DELETE it is how you tell "changed nothing" from "changed something", which is the honest way to raise a not-found error. After a SELECT it is -1, because SQLite cannot know how many rows a query will produce until it has produced them.
- rowid Day 89
- The 64-bit integer that identifies a row in an ordinary SQLite table. The table itself is a B-tree keyed by it, so a lookup by rowid is already a seek with nothing created. Declaring a column INTEGER PRIMARY KEY makes that column become the rowid rather than adding a second key; any other primary key type creates a separate index.
- RPC Day 23
- Remote Procedure Call — an API style that models operations as named functions to invoke (e.g. createUser) rather than resources to act on; gRPC is a modern high-performance form.
- rubber-duck debugging Day 48
- The practice of explaining your code aloud, line by line, to an inanimate object or patient listener, which often surfaces the flaw the moment intent and reality are compared.
- Rule code Day 76
- The short identifier attached to every linter finding, such as `F401` or `B006`. The letter prefix names the tool family the rule came from — `E`/`W` pycodestyle, `F` pyflakes, `I` isort, `B` bugbear, `SIM` simplify, `UP` pyupgrade, `N` naming, `S` bandit-style security — and the number identifies the rule within it. Select, ignore and suppress by code, never by the wording of the message.
- Run id Day 84
- A short random label generated once per run and stamped on every log line and on the state record for that run. It is what lets you pull the lines belonging to one 03:00 run out of a month of output. Generating a different one in the logger and in the state file is a small bug that doubles the time an investigation takes.
- Run id Day 98
- A single identifier generated once per execution and carried on every log line and, here, on every stored row. It is what turns a pile of log lines into a story: without it, a system with two concurrent runs can tell you that something failed but not which run it was. Stored alongside the data, it also makes an undo possible — deleting exactly what one run wrote is one statement rather than a reconstruction.
- Run identifier Day 97
- A value unique to one execution — a scheduler job id, a CI run number, a uuid4 — stamped onto every line so that two runs of the same program in one file are separable. It belongs on the formatter as a static field rather than at every call site, because a value that must appear everywhere should be attached once.
- Run manifest Day 97
- The first line of a run's log: the resolved configuration and the provenance of every value, with secrets replaced by a placeholder. It is what makes a run reproducible from its own record rather than from anybody's memory, and it is the difference between a result and an anecdote — the seed, the data version, the model name and the hyperparameters are all configuration, and nothing else records them.
- Run summary Day 84
- A few lines printed at the end of every run: how many items succeeded, how many failed, how many were new, and every failure named with its cause. It is what a human reads in three seconds, as opposed to the log, which is what a human reads when something has gone wrong.
- Runbook Day 84
- One page that lets somebody who is not you operate and fix the job: what it does and who would notice if it stopped, when and where it runs, what each exit code means, what to check first when it fails, how to run it by hand including the dry run, and how to turn it off. The test is not whether it is complete but whether somebody else can recover from a failure using only that page.
- Running Statistics Day 208
- Exponential moving averages of mean and variance accumulated by BatchNorm during training to use for deterministic inference.
- Saddle point Day 109
- A stationary point that goes up in some directions and down in others — the middle of a mountain pass, or the origin of x² − y², which rises along x and falls along y. In two dimensions this is a curiosity. In a model's parameter space it is the dominant case, because being a minimum requires the surface to curve upward in every one of millions of directions simultaneously while being a saddle requires only one of them to disagree. The practical hazard is not that an optimiser stops there but that near one the gradient is small without being zero, so progress crawls, and from outside a crawl is hard to tell from convergence.
- safe Day 23
- A property of a request that only reads and never changes server state; GET is safe, which is why it can be cached and retried freely.
- Safe fix Day 76
- An autofix the tool can argue preserves what the program does and discards nothing — no comment, no code you might have meant. Deleting an import that provably nothing references, or sorting an import block, is safe. These are what plain `--fix` applies.
- Safe method Day 78
- A method that is not supposed to change anything — a read. GET and HEAD are safe. Safety is what lets a proxy cache a response and a browser prefetch a link without asking anyone's permission.
- Safetensors Day 193
- A safe, zero-copy serialization format for deep learning tensors that prohibits executable code.
- Safety net Day 73
- The everyday name for a regression suite when it is being used to make a change feel affordable. Its value is proportional to how fast it runs and how often it is run: the bowling suite finishes in 0.01 seconds, which is what makes running it on every save realistic.
- Sample Day 117
- The subset of the population actually observed. A sample of size n drawn "with replacement" allows the same population member to appear more than once; this lesson's lab draws every sample this way, which is what lets a finite array stand in for an effectively infinite population.
- Sample Reweighing Day 179
- A pre-processing mitigation technique assigning sample weights inversely proportional to demographic group-outcome co-occurrences.
- Sample space Day 113
- The set of every possible outcome of an experiment, usually written Ω. For two dice, Ω is the set of all 36 ordered pairs (d1, d2) with each die from 1 to 6. In this lesson, sample spaces are built by exact enumeration with itertools.product rather than written out by hand.
- Sample-ratio mismatch (SRM) Day 119
- A statistically significant difference between the planned traffic split and the realized one -- for example, planning 50/50 and observing 48/52 at a large sample size. Detected with a one-shot chi-squared goodness-of-fit test over the final group counts. A failed SRM check means the two groups are not known to be comparable, which invalidates every downstream comparison regardless of how careful that comparison is.
- sampling bias Day 138
- Systematic mismatch between the sampling frame and the population it claims to describe. Unlike sampling error it does not shrink with sample size: in this lesson's measurement the error for an under-represented group was 5.9459 at n = 500 and 5.9397 at n = 50,000, a change of 0.13% across a hundredfold increase in data.
- Sampling bias Day 117
- A systematic mismatch between the population a sampling frame actually reaches and the population being claimed. Unlike sampling error, it does not shrink with n at all: measured in this lesson's lab, a sampler restricted to the upper half of a population showed a mean absolute error that stayed essentially flat (2.0712 versus 2.0722) across a hundredfold growth in sample size, while an honest sampler's error shrank by 10.28x over the same range.
- Sampling distribution Day 117
- The distribution of a statistic's value across every sample the sampling process could have produced. Not a single number and not the population -- a genuinely separate object, built in this lesson's lab by literally repeating the draw-a-sample-and-compute-the-mean process thousands of times and studying the resulting array of means.
- Sampling error Day 117
- The honest wobble in a statistic that comes purely from which particular population members happened to land in the sample. Shrinks as 1/sqrt(n), exactly as the standard error formula predicts, and is what every standard error and confidence interval in this lesson measures.
- sampling frame Day 138
- The list of things that could possibly have been sampled at all -- every telephone number that could have been dialled, every record that could have been drawn. It is a claim about who is in the world, and when the claim is wrong, everything downstream is wrong in a way no amount of additional sampling repairs. The frame is the single most important thing a datasheet records and the single thing least often written down.
- sampling rate Day 5
- How many times per second a sound wave is measured when digitizing audio, in hertz (for example 44,100 Hz).
- Saturation Day 110
- The region where a bounded non-linearity flattens out and its local derivative approaches zero — tanh far from the origin, or the sigmoid at either extreme. Saturation is the usual explanation for vanishing gradients, but it is a claim about a particular network at particular values rather than a property of the curve: a stack of pure tanh operations pulls its own inputs back towards zero, where the slope is 1, and decays far more slowly than a constant-factor argument predicts.
- savefig Day 128
- The Figure method that writes a chart to a file, with the output format inferred from the extension (or set explicitly via format=). Its output size in pixels is figsize (inches) times dpi, exactly -- unless bbox_inches='tight' trims the canvas to the drawn content afterward, which breaks that exact prediction.
- Scalar Day 99
- An ordinary single number, used to distinguish it from a vector. The word exists because in an expression like 2.5 times v you need to be able to say which of the two things is the plain number. Multiplying by a scalar scales the vector — hence the name.
- Scalar Day 103
- A single number, as opposed to a vector. The dot product of two vectors is a scalar, which is why it is also called the scalar product, and it is worth saying out loud because it is the point where a pile of numbers becomes one comparable answer.
- Scalar function Day 86
- A function that takes one row's values and returns one value: UPPER, LENGTH, SUBSTR, ROUND, ABS, COALESCE, STRFTIME and the rest. Run it over 24 rows and you get 24 answers, which is why it is legal anywhere an expression is legal, including WHERE. Applied to NULL it almost always returns NULL, and that NULL then propagates through everything downstream.
- Scalar multiplication Day 99
- Multiplying every component of a vector by the same number. A positive scalar changes the magnitude and leaves the direction alone; a negative scalar reverses the direction as well; zero collapses the vector to the zero vector. Scaling by 2 doubles the length; scaling by one over the magnitude is normalisation.
- Scalar subquery Day 91
- A subquery returning exactly one row and one column, which can therefore appear anywhere a value can — including in the SELECT list. Two independent scalar subqueries are how the lesson answers "how many books are on the shelves, and how many are out" in a single statement.
- Scale Invariance Day 162
- The property of decision trees where monotonic feature transformations (e.g. scaling or log-transforms) have zero effect on split choices or model predictions.
- Scale-dependence Day 151
- The fact that a penalty is applied in whatever units the coefficients happen to be in. The single most practically important measurement in this lesson: the identical alpha, on identical data, selected 10, 7 and 3 features under raw, standardized, and scikit-learn's own unit-norm scaling respectively.
- Scaling Day 102
- Stretching or shrinking along the axes, with matrix [[sx, 0], [0, sy]]. Derived rather than remembered: one step right becomes sx steps right, so e1 lands at (sx, 0); one step up becomes sy steps up, so e2 lands at (0, sy). Its determinant is sx times sy, which is why scaling by 2 and 3 makes every area six times bigger.
- scan_csv (polars) Day 121
- polars' lazy CSV-reading entry point, which builds a query plan without immediately loading data, deferring the actual read until the plan is executed -- a different answer to "a file larger than memory" than pandas' chunksize, described here from documentation only, since polars is not installed in this environment.
- scheduled task Day 14
- A command or script set to run automatically at specified times or intervals by a scheduler, rather than being started by hand.
- scheduler Day 7
- The part of the operating system that decides which runnable thread gets which CPU core, and for how long, balancing responsiveness, throughput, and fairness.
- Scheduler Day 81
- A component whose only job is to start a program at a specified time or interval. It does not know what your program is for, whether it succeeded, or whether it did the same work twice. Everything beyond "start this now" belongs to you.
- schema Day 24
- A description of the shape valid data must take; for JSON, JSON Schema is itself a JSON document specifying required keys, value types, and allowed ranges.
- schema Day 39
- The declared structure of a relational database: which tables exist, which typed columns each has, and which rules (uniqueness, references) must hold.
- schema Day 82
- A description of the shape of some data: which fields, of which types, with which constraints, which required. Your pydantic models are schemas, and they appear in the generated OpenAPI document under `components.schemas` — which is how you can check that no internal field is part of your published contract.
- Schema Day 85
- The written-down structure of a database — its tables, their columns and types, and the constraints on them. The important word is "written down": a schema is enforced by the engine on every write from every program, including programs that do not exist yet, which is what makes it different in kind from validation code.
- Schema Contract Day 193
- A strict specification defining the expected feature names, data types, and value constraints required by a model.
- Schema design Day 91
- The activity of deciding what tables exist, what columns they have, which values are legal and how the tables relate — so that the questions your users will ask are answerable and the states your data cannot legally be in are unrepresentable. It is judged by the questions it can answer cheaply, not by how normalized it is.
- schema drift Day 135
- A field that is absent from earlier pages of a paginated API response and present on later ones (or the reverse). Assembling the pages with a plain concatenation produces a column that is silently NaN for the earlier rows, with no error or warning, because pandas aligns columns by name and backfills the rest. A deliberate detector names the field and the first page it appeared on.
- Schema version Day 88
- The number recording how many migrations a database has had. This lesson uses PRAGMA user_version, a 32-bit integer in the SQLite header that SQLite never touches itself and that transactions cover like any other write — which is what lets the change and the version bump succeed or fail together. Its limit is that one integer holds no history of when or by whom.
- Schema-on-read Day 92
- The shape of a record is not declared to the store, so it is interpreted by whatever code reads it. Adding a field costs nothing; having added one costs every reader forever, because both shapes now exist and nothing lists which shapes there are. The schema did not go away — it moved from a place that enforces it to a place that hopes. Its characteristic failure is a query that silently returns nothing rather than raising an error.
- Schema-on-write Day 92
- The shape of a record is declared once, in the database, and checked by the engine on every write without exception. A mistake is refused at the moment it is made, with the offending field named. The cost is that adding a field is a migration — planned, reviewed and deployed. The pain is concentrated, visible, and happens on a day of your choosing.
- scikit-learn Pipeline Day 167
- A utility that chains data transformers and an estimator into a single object, enforcing leak-free fit and transform execution across cross-validation folds.
- Scikit-Learn Pipeline Day 173
- A sequential chain of data transformers terminating in an estimator that exposes unified fit, transform, and predict methods.
- scope Day 25
- A named permission an OAuth token is limited to (such as read photos but not delete them), shown on the consent screen so the user can approve or refuse it.
- scope Day 58
- The region of a program where a given name is visible and can be used. Python decides which variable a name refers to by searching scopes in a fixed order (the LEGB rule) and stopping at the first match.
- Scott's rule Day 130
- A bin-width rule based on the sample's standard deviation and size, choosing a width proportional to 3.49 * (standard deviation) * n^(-1/3). Like Sturges, it assumes roughly normal data, so a heavy outlier or a strongly skewed shape inflates the standard deviation and produces bins wider than the data's real structure would justify.
- script Day 41
- A file of commands that runs top to bottom, capturing a sequence of steps so they can be replayed identically — the foundation of all automation.
- script Day 43
- A file of Python code, run all at once with python3 filename.py, as opposed to typing lines interactively in the REPL.
- script Day 49
- A Python file meant to be run start-to-finish from the command line to do one job, as opposed to a notebook (interactive cells) or a package (a directory of modules).
- sdist Day 83
- A source distribution: a gzipped tar archive of the project roughly as the maintainer has it — source with its directory layout intact, tests, licence, `pyproject.toml`, `MANIFEST.in` and a `PKG-INFO`. Installing one means building it first, which runs the publisher's build backend on the installing machine.
- Seam Day 74
- A place where a test can substitute one implementation for another without editing the code under test. A parameter is a seam checked by the interpreter and visible in the signature; a patch target is a seam expressed as a string that nothing checks until the test runs.
- Seam (handoff) Day 140
- The interface between two stages of a study -- the artefact one stage owes the next. A study has nine stages and eight seams, and a capstone almost always fails at a seam rather than inside a stage, because a seam is invisible from within either stage it joins.
- Seasonality Day 192
- Predictable, repeating cyclical patterns or fluctuations occurring at regular calendar intervals (hourly, weekly, annual).
- Secant line Day 108
- The straight line through two points on a curve. Its slope is exactly the average rate of change between those two points, which makes "average rate of change" and "slope of the secant" two names for one number. As the two points move closer together, the secant pivots — and what it pivots towards is the tangent.
- Second derivative Day 108
- The derivative of the derivative, written f''(x) or d²y/dx². It answers whether the slope is itself increasing or decreasing. Numerically it collapses to (f(x + h) − 2f(x) + f(x − h)) ÷ h², which reads as how far the middle value sags below the average of its neighbours. Note the h² in the divisor: it amplifies rounding error far harder than a first difference does, so its usable range of h is both narrower and larger.
- Second difference Day 149
- The discrete analogue of a second derivative: `diff(diff(values))`. Constant across a swept squared-error curve here (standard deviation 0.000000, a parabola); varying across the matching absolute-error curve (standard deviation 1.9366, a kinked, piecewise-linear shape).
- Secondary index Day 92
- Any index on something other than the primary key, letting you find records by a field you did not key on. In a relational engine you declare one and the engine maintains it inside every transaction. Over a key-value store you build it as extra keys and maintain it yourself — and when a delete forgets to repair it, the index points at a key that no longer exists, with no error raised. That is an orphaned reference, recreated by hand.
- Secondary table Day 93
- The junction table behind a many-to-many relationship, passed to relationship() as secondary=. SQLAlchemy wants it as a Core Table rather than a mapped class precisely because it is not an entity — it carries nothing but the two foreign keys and has no identity worth talking about. The moment it acquires an attribute of its own it stops being secondary and becomes a mapped class, which is the Day 91 lesson restated in ORM terms.
- secret Day 25
- Any credential — API key, token, or password — that grants access and must be kept out of code and version control; equivalent to a password in the harm a leak causes.
- secret Day 26
- A random string known only to the sender and receiver, used to compute and verify webhook signatures; a credential that must be kept out of source code and logs.
- Secret Day 84
- A credential — a token, a password, a key. It is read from the environment and from nowhere else, because a command-line flag lands in your shell history and in ps output while a configuration file lands in version control. When one leaks, revoke it first and clean up second; a rewritten repository history does not un-publish anything already cloned.
- Secret Day 97
- A value that grants access — an API key, a token, a password. It belongs in the environment or a secret manager, never in a file in the repository, where deleting the line does not remove it from the history, and never as a command-line flag, where it is visible in `ps` to every other user and lands in the shell history file. Its presence and its provenance may be printed; its value may not.
- sed Day 10
- The stream editor: a command that applies editing operations — most often substitution with `s/old/new/` — to a flowing stream of text, printing the result without changing the source file by default.
- seed (in a seaborn call) Day 129
- An integer passed to functions that compute a bootstrapped error bar (for example sns.barplot(..., seed=42)), fixing the random number generator's starting state so the same call on the same data produces an identical interval on every run. Omitting it means two runs of the same call can produce slightly different bar extents.
- Seeded generator Day 104
- An object produced by numpy.random.default_rng(seed) that yields a reproducible stream of pseudo-random values. It replaces the older numpy.random.seed, which the library's own docstring calls "a convenience, legacy function": that one sets a single global generator shared by every library in the process, so a call you did not write can move your sequence. A generator you own and pass around cannot be moved by anyone else, which is what allows a lab to assert on specific numbers rather than on vague properties.
- Segment fishing Day 119
- Testing many segments (region, device, tenure) at the same significance threshold used for the primary metric and reporting whichever one looks interesting, without correcting for the number of segments tested. The multiple-comparisons problem wearing a business-stakeholder-friendly disguise; the fix is treating segment findings as hypotheses for a dedicated follow-up, never as conclusions.
- selectinload Day 93
- An eager-loading strategy that issues a second SELECT with an IN clause listing the parent keys. Two statements, always, whatever N is. No join, so no row duplication — which makes it the right default for a one-to-many collection.
- Selection bias Day 143
- The optimism introduced by choosing features, models or thresholds using data that is later used to evaluate them. Measured here at 0.23 accuracy points at twenty features and 0.47 at fifty, on data containing nothing to learn.
- Selection bias Day 144
- The optimism created by keeping the best of several candidates measured on the same set. Not a vague hazard but a computable quantity -- measured here at 0.0728 for a thousand candidates that were literally coin flips.
- Selection Bias (Leakage) Day 172
- Optimistic evaluation bias caused by selecting features on the full dataset rather than strictly inside cross-validation training folds.
- Selection of a regression metric Day 152
- The decision, made before reporting, about which function best answers the actual business question -- whether occasional large errors are more costly than being typically slightly off, whether a percentage is meaningful given the target's scale, and what unit a stakeholder needs to hear. Not a formality; measured directly to change which of two models looks better.
- Selection optimism, measured Day 147
- What actually happened when the prediction above was checked against a real test evaluation, over 20 independent seeds: a mean drop of -0.0001, far below the 0.0330 mean prediction, because the candidates in this sweep are correlated and genuinely skilled rather than independent and skill-free.
- Selection optimism, predicted Day 147
- The optimism Day 144's formula predicts for a specific sweep: the standard error of an accuracy on one cross-validation fold's worth of rows, times the expected maximum of K standard normal draws. Computed here at 0.0326 for a 36-candidate sweep, before the test set is ever consulted.
- Selectivity Day 89
- The consequence of cardinality: how many rows the average distinct value matches. In this lesson's data, run_id matches about 100 rows and status matches about 133,334. Seeking a value that matches a third of the table is genuinely more expensive than reading the table straight through, which is why the planner sometimes declines a perfectly valid index and is right to.
- self Day 67
- The conventional name for a method's first parameter, which receives the instance the method was reached through. It is an ordinary parameter, not a keyword, and Python makes it explicit so the mechanism is visible rather than hidden.
- self-assessment Day 42
- An honest rating of your own confidence across the six areas, used to find your weakest area and the specific earlier day to revisit — a repair map rather than a grade.
- Self-join Day 87
- A table joined to itself, with two distinct aliases so the query can tell the copies apart. It relates rows to other rows in the same table: employees to managers, members to whoever referred them, replies to the comment they answer. Use LEFT unless you specifically want to exclude the rows that reference nobody, because an inner self-join silently drops them.
- Self-supervised learning Day 142
- Supervised learning in which the target is manufactured from the input itself -- next-token prediction being the case that matters most. Mechanically it is ordinary supervised learning; what changes is that the labels are free, which changes the economics completely.
- Semantic search Day 103
- Retrieval by meaning rather than by keyword. Turn every document into a vector, turn the query into a vector the same way, and return the documents whose vectors point most nearly the same way as the query. The core is four lines: score everything with cosine similarity, sort, take the top few. Everything a production system adds is about getting better vectors and searching many more of them quickly.
- semantic versioning Day 35
- A convention that gives version numbers meaning as MAJOR.MINOR.PATCH: MAJOR for breaking changes, MINOR for backward-compatible features, PATCH for backward-compatible bug fixes.
- Semantic versioning Day 83
- The convention that a version is `MAJOR.MINOR.PATCH`, incremented respectively for a breaking change, a backwards-compatible addition, and a backwards-compatible fix. Published by Tom Preston-Werner, with version 2.0.0 of the specification dating from 2013. It is a real service to your users when you follow it — and many projects do not, so read changelogs rather than trusting the numbers.
- Semantic Versioning (SemVer) Day 193
- A versioning convention (MAJOR.MINOR.PATCH) communicating breaking schema changes, retraining updates, and hotfixes.
- Semi-supervised learning Day 142
- Learning from a small labelled set alongside a large unlabelled one. Not a fourth setting but a practical response to label cost: clustering the unlabelled data and labelling one representative per cluster scored 0.876 on iris against 0.6455 for three labels chosen at random.
- separation of concerns Day 63
- The design principle that each distinct aspect of a program — parsing, computing, formatting, input/output — should live in its own place, so you can think about, test, and change one concern without disturbing the others. Named by Edsger Dijkstra in 1974.
- sequential palette Day 127
- A colour ramp that increases monotonically in luminance, such as viridis, for quantitative or ordinal data where more is more. Its order survives greyscale printing: five steps of viridis measure 0.019, 0.089, 0.223, 0.451 and 0.783 in relative luminance, a rank correlation with position of exactly +1.00.
- Sequential updating Day 115
- Applying Bayes' theorem (in odds form, one likelihood ratio at a time) across multiple pieces of evidence in succession. The order the evidence arrives in does not affect the final posterior, because each update multiplies the running odds by a factor, and multiplication is commutative.
- serialization Day 24
- The act of turning an in-memory value into a flat, self-contained string of characters that can be stored or transmitted and later rebuilt.
- serialization Day 65
- Turning in-memory objects into a sequence of bytes that can be stored or transmitted — what json.dump and csv.DictWriter do.
- serialization Day 82
- Turning Python objects into bytes a client can read — here, into JSON. It is where a `datetime` becomes an ISO string and a parsed URL becomes text, and, when a response model is declared, where undeclared fields are dropped.
- Serialization Day 94
- Turning a validated object back into transportable data. model_dump() produces Python objects and leaves a datetime as a datetime; model_dump_json() produces a JSON string and renders it as ISO 8601 text. Both take exclude, include, by_alias and exclude_none, which is where you decide what an outward-facing extract may contain.
- Series Day 120
- A one-dimensional pandas data structure: a sequence of values paired with a sequence of labels called the index. The values are typically backed by a NumPy array (or, for certain dtypes since pandas 2.0, a PyArrow array); the index is what a bare NumPy array does not have.
- server Day 15
- The program that listens for requests and returns responses, such as the machine hosting a website.
- server Day 22
- The machine and code that receives requests and fulfills them, implementing the API behind the contract while keeping its database and internals private.
- server-sent events Day 26
- A web standard (SSE) in which a server streams a sequence of events to a client over one long-lived, one-way HTTP connection.
- server-side rendering Day 20
- Assembling the finished HTML on the server for each request so content appears quickly and is easy for search engines to index, at the cost of more work per request.
- Session Day 78
- In requests, an object that carries configuration shared by many requests — headers, cookies, authentication — and, more valuably, a pool of open connections. Using one is usually worth more than every other optimisation in a client combined, especially over HTTPS.
- Session Day 93
- The ORM's unit of work. It holds an identity map, tracks which objects are pending, dirty and deleted, decides when to flush that work to the database, and owns a transaction while it does. Nearly every confusing ORM error is really a question about which state an object is in, when the flush happened, or whether the Session that loaded the object is still open.
- Session per request Day 93
- The standard lifecycle for a Session in a server: begin one at the start of a request, commit or roll back at the end, close it, and never share it between threads or requests. It matches a Session's transaction to a unit of user intent. A global Session accumulates every object ever loaded and never lets go of a transaction; a Session per query throws away the identity map that makes the ORM worth having.
- set Day 54
- An unordered collection of unique, hashable items, written with braces, e.g. `{"a", "b"}` (but the empty set is `set()`, since `{}` is an empty dict). It removes duplicates automatically and answers membership in roughly constant time.
- set -e Day 12
- A shell option (part of `set -euo pipefail`) that makes a script exit immediately when any command fails, instead of blindly continuing after an error.
- set comprehension Day 55
- A comprehension in curly braces that builds a set, so duplicates collapse and order is not kept — for example `{r["team"] for r in records}`.
- set_params() Day 146
- Accepts the same keys get_params() reports and writes them back, reaching through nested prefixes to mutate a Pipeline's actual step objects. Measured to change a nested LogisticRegression's live .C attribute directly.
- setdefault Day 53
- The dictionary method d.setdefault(key, default) that returns the value for key, inserting default first if the key is missing. It is the standard tool for grouping, because a per-key collection is created exactly once.
- settings Day 36
- A list of an editor's preferences — font size, tab width, whether to trim stray whitespace on save — usually stored as a plain-text file you can edit and share.
- shallow copy Day 52
- A copy that duplicates the outer list but shares the objects it references, made with `a[:]`, `list(a)`, or `a.copy()`. The two outer lists are independent, but nested lists are still shared between them.
- Shannon Entropy Day 162
- An information-theoretic measure of uncertainty: H = - sum(p_k * log2(p_k)), measuring the expected bits required to encode class labels.
- SHAP (SHapley Additive exPlanations) Day 168
- A unified framework based on cooperative game theory that assigns each feature an exact additive attribution score for individual model predictions.
- SHAP (SHapley Additive exPlanations) Day 178
- A unified framework interpreting predictions by computing Shapley values of conditional expectations across feature coalitions.
- shape Day 104
- A tuple of non-negative integers giving the number of elements along each axis — NumPy's guide defines it as exactly that. A (3, 4) array holds twelve values arranged as three rows of four, in one block. The shape is a description of how to read the block, not a description of how it is stored, which is why reshaping and transposing can cost nothing.
- Shape Day 100
- The pair (rows, columns) describing a matrix's size, and in NumPy the tuple returned by .shape. Rows first — a convention rather than a law, and one worth saying out loud, because half the time spent confused about an array is time spent unsure which number is which. Related: .ndim is how many axes there are (2 for a matrix) and .size is the total entry count, rows times columns.
- Shape error Day 101
- The ValueError raised when the inner dimensions of a product disagree, and the most common error in applied linear algebra. NumPy message mentions a gufunc signature which can be ignored on first reading; the useful part is the phrase naming the two sizes. The repair is usually a transpose, but there are two of them — X @ X.T compares examples with examples and X.T @ X compares features with features — and they have different shapes and different meanings, so transposing until the error goes away trades a loud failure for a quiet wrong answer.
- Shape rule Day 101
- An (m, n) @ (n, p) gives an (m, p). Worth deriving rather than memorising: the inner dimensions match because of what each side accepts and produces, and the outer dimensions survive because they are the two ends of the pipeline — what goes in at one end and what comes out at the other. Reading a shape error means printing both shapes and looking only at the inner two numbers.
- Shape versus duration (in a performance claim) Day 96
- The distinction that makes a measurement portable. A duration — "it took 172 milliseconds" — is a fact about one machine on one day and is worthless to a reader and flaky in a test. A shape — "threaded I/O is at least four times faster than sequential; threaded CPU work is not meaningfully faster" — is a fact about the program and reproduces elsewhere. This lesson tests assert only shapes, with wide margins, and every reported figure names the machine, the number of runs and the spread.
- Shapley Value Day 178
- The unique game-theoretic payoff allocation satisfying efficiency, symmetry, dummy player, and additivity axioms.
- Sharding Day 92
- Splitting a dataset across machines by a key, so each machine holds a slice of the whole. It increases capacity for both reads and writes, and it is what turns a join across the split into a network operation and a foreign key across the split into a distributed transaction. Distinct from replication, which solves a different problem.
- Shear Day 102
- A sideways slide in proportion to height, with matrix [[1, k], [0, 1]] for the horizontal case. The deck of cards pushed over: the bottom card does not move, every card above it slides further. e1 has height 0 so nothing pushes it; e2 has height 1 so it lands at (k, 1). Its determinant is exactly 1, because sliding the cards changes no areas — the sheared square has the same base and the same height as the original.
- shebang Day 12
- The `#!` characters on a script's first line, followed by the path to an interpreter (e.g. `#!/usr/bin/env bash`), telling the system which program should run the file.
- shell Day 6
- The user-space program (such as zsh or bash) that reads typed commands and asks the kernel to run them — distinct from both the terminal window and the operating system itself.
- shell Day 8
- The program running inside a terminal that reads your command lines, interprets them, launches the corresponding programs, and prints their output; examples include bash, zsh, and fish.
- shell function Day 11
- A named block of shell commands that can take arguments and contain logic, used like a command; more powerful than an alias for anything beyond fixed text substitution.
- shell variable Day 11
- A named value known only to the current shell; unlike an environment variable, it is not inherited by the programs the shell launches unless it is exported.
- ShellCheck Day 12
- A free, open-source static analyzer (linter) for shell scripts that flags bugs like unquoted variables and misused test brackets before the script is ever run.
- ShellCheck Day 37
- A free, open-source linter for shell and Bash scripts that flags quoting, test-command, and portability bugs, each tagged with a rule code (such as SC2086) linking to an explanation.
- Shoelace formula Day 102
- A way of computing the area of a polygon from its corners: walk them in order, add x_here times y_next minus x_next times y_here for each edge, and halve the total. Named for the way the cross-multiplied pairs criss-cross like lacing. Its sign depends on which way round the corners are listed, which is what makes it the right tool for measuring a determinant directly rather than computing one.
- short-circuit evaluation Day 50
- Python's lazy, left-to-right evaluation of `and`/`or` that stops as soon as the result is settled: `A and B` skips `B` when `A` is falsy, and `A or B` skips `B` when `A` is truthy. It is both a speed optimisation and a correctness tool (e.g. `x is not None and x.field`).
- Shrinkage (Learning Rate) Day 164
- A regularization scaling factor eta in (0, 1] that multiplies the output of each newly added tree, controlling the step size along the functional gradient.
- side effect Day 57
- Anything a function does beyond returning a value — printing, writing a file, making a network call, or mutating an object it was passed. Side effects are sometimes necessary but make a function harder to test.
- Side effect Day 74
- The unittest.mock attribute that decides what a call does beyond returning a fixed value. Assign a list and successive calls return successive elements; assign an exception and the call raises it — the best way to exercise error handling; assign a callable and it is invoked with the same arguments.
- Sigmoid Function Day 155
- An S-shaped mathematical activation function sigma(z) = 1 / (1 + exp(-z)) that maps any real number into the interval (0, 1).
- sign bit Day 4
- The leftmost bit of a signed integer; in two's complement it carries a negative place value (−128 in a byte), so a 1 there makes the whole number negative.
- signal Day 7
- A small numbered notification the kernel delivers to a process, such as SIGTERM ("please shut down"), SIGINT (Ctrl+C), or SIGKILL (unrefusable termination).
- signature Day 26
- A value (typically an HMAC computed over the raw body with a shared secret) attached to a webhook delivery so the receiver can prove the payload is authentic and unaltered.
- Signed Distance Day 156
- The perpendicular Euclidean distance from a point to a hyperplane, with positive sign indicating the positive half-space and negative sign indicating the negative half-space.
- Silhouette Coefficient Day 183
- A cluster validation metric ranging from -1 to +1 measuring how well-separated and cohesive clusters are.
- Silhouette score Day 142
- An internal clustering criterion comparing each point's distance to its own cluster against its distance to the nearest other cluster. It measures separation and says so honestly. On iris it picks k equals 2, for a dataset with three species, because two of those species overlap.
- Similarity versus distance Day 107
- A distance shrinks as two things become more alike and is zero when they are identical; a similarity grows. Cosine and Jaccard are similarities; L1, L2, L-infinity, Hamming and Mahalanobis are distances. No library knows which one it has been handed, so a ranking function has to be told — and getting it backwards produces a result that still looks like a ranked list. Converting between the two is a modelling assumption rather than a derivation: 1 minus cosine similarity is bounded and well behaved, while 1 minus a Euclidean distance goes negative and 1 divided by (1 plus d) is a choice somebody made.
- Simple linear regression Day 148
- A model with exactly two learned numbers -- a slope and an intercept -- fitted to one predictor and one target so their squared errors are as small as possible. "Simple" means one predictor, as opposed to multiple linear regression's several predictors.
- Simple regression coefficient Day 150
- A predictor's coefficient when it is the only predictor in the model -- its raw, unconditional association with the target, before any other variable is accounted for.
- Simple Statistical Baseline Day 181
- A fast, interpretable model (logistic regression, linear regression) serving as the minimum complexity benchmark.
- SimpleImputer Day 125
- scikit-learn's imputation transformer, performing the same arithmetic as pandas' fillna(mean) but behind a fit/transform boundary: fit() learns the imputation statistic from training data only, and transform() applies it to both training and test data, preventing the test set's own statistics from leaking into what the model is trained on.
- SimpleImputer Day 174
- A univariate imputation transformer that replaces missing values with fixed summary statistics (mean, median, mode, or constant).
- Simpson's paradox Day 116
- A trend that holds in every subgroup of a dataset and reverses when the subgroups are pooled, purely because of how the subgroups were weighted, with no error anywhere in the arithmetic. The overall (pooled) rate is a weighted average of the subgroup rates, and unequal weights across the groups being compared can flip the ranking entirely.
- Simpson's paradox Day 119
- A pattern in which an effect points one way in every subgroup of a dataset and the opposite way when the subgroups are pooled, caused by the subgroups' relative sizes differing between the groups being compared. Measured directly in this lesson's dataset B, where every segment shows a negative effect while the pooled effect is positive.
- Simpson's paradox (as a coefficient flip) Day 150
- The same reversal Day 119 measured in aggregated rates, here appearing as a continuous coefficient: conditioning on a correlated variable can invert the apparent direction of another variable's relationship with the target.
- single responsibility Day 63
- The principle that a function or module should do one nameable thing and have one reason to change. A test of it: if you cannot describe what a function does in a single "it ..." sentence without an "and," it has more than one responsibility.
- Single-Batch Overfit Test Day 209
- A foundational sanity check where a model is trained on 10-32 samples to verify it can drive loss to zero and achieve 100% accuracy.
- Singular matrix Day 102
- A square matrix whose determinant is zero, so it has no inverse. Geometrically it flattens the space: for a 2 by 2 matrix both columns lie along the same line, so every vector lands on that line and two different starting points can share a landing place. numpy.linalg.inv raises LinAlgError with the message "Singular matrix" rather than returning anything, and because LinAlgError is a subclass of ValueError, except ValueError catches it.
- Singular Value Decomposition (SVD) Day 185
- The matrix factorization X = U Sigma V^T decomposing a data matrix into left singular vectors, singular values, and right singular vectors.
- Singular versus ill-conditioned Day 153
- A singular matrix cannot be inverted at all; an ill-conditioned one can be inverted but the inversion amplifies floating-point error. The near-duplicate column in this lesson's dramatic case is ill-conditioned, not exactly singular -- which is why the normal equations return a number at all, just a badly wrong one.
- size() (GroupBy) Day 123
- Counts the number of rows in each group, regardless of whether any column's value is missing. Differs from count() exactly on groups containing missing values.
- Skew Day 116
- Asymmetry in a distribution's shape. A right-skewed distribution (a long tail of unusually high values, such as income or house prices) pulls the mean above the median; a left-skewed distribution pulls it below. For a symmetric distribution, mean, median and mode coincide.
- Skewness Day 148
- A rough measure of a distribution's asymmetry, zero for a perfectly symmetric one. Used here as an informal check on whether a model's residuals look roughly normal -- 0.156 for the BMI model's residuals, mildly asymmetric and not alarming.
- sklearn Pipeline Day 143
- scikit-learn's object composing preprocessing steps with a model so that every fit happens inside the cross-validation fold. It makes today's leak structurally impossible rather than merely unlikely -- but only for the steps placed inside it.
- Slack Variable (xi) Day 169
- A non-negative penalty variable introduced in soft-margin SVMs to quantify the degree to which a sample violates the margin boundary.
- slice Day 45
- A run of characters copied out of a string with s[start:stop], returning a new string that includes start but excludes stop (stop − start characters).
- slice Day 52
- A sub-sequence taken with `list[start:stop:step]`, which returns a NEW list of the items from `start` (included) up to `stop` (excluded), stepping by `step`. Examples: `a[1:3]`, `a[::2]` (every other), `a[::-1]` (reversed).
- Slice Performance Audit Day 181
- Evaluating model performance across critical demographic, operational, or business cohorts to detect hidden failures.
- SLO Day 40
- A Service Level Objective: a target you commit to for a measurement of user experience, such as 99.9% of requests succeeding in under 300 ms over a 30-day window, giving alerting a principled basis.
- Slope Day 148
- The change in the predicted target per one unit of the predictor, in the target's real units. Measured here at 10.2331 points of disease progression per unit of BMI -- only interpretable in raw units, not the mean-centred, unit-norm-scaled default scikit-learn's diabetes dataset returns.
- slots Day 69
- The `slots=True` option, which generates a class using `__slots__` so instances carry no per-instance dictionary. It saves memory when you hold very many small records, at the cost of forbidding attributes that were not declared as fields.
- small multiples Day 127
- A grid of small charts sharing a scale, one per group, instead of many series crowded into one panel. Trades rung one of the accuracy ordering for rung two in exchange for making a tangle readable.
- small multiples Day 131
- A grid of individually small charts, one per category or series, sharing the same axis scales so they remain directly comparable. The standard remedy for a spaghetti chart once the series count exceeds roughly five or six lines on one set of axes.
- sMAPE Day 176
- Symmetric Mean Absolute Percentage Error, providing scale-independent percentage error bounded between 0% and 200%.
- sMAPE Day 192
- Symmetric Mean Absolute Percentage Error: an evaluation metric bounding percentage errors between 0% and 200%.
- SMOTE Day 160
- Synthetic Minority Over-sampling Technique: an algorithm that synthesizes new minority class instances by interpolating between k-nearest neighbors in feature space.
- snapshot Day 29
- The captured state of the tracked files at the moment of a commit; a project's history is a sequence of these snapshots.
- snapshot Day 30
- The complete state of every tracked file at the moment of a commit; Git stores snapshots rather than lists of edits, and computes differences on demand.
- socket Day 17
- One endpoint of a network connection, identified by an IP address and a port together (written host:port).
- Soft delete Day 88
- Marking a row as deleted, usually with a nullable deleted_at column, instead of removing it. The row stays, so foreign keys still resolve, history still adds up, and an accident is one UPDATE away from being undone. The cost is a filter every future query must remember, and the day somebody forgets it, deleted rows reappear in a report.
- Soft delete Day 91
- Marking a row as removed with a column — withdrawn_at, left_at — instead of deleting it, so that history still resolves. The cost is exact and permanent: every present-tense query must now decide and state which rows it means, and the one that forgets returns a wrong number without erroring. Which filter applies is a property of the question rather than of the table.
- soft reset Day 34
- git reset --soft: moves only HEAD to the target commit, leaving the index and working tree untouched, so the rewound changes remain staged.
- Softmax Day 198
- A normalized exponential function that maps a K-dimensional vector of arbitrary real logits into a categorical probability distribution summing to 1.0.
- Softmax Regression (Multinomial) Day 156
- A direct multiclass generalization of logistic regression that models a normalized categorical distribution over all K classes simultaneously.
- sort (groupby) Day 123
- A groupby keyword, default True, controlling whether the result is sorted by the group key. Passing sort=False skips that sort as a cheap performance win when the result's order does not matter, without changing any of the computed values.
- sort vs sorted Day 52
- `list.sort()` orders the list in place and returns None; `sorted(list)` returns a NEW sorted list and leaves the original untouched. Both accept a `key=` function and are stable. Confusing the two causes the `a = a.sort()` bug.
- source assessment Day 134
- A fast, structured check run against a candidate dataset before committing time to it, covering provenance, the presence of a data dictionary, granularity, coverage, licence, and whether a checksum can be produced. Failing a gate does not disqualify a source; it means the source needs a stated caveat rather than a silent, undocumented assumption.
- spaghetti chart Day 131
- A single set of axes carrying so many overlaid line series that individual lines become impossible to distinguish by color or position alone. The practical fix past a small series count is small multiples -- one panel per series, sharing axes for comparability.
- span Day 40
- One unit of work within a trace — a database query, a service call, a computation — with a start time, a duration, and a name, nested under a parent span.
- Sparse ground truth Day 151
- A synthetic dataset (built with make_regression) where the exact set of informative features is known in advance, used to measure whether lasso's selection is actually CORRECT rather than merely sparse. Measured precision 1.0 and recall 1.0 at a sensible alpha and low noise; recall 0.0 at a heavy penalty and high noise.
- Sparse matrix Day 100
- A representation that stores only the non-zero entries plus their coordinates, for matrices where nearly every entry is zero. Not a niche case: document-term matrices, recommendation data and graph adjacency matrices are all overwhelmingly zero. A 100,000 by 50,000 document-term matrix is 40 GB dense in float64 and unremarkable sparse. The cost is real — some operations are slower and some unsupported, and when only a modest fraction of entries are zero the bookkeeping can outweigh the saving — but when a sparse representation is the only workable one, it is genuinely the only one.
- Sparsity-Aware Split Finding Day 165
- An algorithm that evaluates splits on non-missing values and learns an optimal default branch direction (left or right) for missing values.
- Spearman correlation Day 116
- A measure of MONOTONE association of any shape, computed as Pearson's correlation applied to the RANKS of two variables rather than their raw values. Reports exactly 1.0 for any perfectly increasing relationship, linear or not -- for example, y = x^3.
- Spearman correlation Day 130
- A correlation computed on the RANKS of two variables rather than their raw values, so it measures the strength of any MONOTONIC relationship (one that consistently increases, or consistently decreases), not just a linear one. It still misses a relationship that rises and then falls, such as a symmetric parabola, because that relationship is not monotonic either.
- Specification Day 73
- A statement of what a system must do. In test-driven development the test is the specification, and the difference from a document is that this one is executable and fails loudly the moment the code stops matching it.
- Specificity (True Negative Rate) Day 159
- The proportion of actual negative instances that were correctly identified: Specificity = TN / (TN + FP).
- Spectral radius Day 106
- The largest absolute value among a matrix eigenvalues. The word spectrum for the set of eigenvalues comes from Hilbert work on integral equations, predating its use in physics for what a prism does to light. The spectral radius is the single number that answers whether repeated application of a matrix grows or decays: above 1 and the iterates grow without bound, below 1 and they shrink to nothing, exactly 1 and they hold steady. That makes it the honest one-number stability test for anything driven by an iterated linear map, and it is what the power method converges towards. Related and worth knowing alongside it: the ratio of largest to smallest eigenvalue magnitude is the CONDITION NUMBER, which measures how much a small error in the input can be amplified in the output.
- split Day 45
- A string method that breaks text into a list of pieces on a separator; with no argument it splits on any run of whitespace.
- split-apply-combine Day 123
- The three-stage pattern groupby implements. Split: rows are sorted into buckets by their group key, and rows with a missing key are excluded from every bucket by default. Apply: a function runs once per bucket, on that bucket's rows only. Combine: the per-bucket results are stitched back into a final object, whose shape depends on which combine strategy (agg, transform, filter, apply) was used.
- Spy Day 74
- A test double that answers like a stub and additionally records how it was used, leaving the assertion to the test. A recording sleep collects the requested waits, so a retry test can prove the backoff schedule while nothing ever waits.
- SQL Day 39
- Structured Query Language, the standard language for asking questions of and changing data in a relational database, with clauses such as SELECT, WHERE, and GROUP BY.
- SQL Day 85
- The language for querying and modifying relational data, designed at IBM as SEQUEL by Donald D. Chamberlin and Raymond F. Boyce and renamed after a trademark conflict. It became an ANSI standard in 1986 and an ISO standard the following year. In practice it is a family rather than one language: every engine implements the core and then diverges.
- SQL injection Day 90
- What happens when a value becomes part of a statement instead of an argument to it. Given the input Ada' OR '1'='1, a concatenated lookup becomes WHERE name = 'Ada' OR '1'='1', which is true for every row. Nothing malfunctions; the engine answers the question it was actually asked. Escaping is not an equivalent fix, and the module's refusal to run two statements in one execute is a limit rather than a defence.
- SQLAlchemy Core Day 93
- The lower of SQLAlchemy's two layers: an SQL expression language with Table, MetaData, select(), insert() and update(), plus the engine, the dialects and the connection pool. It is a complete library on its own — you can use it with no models and no Session at all. Knowing the two layers are separate is what makes dropping from the ORM to Core a normal move rather than an admission of defeat.
- SQLAlchemy ORM Day 93
- The upper layer, built on Core: declarative models, relationships, and the Session. It does not bypass Core — it emits its work AS Core expressions, which is exactly why you can mix the two in one transaction without ceremony.
- sqlite_stat1 Day 89
- The ordinary table ANALYZE writes its statistics into. You can read it with a SELECT like any other table, which is the quickest way to find out what the planner believes about your data — and to discover that a column you were about to index matches a third of the rows.
- sqlite3.Row Day 90
- The row type that supports both row["title"] and row[1], along with keys() and len(). It is deliberately not a dict: it has no .get, it is immutable, and json.dumps refuses it. dict(row) converts one when you need the real thing. Using it removes a whole class of bug in which adding a column to a SELECT list silently shifts every positional index.
- square law of area encoding Day 127
- The fact that a circle's area goes as the square of its radius, so encoding a value by radius squares every ratio in the chart -- a doubled value is drawn four times as large. Measured here as an analytic area ratio of 4.0 for a data ratio of 2.0, and as 20,368 rendered pixels against 5,156. Fixed by scaling the radius by the square root of the value so that area is proportional.
- Squared error Day 149
- The loss `sum((y - prediction)^2)`. Minimised by the mean; smooth everywhere, with one minimum; squares every residual, so an 80-unit error contributes 6,400 to the total, seventeen to seventy-two times more than the loss below moves for the same outlier.
- Squared Euclidean distance Day 107
- The sum of squared differences with the square root omitted. Common because it avoids a square root and because it is what least squares minimises, and not a norm: doubling a vector multiplies it by four rather than by two, so absolute homogeneity fails and the triangle inequality goes with it. It is safe for ranking, because squaring preserves order on non-negative numbers, and unsafe anywhere the triangle inequality is assumed — a ball tree, a cover tree, or a metric-space index.
- Squared-error loss Day 110
- A single number measuring how wrong a prediction is, computed as (prediction minus target) squared. Its derivative with respect to the prediction is 2 times (prediction minus target), which is where every backward pass in this lesson begins. Squaring makes the loss a scalar with a well-defined minimum, and being a scalar is what lets reverse mode differentiate it against millions of parameters in one sweep.
- squash merge Day 33
- A merge strategy that combines all of a branch's commits into a single new commit on the target branch, producing a flat, one-commit-per-pull-request history.
- src layout Day 83
- Putting the importable package under `src/` rather than at the project root. The argument is not tidiness: Python puts the working directory near the front of its search path, so a flat layout lets an uninstalled working copy win over the installed one silently. With `src/` there is nothing importable in the working directory, so your tests exercise the installed package — the thing your users actually get.
- SSD Day 3
- A solid-state drive: persistent storage built from flash memory with no moving parts, answering random reads in roughly a tenth of a millisecond.
- SSH key Day 32
- A cryptographic key pair used to authenticate to a remote: a private key stays on your machine and a public key is uploaded once, and your identity is proven by a handshake with no secret transmitted.
- Stability threshold Day 112
- The learning rate beyond which an iterative update stops converging and starts diverging. For gradient descent on f(x) = a*x^2, the exact threshold is eta = 1/a: below it the update multiplier |1 - 2*a*eta| is under 1 and the run shrinks toward the minimum; above it, the multiplier exceeds 1 and the run grows without bound.
- stable sort Day 52
- A sort that preserves the original relative order of items that compare equal. Python's sort (Timsort) is stable, which lets you sort by two keys in turn — sort by the minor key first, then the major key.
- stack / unstack Day 124
- DataFrame methods that move a level of a MultiIndex between the row index and the column labels. stack() moves the innermost column level down into the row index, making the frame taller; unstack() moves the innermost row-index level out into columns, making it wider.
- stack frame Day 48
- One entry in a traceback (and in the call stack): a single function's place in the chain of calls, recording the file, line number, function name, and the exact line being executed.
- stack frame Day 62
- The private workspace for a single function call, holding that call's own arguments and local variables while it waits for the calls it made to finish. In factorial(4), four frames exist at the deepest point, each with its own value of n, before they unwind one by one.
- stack overflow Day 62
- The condition where the call stack grows past its limit — in Python surfaced as RecursionError. It is caused by recursion that never reaches its base case, or by input nested deeper than the limit allows; the fixes are a correct base case, a higher limit (with care), or an iterative rewrite.
- Stacking (Stacked Generalization) Day 168
- An ensemble machine learning technique where multiple base models generate out-of-fold predictions, which serve as features for a higher-level meta-learner.
- stage Day 41
- One step in a pipeline that runs a specific check or action, such as linting or testing, and must succeed for the pipeline to continue.
- Stage Day 98
- One step of a pipeline with a single responsibility and a single promise. This day uses five — ingest, validate, store, report, observe. The value of the division is not tidiness: it is that when a run goes wrong, the stage boundary tells you where to look, and each stage can be tested on its own because its inputs and outputs are ordinary values.
- Stage Day 143
- One step of a workflow together with the declaration of what it requires and what it produces. The declaration is the part that matters: without it a stage is just a function, and the order it must run in exists only in somebody's memory.
- Stage contract Day 143
- The pair of key lists a stage declares. The runner checks required keys are present before running and that produced keys match afterwards, so a mis-ordered pipeline raises a named error instead of returning a number. It cannot protect against a declaration that is false.
- Stage ordering Day 143
- Which stage runs before which. The subject of this lesson, because leakage is usually not a mistake in reasoning but a mistake in ordering -- and ordering is exactly what a notebook does not enforce.
- staging area Day 30
- A holding area where you assemble exactly the changes to include in the next commit; git add puts changes here. Also called the index.
- Standard basis Day 102
- The particular pair e1 = (1, 0) and e2 = (0, 1) in two dimensions: one step right and one step up. Every vector (x, y) is x lots of e1 plus y lots of e2, which is what makes their landing places sufficient to describe a whole transformation. Written as e1, e2 and so on up to en in n dimensions.
- standard error Day 10
- A second output stream (stderr, file descriptor 2) reserved for error and diagnostic messages, kept separate from standard output so errors never contaminate the data flowing through a pipe.
- Standard error Day 80
- The stream carrying DIAGNOSTICS: progress notes, warnings, error messages. Keeping it separate from standard output is what lets `mytool > results.json` produce a clean file while the tool chatters on screen, and what stops an error message from being fed to a downstream program as if it were data.
- Standard error Day 114
- The standard deviation of a sampling statistic itself — for a sample mean, sqrt(variance / n). It is the quantity every tolerance in this lesson's lab is derived from, rather than guessed: a simulated value is expected to land within about three standard errors of the true value on roughly 99.7% of runs.
- Standard error Day 117
- The standard deviation of a statistic's own sampling distribution -- how much the statistic itself wobbles from sample to sample. For the sample mean, the standard error equals sigma / sqrt(n), where sigma is the population's standard deviation. Not the same quantity as the population's own standard deviation, which describes individual observations rather than the average of several of them.
- Standard error of a proportion Day 113
- sqrt(p(1-p)/n), the typical size of the gap between a Monte Carlo estimate and the true probability it estimates, for n independent trials. This lesson derives simulation tolerances from this formula rather than choosing a number that happens to make a test pass — three standard errors is the band inside which about 99.7% of honest simulation runs should land.
- Standard error of a slope Day 148
- How much a fitted slope would wobble under a fresh sample of the same size, computed from the residual variance and the spread of the predictor. Measured at 0.6738 for the BMI slope, giving a 95% confidence interval of [8.9125, 11.5538].
- Standard error of an accuracy Day 144
- sqrt(p times one minus p, divided by n) -- how much an accuracy estimate wobbles from the split alone. 0.0224 on 500 rows at p = 0.5. Theory matched 20000 measured draws to four decimal places at every size tried.
- standard input Day 10
- The default stream (stdin, file descriptor 0) a program reads from — the keyboard by default, or a file or pipe when redirected.
- Standard input Day 80
- The stream a value can arrive on from another program instead of from the command line. By a convention older than Python, an argument of a lone `-` means "read this from standard input" — which is how a tool joins a pipeline, and also how a secret is kept out of the process list and the shell history.
- standard library Day 43
- The large set of modules that ships with Python itself, available without installing anything from PyPI.
- standard library Day 60
- The large collection of modules distributed with the Python interpreter itself, available with a simple import and no installation — the "batteries included" that let a great deal of everyday work happen with nothing to download.
- standard output Day 10
- The default stream (stdout, file descriptor 1) a program writes its results to — the terminal by default, or a file or the next command in a pipe when redirected.
- Standard output Day 80
- The stream carrying the program's RESULT — the thing the caller actually wanted. Redirected by `>` and consumed by the next program in a pipeline, which is why nothing but the result may go here.
- Standardisation Day 107
- Subtracting a column mean and dividing by that column standard deviation, so every column ends with mean 0 and standard deviation 1. Also called the z-score. It exists because distances sum contributions across features and nothing in that sum knows what units the features are in: with bore diameter in metres against mass in grams, the bore column contributes 0.0036 per cent of every distance and the ranking is decided by mass alone. Two details matter in practice. Use the population divisor n, which is what numpy.std and scikit-learn StandardScaler both use. And standardise a query with the catalogue statistics rather than its own, since a single row standardised against itself is a row of zeros.
- Standardisation (z-score) Day 116
- (x - mean) / standard deviation, applied to every value in a dataset, producing a new dataset with mean exactly 0 and standard deviation exactly 1. Standardising does not change the Pearson correlation between two variables, because correlation depends only on relative structure, which a uniform rescaling cannot alter.
- Standardization Day 151
- Rescaling each feature to zero mean and unit variance (StandardScaler), the ordinary fix for scale-dependence. Not the same convention scikit-learn's own load_diabetes(scaled=True) uses -- that dataset is unit-L2-norm scaled instead, and the two conventions select different feature sets at the same nominal alpha.
- StandardScaler (Z-Score) Day 170
- A transformation z = (x - mu) / sigma that centers data to zero mean and scales to unit variance.
- Startup validation Day 97
- Checking every configuration value before any work begins, so that a bad value fails when somebody deployed it rather than at 03:00 when the code path is finally reached. Two design decisions go with it: report every problem at once, because fixing configuration one error per run pushes people towards guessing; and name the provenance in each message, because that is what turns "what is wrong" into "where to fix it".
- State file Day 84
- The durable record of what an automation has already processed, read at the start of every run and written at the end. It is what makes idempotence possible, which makes it the most valuable file the tool owns: losing a cache costs time, while losing state costs correctness, because the next run cannot tell what it has already done.
- state machine Day 65
- A parser design that holds one piece of state — here, which of four quoting states it is in — and decides what to do with each character based on it. It is what makes correct CSV parsing possible and hand-rolled splitting impossible.
- state_dict Day 204
- A Python dictionary mapping layer names to their corresponding parameter and persistent buffer tensors.
- state_dict Day 210
- A Python dictionary mapping each layer parameter and buffer tensor to its corresponding PyTorch Tensor values.
- stateless Day 18
- The property that each HTTP request is self-contained and the server keeps no memory of a client between requests, which is what lets many identical servers share the load.
- stateless Day 23
- A design in which each request carries everything the server needs and the server keeps no memory of the client between requests, so any request can be handled by any server copy.
- static analysis Day 37
- Examining a program by reading its source code while it sits still on disk — without executing it — to find problems; the opposite of dynamic analysis, which observes a running program.
- Static analysis Day 76
- Examining a program without executing it. Linters, formatters and type checkers are all static; a test suite is not. The trade is exact: static tools are fast and safe to run on every keystroke, and they are blind to anything that is only knowable at runtime.
- static type checker Day 69
- A separate program that reads your source without executing it, models every annotation, and reports where an expression contradicts what the annotations promise. mypy and pyright are the two mainstream ones; both are free and open source. The clerk who reads the filled form before it is filed.
- static typing Day 44
- The alternative approach, used by languages like Java, where a variable's type is declared in advance and checked before the program runs.
- static typing Day 75
- Checking that values flow where their declared types allow, before the program runs, by reading the source rather than executing it. "Static" is the whole point: the analysis happens on the text, so it reaches every path in the file, including the ones no test walks and the one that would have crashed in production.
- staticmethod Day 67
- A function stored on a class that receives neither `self` nor `cls`. It belongs with the class conceptually — a validation rule, a unit conversion — rather than needing any particular object.
- Stationarity Day 192
- A property of a time series where statistical properties (mean, variance, autocorrelation) remain constant over time.
- Stationary point Day 108
- A point where the derivative is zero: the graph is momentarily flat. A minimum, a maximum and a horizontal inflection are all stationary points, and the first derivative cannot tell them apart, because it reports the same zero at all three. Finding a stationary point means finding a candidate, not finding an answer.
- Stationary point Day 109
- A point where the gradient is the zero vector — Wikipedia names it as such. The ground is level in every direction to first order. The gradient carries no information at all about what KIND of point it is: a minimum, a maximum and a saddle all produce the identical zero vector, and no amount of extra precision would separate them, because the distinguishing information lives in the second derivatives rather than the first.
- Statistical efficiency Day 149
- How small an unbiased estimator's variance is, relative to alternatives. Measured here as the ratio of two standard deviations across 500 replications: 0.9524 in OLS's favour under Gaussian errors, 1.3957 in Huber's favour under heavy-tailed errors.
- Statistical power Day 118
- The probability of correctly rejecting a false null hypothesis of a given true effect size -- 1 minus beta. Depends jointly on the true effect size, the sample size, and alpha; this lesson measured power rising monotonically with both n and effect size and confirmed a closed-form formula against a direct simulation to within 0.002.
- Statistical versus practical significance Day 119
- Statistical significance answers whether an effect is distinguishable from noise; practical significance asks whether an effect, once distinguished from noise, is large enough to be worth the cost of shipping and maintaining it. A confidence interval that excludes zero but spans only a trivially small range can be statistically significant and not practically worth acting on.
- statistics Day 60
- The standard-library module for basic descriptive statistics over plain Python data: statistics.mean, median, and stdev summarise a list of numbers without needing NumPy for small, everyday summaries.
- status code Day 18
- A three-digit number in the response that summarizes the outcome; its first digit sorts it into a class (1xx informational, 2xx success, 3xx redirection, 4xx client error, 5xx server error).
- status code Day 21
- A three-digit number in an HTTP response signalling the outcome: 2xx success, 3xx redirection, 4xx a client (request) error, and 5xx a server error.
- status code Day 82
- The three-digit result of a request, and the part of the answer a machine reads first. 200 here-it-is, 201 I-made-it (with a `Location` header), 204 done-and-nothing-to-say (with an empty body), 404 no-such-thing, 422 your-fields-are-wrong, 500 I-broke. The 4xx-versus-5xx line decides whose mistake it was, and getting it backwards ruins every dashboard you will ever build.
- Status code Day 78
- The three-digit machine-readable verdict on a request. The first digit gives the family: 1xx informational, 2xx it worked, 3xx look elsewhere, 4xx you were wrong, 5xx they were wrong. A response arriving at all is a success at the transport layer, which is why a 500 raises no exception in requests.
- stderr Day 47
- Standard error (file descriptor 2), a second output stream reserved for messages about the run — errors, warnings, progress — kept separate so they do not contaminate the data on standard output.
- stdin Day 47
- Standard input (file descriptor 0), the stream a program reads from; it may be a keyboard or, in a pipeline, the output of an upstream program.
- stdout Day 47
- Standard output (file descriptor 1), the stream a program writes its results to and the channel that feeds the next program in a shell pipeline.
- stdout / stderr Day 56
- The two output streams of a command-line program: standard output (stdout) carries results meant to be read or piped onward, and standard error (stderr) carries diagnostics and error messages, kept separate so piped results stay clean.
- Steepest ascent Day 109
- The direction in which a function increases fastest from a point, which is the direction of its gradient. It follows from the geometric dot product: D_u f = |∇f| cos θ, cosine cannot exceed 1, and it reaches 1 exactly when the direction is the gradient's. The largest available rate is therefore |∇f| and the most negative is −|∇f|, attained by walking exactly the opposite way — which is gradient descent. The property requires the function to be DIFFERENTIABLE, not merely to have partial derivatives; Wikipedia gives a function whose partials all exist at the origin and whose gradient formula nonetheless "fails to point towards the steepest ascent in some orientations" there.
- step into Day 37
- A debugger command that descends into a function being called so you can watch its inner lines execute one at a time; its counterpart, step out, finishes the current function and returns to its caller.
- step log Day 126
- A record, built while a pipeline runs, of each step's name, rows in, rows out, and the net change. Read after the fact, it is how a silently row-dropping step is discovered rather than guessed at -- the reconciliation habit from groupby (Day 123) generalised to a whole pipeline.
- Step log Day 143
- The ordered record of which stage produced which keys. It records what happened rather than what was intended, which is why it is evidence rather than documentation.
- step over Day 37
- A debugger command that runs the next line and stops again, treating any function call on that line as a single step rather than descending into it.
- StepLR Day 207
- A scheduler that reduces the learning rate by a multiplicative factor gamma every step_size epochs.
- Stochastic Gradient Boosting Day 164
- An extension where a random subsample of training instances (and/or features) is drawn without replacement at each iteration to compute pseudo-residuals.
- StopIteration Day 55
- The exception an iterator raises when it has no more items. A `for` loop catches it silently as its signal to stop; you also see it when calling `next()` past the end by hand.
- Stopping criterion Day 111
- A rule that decides when to stop a gradient-descent loop: the gradient's norm falling below a tolerance, the change in loss between steps falling below a tolerance, or a maximum number of iterations. The first is the most honest; the second can fire early on a shallow, unsolved part of a landscape, mistaking a slow approach for arrival.
- Stopping rule Day 136
- A rule, decided in advance, for when exploration ends -- for example a fixed time budget or a fixed count of questions. A stopping rule that depends on what has been found so far ("stop when significant") inflates the true false-positive rate well above the nominal alpha.
- Storage class Day 85
- What a value in SQLite actually is, as opposed to what its column asked for. There are five: NULL, INTEGER, REAL, TEXT and BLOB. The typeof() function reports the storage class, which is the tool for diagnosing a query that silently returns fewer rows than you expect.
- Storytelling versus neutrality Day 132
- The distinction that an unlabelled, unordered, uncommented chart is not a neutral presentation of facts but an unhelpful one. It makes no claim, so a reader cannot disagree with it, and whatever they conclude is an accident. Ordering, annotation, emphasis through contrast and the removal of uninformative marks are craft in service of honesty, not opposed to it.
- str Day 44
- The string type: text as a sequence of characters, such as "hello". Immutable, so "changing" a string produces a new object.
- str dtype (pandas 3.0) Day 120
- The default dtype pandas 3.0 assigns to a column built from Python strings, backed by PyArrow's contiguous string storage. It replaces object as the default; object remains available on request and is still what a genuinely mixed-type column falls back to.
- Stratified 3-Way Split Day 161
- Partitioning a dataset into Train (60%), Validation (20%), and Test (20%) subsets while preserving exact class prevalence across all three splits.
- Stratified K-Fold Day 160
- A cross-validation splitting scheme that ensures each fold contains approximately the same percentage of samples of each target class as the complete dataset.
- Stratified K-Fold Day 167
- A cross-validation variation where folds are selected so that the mean target value (or class proportion) is approximately equal across all folds.
- Stratified split Day 144
- A split preserving each class's proportion in both halves. Costs nothing, has the same mean as a random split, and cuts the spread by a factor of 2.65 here -- while never once producing the empty test half a random split produced 21 times in 500.
- Streaming response Day 78
- Consuming a response body incrementally rather than loading it all at once. In requests, stream=True returns as soon as the headers arrive and iter_content pulls the body a chunk at a time, so a four-gigabyte download needs one chunk of memory rather than four gigabytes. It is also how token-by-token model output reaches a screen.
- strict mode Day 12
- The convention of putting `set -euo pipefail` near the top of a script so it stops on errors, errors on unset variables, and detects failures anywhere in a pipeline.
- strict mode Day 75
- mypy's `--strict` flag, or `strict = true` in configuration — a bundle switching on roughly a dozen individual settings, including `disallow_untyped_defs` and `warn_return_any`. It is what turns "mypy found nothing" from a statement about your annotations into a statement about your code.
- Strict mode Day 94
- The opposite policy, requested per call with strict=True, per field with Field(strict=True), or per model with ConfigDict(strict=True). No conversions are attempted; a value must already be the declared type. In pydantic 2.13.4 the one exception observed is int to float, which is still accepted. Reach for it when a wrong guess is worse than a rejection — money, identifiers, anything from a source that is supposed to be well typed already.
- STRICT table Day 85
- A table declared with the STRICT keyword, added in SQLite 3.37.0, in which every column must be one of INT, INTEGER, REAL, TEXT, BLOB or ANY and the engine enforces it. It refuses values that genuinely are not the declared type; it still permits the lossless conversion, so '1970' remains acceptable in an INTEGER column.
- STRICT table Day 88
- A table declared STRICT, which enforces its column types instead of treating them as mere affinities. It converts losslessly and refuses the rest: verified here, the text 7 into an INTEGER column stores 7 and 4.0 stores 4, while banana and 3.5 are both refused. In an ordinary table a column declared INTEGER will hold the word banana quite happily.
- stride Day 104
- How many BYTES to skip to move one step along an axis. A (3, 4) array of int64 has strides (32, 8): one column across is one 8-byte element, one row down is four of them. Strides are what turn indexing into arithmetic rather than a search, and swapping two of them is all a transpose has to do — which is why a transpose copies nothing.
- Strides Day 202
- The number of memory elements in flat 1D storage that must be stepped over to advance by one position along a given tensor dimension.
- string Day 45
- A piece of text in Python: an ordered, immutable sequence of Unicode characters, written between quotes and represented by the built-in type str.
- string normalisation Day 125
- Cleaning a text column's formatting -- stripping whitespace (.str.strip()), lowercasing (.str.lower()), removing or replacing punctuation (.str.replace()) -- so that values which mean the same thing ("USA", "U.S.A.", " usa ") collapse to one canonical spelling before any groupby or value_counts() is run on the column.
- string normalisation Day 126
- Collapsing superficially different text representations of the same value (whitespace, casing, known synonyms) to one canonical form (Day 125). Whether it runs before or after deduplication changes which rows are recognised as duplicates -- this lesson's central order-dependence example.
- Stringly typed Day 70
- Using plain strings for values that belong to a closed set, such as a status, a role or a tier, so a typo is accepted where it is written and fails somewhere far away. enum.Enum makes the typo impossible.
- strip plot / swarm plot Day 129
- Plots that draw every individual observation as a point along a categorical axis (stripplot jitters points randomly to reduce overlap; swarmplot arranges them so none overlap) rather than reducing each group to a single summary statistic -- the natural counterpart to a barplot or boxplot when the sample size is small enough that individual points matter.
- Structural Risk Minimization Day 177
- An inductive principle for model selection that balances empirical risk against functional capacity bounds.
- structural typing Day 68
- Checking that an object has the right shape rather than the right ancestry — duck typing written down. Provided by `typing.Protocol` since Python 3.8, and useful precisely when you consume objects other people wrote and cannot demand they inherit from you.
- structural typing Day 75
- Deciding type compatibility by shape: if it has the right methods with the right signatures, it fits. This is duck typing with the expectation written down, and `Protocol` is its form in Python. When it fails, mypy names the specific member that conflicts and shows both signatures.
- Structured concurrency Day 96
- The principle that a concurrent task must not outlive the lexical scope that created it, so concurrency has the same block structure as ordinary control flow. asyncio.TaskGroup implements it: the async with block does not exit until every child has finished, a child that raises causes its siblings to be cancelled, and failures arrive together in an ExceptionGroup. The idea came from the trio library, where the same construct is called a nursery.
- Structured log Day 98
- A log where each line is a machine-parseable object — here one JSON object per line — rather than a sentence. The difference matters on the day you need it: a prose line has to be parsed with a regular expression that breaks the first time somebody adds a word, while a JSON line can be filtered, counted and joined. Structure also makes redaction possible in one place, because the logger can walk the values before writing them.
- structured logging Day 40
- The practice of emitting each log entry as machine-readable key-value data (usually JSON) rather than free-form prose, so its fields can be queried precisely.
- Structured logging Day 81
- Writing one machine-readable object per event — here one JSON object per line — rather than free-form prose. One line per event is what makes a log processable with grep and json.loads together; a multi-line traceback in the middle of the stream is not. Include a run id, a status, a duration, an exit code and enough domain context to answer "what did it do?" months later.
- Structured logging Day 84
- Writing log records as data with named fields rather than as lines of prose — in practice, one JSON object per line. The idea descends from syslog, written by Eric Allman in the 1980s: a record has a severity, a timestamp and fields, so it can be filtered by run and by item months later.
- Structured logging Day 97
- Emitting each event as a machine-parseable object with named fields — usually one JSON object per line — rather than as a sentence. It turns "read the log" into "query the log", which is the only thing that scales past one file on one machine. The honest cost is that JSON is unpleasant to read with your eyes, which is why the usual arrangement is JSON to the collector and a human formatter on the console: the same records, two handlers, two formatters.
- Structured output Day 94
- Asking a language model for JSON matching a schema rather than for prose. The model returns text claiming to be JSON; a parse and a validation decide whether it is usable. This is exactly the boundary problem of this lesson, with a particularly unreliable source on the other side, and it is why the retry loop that feeds the validation errors back to the model is the standard pattern rather than a hack.
- Stub Day 74
- A test double that returns canned answers and records nothing. `frozen_clock(day)` returning `lambda: day` is a complete stub in one line; most tests need nothing more.
- stub file Day 75
- A `.pyi` file containing signatures and no bodies — a header, or a data sheet for a component you cannot open. Stubs describe the types of code the checker cannot otherwise read, and are distributed either inside a package or as a separate stub-only package.
- Student-t Distribution Day 186
- A heavy-tailed probability distribution (Cauchy distribution with 1 dof) used by t-SNE in the embedding space to alleviate crowding.
- Study Day 140
- As this lesson uses the word: a directory containing a written question, the data that answers it, a record of everything done to that data, the answer with its uncertainty, and an honest statement of what the answer cannot support. Distinct from a notebook (a medium), a dashboard (a repeated answer) and a model (a prediction).
- Sturges' rule Day 130
- A bin-count rule based only on the sample size n, choosing roughly log2(n) + 1 bins. It assumes the data is close to normally distributed and tends to under-bin skewed or heavy-tailed data, but is matplotlib's and NumPy's default because it is cheap and rarely produces an unreasonable-looking chart on well-behaved data.
- style guide Day 61
- A shared set of conventions for how code should look and be organised, so a team's code reads as if one careful person wrote it. For Python the canonical style guide is PEP 8.
- Style guide Day 76
- A written document stating how code in a language or a project should be laid out and named. It is written for humans, contains judgement calls, and cannot be executed. A formatter implements one specific consistent interpretation of a subset of a style guide; the two are not substitutes.
- subcommand Day 56
- A named group of arguments that selects one of several operations a tool offers, created with argparse's add_subparsers — for example the add, list, find, and delete in `records.py add ...`, much like `git commit` and `git push`.
- Subcommand Day 80
- A first positional argument that selects an entire second interface, as in `git commit` versus `git log`. Built with `add_subparsers` and `add_parser`, and the way any tool with more than about three verbs stays comprehensible.
- Subgroup Fairness Day 161
- Evaluating model performance (Precision, Recall, False Positive Rate) across demographic or operational subgroups to ensure equitable outcomes.
- subnet Day 16
- A contiguous block of addresses that share a leading prefix and are treated as one local network.
- subplots grid Day 128
- The array of Axes objects plt.subplots(nrows, ncols) returns when either dimension exceeds 1 -- a genuine 2-D numpy array shaped (nrows, ncols), not a flat list. Each entry is a fully independent Axes: setting a label on axes[0, 0] never touches axes[0, 1].
- subset duplicate Day 125
- A row that matches another row only on a NAMED subset of columns, detected by DataFrame.duplicated(subset=[...]), even if the two rows differ elsewhere. Which definition is "correct" depends entirely on the question being asked, not on a universal notion of duplication.
- subshell Day 11
- A child shell created by wrapping commands in parentheses; variables it sets and exports affect only itself and vanish when it exits, leaving the parent environment untouched.
- Successive Halving Day 166
- An early-stopping resource allocation algorithm that trains a pool of configurations on minimal resources, progressively pruning the bottom half and promoting top candidates.
- suffixes Day 124
- A merge() keyword controlling what gets appended to a non-key column name that appears in both input frames. Defaults to ("_x", "_y"), which is how an uninformative column name like price_x ends up in a merged result unless suffixes= is passed explicitly.
- super() Day 68
- A call that dispatches to the NEXT class in this instance's MRO — which under multiple inheritance is often not the parent you would guess, and may be a class the current one does not inherit from at all. Conventionally called first inside a subclass ``__init__``.
- Supervised learning Day 142
- The setting in which every input arrives with its correct output attached. Defined by the information available, not by the algorithm used -- a neural network, a decision tree and a nearest-neighbour lookup are all supervised when handed labelled pairs.
- Support Vector Machine (SVM) Day 169
- A supervised learning model that finds the optimal maximum-margin hyperplane separating classes in feature space.
- Support Vectors Day 169
- The critical training instances that lie on the margin boundary or violate the margin, possessing non-zero Lagrange multipliers (alpha_i > 0).
- Suppression comment Day 76
- A comment that tells the linter to be quiet about one line, written `# noqa: F401 — reason`. Naming the code and the reason lets a reviewer check it in five seconds. A bare `# noqa` silences every rule on that line forever, including rules that did not exist when it was written and including security rules; Ruff's `PGH004` flags those and `RUF100` flags suppressions that no longer suppress anything.
- Surface Day 109
- The graph of a function of two variables, drawn as a landscape in three dimensions with the function's value as height. Wikipedia's article on partial derivatives describes the geometry precisely: at every point on such a surface there are infinitely many tangent lines, and "partial differentiation is the act of choosing one of these lines and finding its slope" — usually the ones parallel to the xz-plane and the yz-plane, which is what freezing y or x respectively produces. Beyond two inputs the surface stops being drawable, which is why the two-input picture is worth learning properly.
- Surrogate key Day 91
- A primary key the database made up, carrying no meaning in the world — usually an integer. Chosen because it never changes, is never absent, and is never mistyped. In SQLite an INTEGER PRIMARY KEY is an alias for the internal rowid, so it costs nothing in storage.
- Surrogate Model Day 166
- A computationally cheap probabilistic approximation (e.g. Gaussian Process, Tree-structured Parzen Estimator) of the true expensive objective function.
- SVD-based solve Day 153
- A least-squares solution method built on the singular value decomposition, which sklearn's default LinearRegression uses. Directly exposes a matrix's small singular values, letting it return the minimum-norm answer on near-collinear data rather than the exploded answer the normal equations and a naive lstsq both fall into on the most extreme cases.
- swallowing Day 66
- Catching an exception and doing nothing useful with it, classically "except Exception: pass". It guarantees the program never crashes and guarantees it never tells you anything, which is how a pipeline reports success while producing half a dataset.
- swap Day 3
- Disk space the OS uses to hold memory pages evicted from full RAM; heavy, sustained swapping (thrashing) makes a machine crawl because disk is thousands of times slower than RAM.
- switch Day 31
- The modern Git command (added in version 2.23) for moving between branches: git switch NAME to switch, git switch -c NAME to create and switch.
- Switch interval Day 96
- How long CPython lets a thread run before considering handing execution to another, controlled by sys.setswitchinterval and defaulting to 0.005 seconds. It is process-wide, so anything that changes it must restore it in a finally block. This lesson lowers it to 1 microsecond in order to make a latent lost-update race land on every run rather than once in a very long while — a diagnostic technique, not a fix, and one that changes nothing about the buggy code itself.
- symbolic link Day 9
- A small special file that points at another path, so following it reaches the target; proof that a path is a name for a file rather than the file itself.
- symmetric difference Day 54
- The set operation `a ^ b` that returns the items in exactly one of the two sets, excluding those in both — e.g. `{1, 2, 3} ^ {2, 3, 4}` is `{1, 4}`.
- symmetric key Day 19
- A single shared secret key used to both encrypt and decrypt messages; fast, but both sides must already share the same key.
- Symmetric matrix Day 100
- A matrix equal to its own transpose, so entry (i, j) always equals entry (j, i). Only a square matrix can be symmetric. It means the relationship from i to j is the same as from j to i, which is why distance matrices, similarity matrices, covariance matrices and undirected graphs are symmetric — and why an attention score table, where token i attending to token j is not the same as the reverse, generally is not.
- Symmetric matrix Day 106
- A square matrix equal to its own transpose, so entry (i, j) always matches entry (j, i). Two guarantees follow, both standard results proved in any linear algebra text and cited rather than proved in this lesson: all its eigenvalues are REAL, and its eigenvectors are ORTHOGONAL. Cauchy proved the real-eigenvalue result in the 1820s while studying the principal axes of quadric surfaces. This is not a niche case — a covariance matrix, a Gram matrix, a correlation matrix and a graph Laplacian are all symmetric by construction, which is precisely why PCA never returns a complex answer you have to interpret and why its components always come out perpendicular. It is also why numpy.linalg.eigh exists and is roughly ten times faster than eig on such input.
- Symmetry Breaking Day 201
- Initializing weights with random non-zero values so that individual neurons in a hidden layer compute different functions and learn distinct features.
- syntax highlighting Day 36
- Coloring the different parts of code — keywords, strings, comments — differently so the structure of the code is easy to see at a glance; a display effect that never changes the file on disk.
- SyntaxError Day 48
- An error raised when Python cannot parse your code because it is not valid Python; it stops the program from starting at all.
- sys.argv Day 47
- A list of the command-line arguments passed to a program, as strings; sys.argv[0] is the script name and the real arguments begin at index 1.
- sys.path Day 59
- The ordered list of directories Python searches to find a module to import. For a `python3 -m` run the current directory comes first, followed by the standard library and installed-package locations; Python imports the first match it finds, which is why file names can shadow standard-library modules.
- system call Day 6
- The controlled doorway through which a user-space program asks the kernel for a service such as opening a file, allocating memory, or sending a network packet.
- systemd timer Day 14
- A scheduling unit on most Linux distributions that runs a paired service on a schedule, managed and logged like any other systemd service.
- systemd timer Day 81
- A Linux .timer unit that activates a .service unit at a time given by OnCalendar. Splitting when from what buys journal logging, catch-up with Persistent=true, dependency ordering with After=, an enforced TimeoutStartSec, free overlap protection, and the ability to run the job by hand exactly as the timer would.
- t-SNE Day 186
- t-Distributed Stochastic Neighbor Embedding: a non-linear probabilistic technique for embedding high-dimensional data in 2D or 3D.
- tab completion Day 8
- A shell feature that finishes a partly typed command or filename when you press the Tab key, or lists the choices if several match, saving keystrokes and preventing typos.
- Table rebuild Day 88
- The documented SQLite procedure for any schema change ALTER TABLE cannot make: create the table you wanted, copy the rows, drop the old table, rename the new one into place — all in one transaction, with foreign keys off around it and PRAGMA foreign_key_check afterwards. The definition must be retyped in full, because whatever you omit is silently dropped without an error.
- Table scan Day 89
- Reading every page of a table and testing every row, because there is no ordered structure that says where the matches might be. SQLite calls it SCAN in a query plan. Its cost grows in proportion to the table, for ever: measured here at 0.31 ms over 25,000 rows and 8.41 ms over 400,000.
- Tabular Data Day 168
- Structured data organized in rows (records) and columns (features) with heterogeneous data types, representing the dominant data modality in business and industry.
- tag Day 35
- A fixed name pinned to one specific commit that never moves, used to mark releases; contrast with a branch, which advances with each new commit.
- tail call Day 62
- A recursive call that is the very last action a function performs before returning. Some languages optimize tail calls into a loop so they use constant stack space; Python deliberately does not (no tail-call optimization), which is why deep recursion in Python can raise RecursionError where an equivalent loop would not.
- Tangent line Day 108
- The line the secants approach as the interval shrinks to nothing, and the line whose slope is the derivative. It is not "the line that touches the curve at exactly one point": plenty of lines do that without being tangents, and a tangent may cross its curve elsewhere. For y = x² at x = 3 the tangent is y = 6x − 9. The useful reading is that the tangent is the best straight-line approximation to the curve near that point.
- target encoding Day 137
- Replacing a category with the mean outcome for that category. Compact for high-cardinality columns and the subtlest way to leak in this lesson, because it reads the target: computed before the split, every test row's feature value is computed partly from its own answer. Usually credited to Micci-Barreca's 2001 SIGKDD Explorations paper, which prescribes smoothing towards the global mean for small categories.
- Target Encoding Day 170
- A categorical encoding method that replaces each category with the average target value of that category, regularized by global Bayesian smoothing.
- Target function Day 141
- The function you wish you had, mapping inputs to correct outputs. You never have it. What you have is a sample of its behaviour, possibly with errors in the recorded outputs, and the model is your best approximation of it from that sample.
- target leakage Day 137
- A feature that encodes the outcome, directly or by proxy. In this lesson's lab, days_to_first_invoice is -1 for every unconverted row and a positive number for every converted one, because an invoice cannot exist before a conversion. It takes the model from 0.64 to 1.00. This kind hides in the column list, and the question that finds it is "when is this value written?".
- Target Leakage Day 180
- Including features that are updated or created as a consequence of the target event having occurred.
- Task Day 96
- A coroutine that the event loop has taken responsibility for running, created with asyncio.create_task or TaskGroup.create_task. Creating one SCHEDULES it; it does not start it. Nothing on a loop starts until the currently running coroutine gives the thread back at an await — a subtlety that produces silent no-op bugs, since unlike a forgotten await there is no warning for it.
- task runner Day 41
- A tool such as make that gives project tasks memorable names and declares their order, so a hook, a CI job, and a developer can all invoke the same steps.
- Task Scheduler Day 14
- The built-in scheduler on Microsoft Windows, used through its graphical tool or commands like schtasks to run programs at set times.
- TCP Day 15
- The Transmission Control Protocol, which delivers a reliable, ordered stream of bytes between two programs, retransmitting anything lost.
- TCP Day 17
- Transmission Control Protocol: a connection-oriented transport that guarantees data arrives complete, in order, by numbering bytes, acknowledging them, and retransmitting anything lost.
- Teardown Day 72
- Cleanup that runs after a test: closing a handle, removing a directory, restoring a setting. In pytest it is the code after a fixture's yield, and pytest runs it whether the test passed, failed, or raised — which is precisely what cleanup at the end of a test body cannot promise.
- Technical debt Day 77
- The accumulated cost of decisions that made a change quick at the time and make every later change slower. A gate does not repay technical debt; it stops new debt being added silently, which is what the ratchet strategy exploits when adopting a gate in an existing messy codebase.
- template method Day 68
- The shape where a concrete method in a base class calls an abstract one that subclasses fill in — the framework calls your code rather than the other way round. It is exactly how a PyTorch `nn.Module` calls the `forward` you wrote.
- temporal leakage Day 137
- Using information from after the prediction moment. It hides in the split itself: a random split scatters every period into both halves, so the model learns each period's behaviour from rows recorded at the same time as the ones it is scored on. Measured here, 0.8833 under a random split and 0.0667 under a time-ordered one, where the majority-class baseline for that period was 0.9333.
- Temporal leakage Day 95
- The failure mode where information from after a prediction's cutoff reaches the features used to make it, so an evaluation reports a score the model cannot reproduce in production. A time-zone bug is one of its quietest causes: a split at "midnight local" against timestamps recorded in another zone moves hours of the future into the past, and the resulting model looks excellent and is worthless.
- Tensor Day 100
- In machine-learning code, an array with any number of dimensions: a scalar is 0-dimensional, a vector 1-dimensional, a matrix 2-dimensional, and a batch of colour images 4-dimensional. This is the usage in PyTorch and everything downstream of it. In mathematics and physics the word is stricter, describing how the object behaves under a change of coordinates, and a matrix is not automatically a tensor in that sense. Both usages are correct in their own fields.
- terminal Day 8
- The text-based interface for typing commands to a computer and reading their text output; historically a separate device at the end of a wire, today usually a software window.
- Terminal detection Day 80
- Asking, with `isatty()`, whether a stream is connected to a terminal or to a pipe or file. Checking it on standard input before reading is what stops `mytool add -` from silently hanging forever when nothing was piped in; checking it on standard output is how tools decide whether to emit colour.
- terminal emulator Day 8
- The application that opens a window, displays text, and forwards your keystrokes to the shell — a program that behaves like the old physical terminal hardware it is named after.
- Terms of service Day 79
- The prose conditions under which a site permits use, frequently addressing automated access explicitly. They are a contract question rather than a technical one: no library can read them for you, they live in a different place from robots.txt, and honouring one document says nothing about the other.
- Test Day 71
- A small program that runs another program and complains if the answer is wrong. It has three parts in a fixed order — arrange the inputs, act by calling the code, assert what must be true — and its result is a fact a machine can read, not an opinion.
- test command Day 12
- The `[ ... ]` (also spelled `test`) or the bash-only `[[ ... ]]` construct that evaluates a condition, such as `-d` for "is a directory", and returns an exit code.
- Test double Day 71
- A stand-in object used in place of a real dependency so that a test stays fast and deterministic — a stub returning a canned answer, a fake with a simple working implementation, a mock that also records how it was called. The technique that makes non-deterministic boundaries such as a network call or a model API testable. The subject of Day 74.
- Test double Day 74
- Any object substituted for a real dependency during a test. The umbrella term was coined by Gerard Meszaros in xUnit Test Patterns (2007), explicitly by analogy with a stunt double, because "mock" had already been claimed for something narrower.
- Test id Day 71
- The `path::Class::name` string that identifies one collected test, such as `test_textstats.py::TestTopWords::test_returns_exactly_n_items`. It appears in verbose output and in the short test summary, and it can be pasted back onto the command line to run exactly that test.
- Test id Day 72
- The name pytest gives a collected test item — the file, the function, and for a parametrized case a label in square brackets, as in test_refuses_a_bad_value[minutes-zero]. Ids are what -k matches against and what a failure report names, which is why hand-written ids= labels are worth the typing.
- Test independence Day 72
- The property that every test gives the same answer whether it runs alone, first, last, or in a shuffled order. It is violated almost entirely by accident, through shared mutable state introduced to make a suite faster. Suppressing an order-shuffling plugin because it turns the suite red hides the defect rather than fixing it.
- Test pyramid Day 72
- Mike Cohn's 2009 model of a suite: many fast unit tests at the base, fewer service tests above, very few slow end-to-end tests at the top. Its economics are real and its shape is contested — critics note that all-green unit tests can sit on top of broken wiring, and that cheap in-memory integration tests justify a much fatter middle layer.
- Test R2 Day 152
- R-squared measured on data the model was not fit on -- the honest number, as opposed to training R2, which climbs mechanically as predictors are added. Measured here at 0.3594 for the full ten-feature diabetes model, unaffected by whether the model was fit on raw or standardised features.
- Test runner Day 71
- A program that discovers tests by name, imports and executes them, records each outcome, prints a report, and exits with a status code describing the whole run. pytest, `unittest` and `doctest` are all runners; a plain script full of asserts is a minimal one.
- Test set Day 144
- The rows that tell you what you will actually get. Exactly one look. Its entire value comes from never having influenced anything, so the second evaluation is a validation score wearing the word test.
- Test-after Day 73
- Writing the code first and the tests afterwards — the most common practice in the industry, and not a sin. It is only honest when it includes the extra step test-first gets for free: break the code on purpose, watch the new test go red, and put the code back.
- Test-driven development Day 73
- The practice of writing a small failing test for each behaviour before writing the code that provides it, and letting the implementation grow only in response to a test that is currently red. It is a design technique whose by-product is a test suite, not a testing technique that happens to affect design.
- Test-set sizing Day 144
- Deciding how many test rows you need from the smallest difference that would change a decision, before splitting. 1225 rows for plus or minus 0.02 at an accuracy of 0.85; 4899 for plus or minus 0.01.
- Test/interval duality Day 118
- The exact equivalence between a two-sided hypothesis test at level alpha and a (1 - alpha) confidence interval: the test rejects a null value precisely when the interval excludes it. This lesson confirmed zero disagreements across 2,000 simulated datasets, because both are built from the identical standardized statistic.
- testability Day 63
- How easily a piece of code can be checked automatically. Pure functions are highly testable — a single call and an assertion suffice — which is the practical reason for keeping logic in a functional core and I/O in a thin shell.
- TestClient Day 82
- FastAPI's in-process client, built on httpx, which hands a request straight to the application object in the same process. No port, no readiness wait, no shutdown handling, no socket — while routing, dependencies, validation, the handler and serialization all run exactly as in production. The only thing it cannot exercise is the wire itself.
- TF-IDF Day 158
- Term Frequency-Inverse Document Frequency: a numerical statistic reflecting how important a word is to a document in a collection or corpus.
- The -> and ->> operators Day 92
- SQLite's shorthand for reaching into JSON, added in release 3.38.0 in February 2022 alongside making the JSON functions built-in, and deliberately compatible with MySQL and PostgreSQL. The arrow returns JSON, so a number comes back as JSON text and a string stays quoted; the double arrow returns a typed SQL value. Use the double arrow when you want to compare, sort or aggregate.
- the "so what" test Day 133
- The question asked of every section and every figure before it is allowed into a report: if this were deleted, would the decision change? Not "is it interesting" -- everything you looked at is interesting to you -- and not "is it correct", which is the entry price. Most sections fail, and failing is the normal outcome rather than a sign of poor work.
- The bias-variance decomposition Day 145
- The identity that expected squared error equals bias squared plus variance plus irreducible noise. Not a metaphor: the lab checks the sum against the error actually observed and finds agreement to within one percent at every capacity.
- The Crowding Problem Day 186
- The mismatch in geometric volume between high and low dimensions that causes moderate-distance points to collapse into a crowded center.
- The empty-string distinction Day 97
- A variable that was never set and one that was set to "" are different states, and os.environ.get collapses them — None and "" both fall to the default under the usual `or default` idiom. Ask `"NAME" in environ` instead. It matters because an empty variable is almost never an accident: it is a deployment template that filled in nothing, a secret injection that failed, or somebody who meant to clear a value.
- the grain trap Day 135
- The specific failure of flattening a nested payload to a finer grain than a question needs, and then aggregating a field that belongs to the coarser grain. On this lesson's example, summing total_amount_due on an order-grain frame (six rows) counts a two-order customer's balance twice, inflating a true total of 1550.0 to 2650.0.
- The i.i.d. assumption Day 141
- Short for independent and identically distributed: the assumption that future inputs are drawn from the same distribution as the training data, each drawn independently. Every claim a trained model makes rests on it, it is frequently false in production, and its failure is silent -- nothing errors and nothing alerts.
- The margin Day 154
- The improvement of a winning model's test RMSE over the baseline RMSE. Here, 70.4637 minus 56.5566 equals 13.9071 RMSE points -- the number a bootstrap interval is computed around, not trusted on its own.
- The one-way gate Day 143
- The test set. Everything before it loops; it is crossed once, at the end, after the looping has stopped. Cross it twice and it becomes another validation set and stops estimating anything.
- The one-word veto Day 115
- The failure mode Laplace smoothing exists to prevent: without smoothing, a single word with zero training-count in a class gives that class a probability of exactly 0, and multiplying by zero erases every other word's evidence for that class, regardless of how strongly the rest of the document points toward it.
- The rule test Day 141
- The first question to ask of any candidate machine learning problem: can the correct answer be computed by a rule you can write down? If it can, write the rule. A rule is exactly correct, needs no labels, never drifts, costs nothing to run and can be reviewed by someone who is not you -- and in this lesson a three-line rule scores 1.000 where the best trained model reaches 0.9675.
- The sqrt(n) law Day 117
- The consequence of the standard error formula that quadrupling the sample size roughly halves the standard error, not quarters it. Measured directly across four sample sizes each 4x the last (10, 40, 160, 640), the ratios came out to 1.985, 1.991 and 2.011, against a predicted 2.0 at every step.
- the stack Day 42
- The layered set of technologies an action passes through, from your keyboard down through the machine, out across the network, into an API, and back — understood here as one connected whole rather than separate topics.
- The two-level rule Day 97
- A record must pass the LOGGER's level and then EACH HANDLER's level, and they belong to two different objects. A logger at DEBUG whose handler is at WARNING emits no debug output and raises no error. This is the single most common logging question there is, and the silence is deliberate: a logging call that raised would take the program down at the worst possible moment.
- Theoretical Initial Loss Day 209
- The expected cross-entropy loss value under uniform random guessing: -ln(1/K) for K balanced classes.
- thread Day 7
- An independent stream of instructions inside a process, with its own program counter and stack but sharing the process's memory and file handles with its sibling threads.
- Thread Day 96
- An independent sequence of execution inside one process, scheduled preemptively by the operating system, which may interrupt it between any two bytecodes. Threads in a process share all memory — the same objects, the same module globals — which is what makes them cheap and what makes every shared mutation something you must reason about. In CPython they overlap WAITING perfectly and cannot overlap Python bytecode execution.
- Three-valued logic Day 86
- SQL has TRUE, FALSE and UNKNOWN rather than two truth values, because any comparison involving NULL yields UNKNOWN. It is not arbitrary: an expression gets a definite answer exactly when that answer would hold for every value the missing operand could have. So NULL AND 0 is FALSE and NULL OR 1 is TRUE, while NULL AND 1, NULL OR 0 and NOT NULL are all UNKNOWN.
- three-way handshake Day 17
- The SYN, SYN-ACK, ACK exchange TCP performs before sending data, so both sides confirm they are ready and agree on starting sequence numbers.
- three-way merge Day 31
- A merge that combines two diverged branches using their common ancestor (the merge base) plus both branch tips, producing a merge commit with two parents.
- Threshold Calibration Day 161
- The empirical tuning of decision threshold tau on validation data to minimize business-specific asymmetric cost functions.
- tie-break Day 126
- A secondary sort key named explicitly to give rows with an equal primary-sort value a deterministic relative order, independent of the order they happened to arrive in. Without one, a "stable" sort merely preserves arrival order, which is not the same thing as a deterministic order across two independently built frames.
- Tikhonov regularization Day 151
- The general mathematical technique -- adding a stabilizing penalty term to an ill-posed problem -- introduced by Andrey Tikhonov, of which ridge regression is the linear-regression special case, named and popularized in statistics by Hoerl and Kennard's 1970 paper.
- Time Series Forecasting Day 192
- The process of analyzing historical sequential data to predict future values across a specified temporal horizon.
- Time Series Split (Rolling-Origin) Day 167
- A temporal cross-validation scheme where training observations strictly precede validation observations in chronological order, typically via expanding windows.
- time slice Day 7
- The brief interval, typically a few milliseconds, that the scheduler lets a thread run before preempting it and giving the core to another.
- time to first byte Day 21
- The elapsed time from sending a request to receiving the first byte of the response, reported by curl as `time_starttransfer` and by the Network tab in a request's Timing sub-tab.
- Time zone Day 81
- A named set of rules mapping instants to local wall-clock times, recorded in the IANA time zone database and reachable from Python through zoneinfo. A fixed offset is not a time zone: it is wrong for half the year in any zone that observes daylight saving.
- Time zone Day 95
- A named region with a shared history of offsets and a shared set of rules for changing them — Europe/London, America/New_York. A zone is not an offset: it is the whole rule set that decides which offset applies at which instant, including every change the region has ever made. The name is the durable identifier; an abbreviation such as IST or CST is not, because several places use each one.
- Time-Series Split Day 180
- A walk-forward validation scheme strictly ensuring training data precedes test data in chronological order.
- timedelta Day 95
- A duration, stored internally as days, seconds and microseconds only. It deliberately has no months or years field, because those have no fixed length: a month is 28, 29, 30 or 31 days depending on which one and which year. So "add one month" is not a timedelta but a policy — clamp to the month end, overflow into the next month, or refuse — and the standard library provides calendar.monthrange to inform the choice while making none.
- timeout Day 27
- A deadline a client sets on a request so that a call which never answers becomes a handled failure rather than an indefinite hang.
- Timeout Day 78
- The limit on how long a client will wait. In requests it is two numbers: a connect timeout covering DNS, TCP and TLS, and a read timeout covering the gap between bytes arriving — not the total duration of the call. There is no default at all, so a call with no timeout= against a socket that never answers waits for as long as the operating system allows, which can be hours.
- Timeout Day 81
- A wall-clock budget after which a job is interrupted. In process, signal.setitimer with SIGALRM — POSIX-only, main thread only, and unable to interrupt a call blocked inside a C library. Around a child process, subprocess with start_new_session and os.killpg, escalating SIGTERM to SIGKILL. Without one, a hang holds the lock and silently stops every later run.
- TLS Day 15
- Transport Layer Security, the protocol that encrypts a connection and verifies the server's identity so traffic is private and tamper-proof; the S in https.
- TLS Day 19
- Transport Layer Security, the protocol that wraps a network connection in encryption and authentication; the modern successor to SSL.
- TLS Day 78
- Transport Layer Security: encryption and server identity verification layered over TCP. HTTPS is HTTP inside TLS. The handshake costs one or two extra round trips, which is why connection reuse matters more over HTTPS than over plain HTTP. requests verifies certificates by default; verify=False reduces HTTPS to obfuscation, because the traffic is then encrypted to whoever answered.
- tmp_path Day 72
- A built-in pytest fixture that hands a test a fresh, empty pathlib.Path directory unique to that test, retained for the last few runs so a failure can be inspected. It is a security control as much as a convenience: a test that writes to a hard-coded path can clobber real data or collide with a parallel run.
- to_numeric(errors='coerce') Day 125
- A pandas function that converts a column to a numeric dtype, and, with errors='coerce', silently turns every value it cannot parse into a missing value rather than raising. Never coerce a column without counting how many values became missing as a result -- the count is the only defence against a mostly-garbage column silently becoming a mostly-NaN column with no complaint.
- to_numeric(errors="coerce") Day 126
- A pandas function that converts a column to a numeric dtype, turning any value it cannot parse into NaN rather than raising (Day 125). Idempotent on an already-numeric column, because the conversion is a no-op once nothing is left to coerce.
- Toil Day 84
- Repetitive manual operational work that produces no lasting value and grows with the size of what you run. The term was popularised by Google's Site Reliability Engineering (2016). It is the thing automation is meant to remove — and the reason to check, before automating, that the task needs doing at all rather than merely needing doing faster.
- token bucket Day 27
- A rate-limiting model in which each request removes a token from a bucket that refills at a steady rate; it permits short bursts up to the bucket size while enforcing a long-run average.
- Tolerance Day 99
- The amount by which two computed floating-point numbers are allowed to differ while still being treated as equal. Comparing floats with double-equals is a bug, because the same mathematically correct calculation can land a fraction of a unit in the last place away from the expected value. A tolerance has two parts — relative, which scales with the size of the numbers, and absolute, which is what matters near zero — and it should be stated out loud rather than left to a library default.
- Tolerance Day 102
- The margin within which two floating-point numbers are treated as equal, stated explicitly and with a reason rather than assumed. This lesson uses 1e-12, because cos of pi over 2 comes out as 6.123233995736766e-17 rather than 0.0 and sin of 30 degrees as 0.49999999999999994 rather than 0.5 — both about 1e-17 from the exact answer. The chosen value sits five orders of magnitude above that rounding and four below the smallest quantity the lab cares about, so it accepts the noise and would still catch a real error.
- Tomek Links Day 160
- Pairs of very close instances of different classes used in data cleaning to remove ambiguous or noisy borderline points.
- tomllib Day 97
- The standard library's TOML reader, added in Python 3.11 and deliberately READ-ONLY — there is no tomllib.dump. Its load function requires a BINARY file object, which catches everybody exactly once. Its advantage over the environment is that TOML has real types, so batch_size = 64 arrives as an int and dry_run = false arrives as a bool, with no conversion and no chance of believing that the string "false" is true.
- Toolkit Day 84
- One installed package providing several related commands over a shared core, configured from outside the code, with a durable record of what it has already done. The step up from a script that most personal automations should take once a second command needs to share logic with the first.
- Top-N-per-group Day 91
- The problem a plain GROUP BY cannot solve: the two most active borrowers in each tier, the most recent row per source, the best three results per query. Aggregation collapses the rows, so the identifying columns are gone by the time you know a value is a winner. The window-function answer computes ROW_NUMBER over a partition and filters it in an outer query.
- Topological order Day 110
- An ordering of a computation graph in which every node appears after everything it was computed from. A backward pass must visit that order in reverse, so that no node passes its gradient onwards before it has received every contribution owed to it. On a branching graph any convenient order will silently drop a path.
- torch.nn.Module Day 204
- The fundamental base class for all neural network architectures in PyTorch, encapsulating layers, parameters, forward logic, and hooks.
- torch.no_grad() Day 202
- A context manager that disables Autograd graph construction to conserve memory and accelerate inference.
- torch.no_grad() Day 204
- A Python context manager that disables autograd tracking to accelerate evaluation and reduce memory consumption.
- torch.utils.data.DataLoader Day 205
- A multi-process batching engine that combines a dataset and a sampler to yield mini-batches with automatic shuffling and worker management.
- torch.utils.data.Dataset Day 205
- An abstract class representing a dataset. Subclasses implement __len__ and __getitem__ to retrieve individual data samples.
- total variation distance Day 138
- Half the sum of absolute differences between two probability vectors: 0.0 when they match exactly, 1.0 when they share no mass. A legitimate one-number summary of how far a sample's composition sits from a reference, and a poor thing to lead a report with, because a severe shortfall in one small group produces only a small distance.
- trace Day 40
- A record of a single request as it travels through a system, reassembled from many spans that share one trace identifier, showing where the time was spent.
- traceback Day 48
- The report Python prints when an uncaught exception occurs, showing the chain of function calls that led to the failure, each with its file, line number, and code, ending with the exception type and message.
- traceback Day 66
- The call stack printed as text when an exception goes unhandled, one block per frame. Frames print outermost first and innermost last — hence "most recent call last" — so the useful lines are at the bottom.
- traceroute Day 16
- A tool that reveals the routers along the path to a host by sending packets with increasing hop limits so each router in turn reports back.
- tracking branch Day 32
- A read-only local mirror of a remote branch, such as origin/main, that Git updates for you during fetch and pull; also called a remote-tracking branch.
- Tracking gap Day 132
- The root-mean-square vertical distance between two drawn curves, measured in fractions of the plot height. Zero means they lie exactly on top of one another. It is the quantity a dual-axis chart really manipulates, and the lab measures it running from 0.4938 to 0.0147 on unchanged data. Because the same small gap is achievable for an uncorrelated pair and a strongly correlated one, a small gap carries no information about correlation.
- Trailing underscore convention Day 146
- A documented naming rule, not a style choice: any attribute ending in "_" was learned from data by fit(); anything without it is a hyper-parameter set by the caller. Measured on a fitted LogisticRegression at exactly five such attributes.
- trailing window Day 131
- A rolling window whose span, at any given point in time, covers only observations up to and including that point -- never any future observation. Because it can only "look backward", a trailing window's own peak necessarily lags the true peak it is summarizing by roughly half the window's width.
- Train-Serve Skew Day 196
- A discrepancy in performance or data processing between how a model was trained and how it executes in live production.
- Train/Serve Skew Day 173
- Discrepancies in data preprocessing between training time and live production inference that cause silent model degradation.
- Train/Serve Skew Day 175
- The discrepancy between feature values computed during training and feature values generated during live production inference.
- train/test contamination Day 137
- Any statistic fitted on rows the model will later be scored on: a scaler's mean, an imputer's fill value, a category's average outcome, a vocabulary. It hides in the order of the code, and the question that finds it is "which rows went into this number?". Its severity varies enormously -- measured here, a contaminated scaler was worth -0.06 points and a contaminated group-mean imputer 8.22.
- Training Harness Day 210
- A structured software engine (Trainer class) orchestrating data loading, forward/backward passes, metric logging, and persistence.
- Training R2 climb Day 152
- The rise in a model's R-squared measured on the same rows it was fit on, as predictors are added, regardless of whether those predictors carry any real relationship to the target. Measured here at 0.5554 to 0.7403 across 0 to 100 pure-noise columns -- not a sign of a better model, a mechanical consequence of ordinary least squares.
- Training set Day 144
- The rows a model fits its parameters on, and the only rows anything fitted may see -- a scaler, an imputer, an encoder, a feature selector or a decision threshold included. Unlimited looks, and a score measured here estimates nothing.
- Training-serving skew Day 143
- When a feature is computed one way during training and another way at prediction time. The same ordering bug in a different costume: silent, inflates the offline number, and found only when live performance disappoints.
- training/serving skew Day 137
- The gap that opens when the feature computed in a training pipeline and the feature computed in a request handler are not quite the same feature. It is the problem feature stores were built for, and it is the reason the same code path is worth more than the better implementation.
- Transaction Day 85
- A group of statements treated as one indivisible act, opened with BEGIN and ended with COMMIT or ROLLBACK. Borrowing a book is a new loan row and one fewer copy on the shelf, and neither is true alone. In Python, "with connection:" commits on success and rolls back on any exception.
- Transaction Day 88
- A boundary you draw around a group of statements with BEGIN, closed with COMMIT to keep them or ROLLBACK to discard them. Inside it, changes are completely real to your own connection and invisible to everyone else. Its promise is about grouping, not about safety in general: a COMMIT after a mistaken statement commits the mistake perfectly.
- Transaction Day 90
- A group of statements treated as one indivisible act: BEGIN, then COMMIT or ROLLBACK. Two writes that are only true together — a loan row and one fewer copy on the shelf — belong in one. If anything at all is raised in between, including a KeyboardInterrupt, the group must be undone, which is why a hand-written transaction context manager catches BaseException rather than Exception.
- Transactional DDL Day 88
- The property that schema statements — CREATE TABLE, DROP TABLE, ALTER TABLE — can be rolled back like ordinary writes. SQLite has it, verified directly for this lesson, and the migration runner depends on it entirely. Engines without it leave a failed migration half-applied, so a runner there needs a recovery story rather than a rollback.
- Transformation matrix Day 102
- The matrix whose columns are the landing places of the basis vectors: column 0 is where e1 goes, column 1 is where e2 goes. Formally A = the matrix whose columns are T(e1), T(e2) and so on. The most common error in the whole topic is reading a ROW as a landing place — the matrix is written across and it means down.
- Transformer Day 146
- An estimator that implements transform() instead of, or beside, predict(). 90 of 210 discovered estimators. Overlaps with predictors only for clustering models and meta-estimators -- 20 of them, named explicitly in this lesson.
- TransformerMixin Day 173
- A mixin class providing the default fit_transform method implementation for transformers.
- transistor Day 1
- A microscopic electrical switch with no moving parts whose on/off state is the physical basis of all digital computing.
- Transpose Day 100
- The matrix obtained by swapping rows and columns: entry (i, j) of the transpose is entry (j, i) of the original, and an (r, c) matrix becomes (c, r). Written M-transpose in mathematics and M.T in NumPy. Transposing twice returns exactly the original. In NumPy it is a view and it moves no numbers at all — it swaps two entries in the description of how to walk the memory, which is why it costs nothing.
- tree recursion Day 62
- Recursion in which the recursive case makes two or more calls to itself, so the calls branch into a tree rather than a single chain. Naive Fibonacci is the classic example; the branching means the same subproblems can be recomputed exponentially many times unless the results are cached.
- TreeSHAP Day 168
- A fast, exact polynomial-time algorithm for computing Shapley values for tree-based ensemble models.
- TreeSHAP Day 178
- A fast polynomial-time algorithm for computing exact Shapley values on tree-based ensembles.
- Triage (in exploration) Day 136
- Deciding which candidate questions are worth pursuing before spending time on any of them, typically weighing expected information, cost, and how much the answer would change a real decision.
- Triangle inequality Day 99
- The rule that the distance from a to c is never more than the distance from a to b plus the distance from b to c — going via a third point cannot be a short cut. It is one of the properties a function must have to be called a distance at all, and both the L1 and L2 norms have it.
- Triangle inequality Day 103
- The rule that going direct is never longer than going via a detour: d(a, c) is at most d(a, b) plus d(b, c). The lesson breaks it with three two-dimensional vectors, a of 1 comma 0, b of 1 comma 1 and c of 0 comma 1: the two cosine distances are 0.292893 each, summing to 0.585786, while the direct distance is 1.000000. The direct route is longer than the detour, which is a counter-example, and one counter-example is a complete proof of the negative.
- Triangle inequality Day 107
- The requirement that a detour can never be shorter than going direct: d(x, z) is at most d(x, y) plus d(y, z). It is what allows an index to skip a region of the dataset without opening it — if the query is 10 from a cluster centre and the cluster has radius 2, nothing inside can be nearer than 8. Cosine distance breaks it: from (1, 0) to (0, 1) costs 1.0 direct and 0.585786 via (1, 1). An exhaustive sweep of all 3375 triples of non-zero four-bit vectors finds 326 violations, while Jaccard distance and Hamming distance survive all 4096 triples of their own sweeps.
- Triangulation Day 73
- Deliberately adding a second (or third) example specifically to make an over-simple implementation untenable, so the code is forced to generalise. It is theatre when no possible implementation passes the existing tests but fails the new one — then the extra test is padding, not a second bearing.
- Trivial Baseline Day 181
- A zero-learning heuristic predictor such as majority class or mean target value.
- Truncated axis Day 132
- A value axis whose range does not begin at zero. For a bar chart this breaks the encoding outright, because a bar's length from the baseline is the value: two bars for 100 and 102 on an axis starting at 99 draw at a measured height ratio of 3.00 against a data ratio of 1.02. For a line chart encoding change it is often legitimate and sometimes necessary, provided the baseline is visible, labelled, and chosen to serve the reader's question rather than the author's conclusion.
- Truncation error Day 108
- The part of a numerical derivative's error that comes from the mathematics rather than the arithmetic: the difference quotient is the limit's approximation at a finite h, and it is wrong by roughly (h ÷ 2)·f''(x) for the forward rule and (h² ÷ 6)·f'''(x) for the central one. It shrinks as h shrinks, which is the half of the story everyone knows.
- trunk-based development Day 35
- A branching strategy where everyone commits to a single main branch (the trunk) many times a day, with any branches living only hours, relying on strong automated tests.
- truthiness Day 44
- The rule that any object can be treated as true or false in a condition. Falsy values are False, None, any zero, and any empty container; everything else is truthy.
- truthy / falsy Day 50
- How Python treats any value when it is used as a condition. The falsy values are `False`, `None`, numeric zero (`0`, `0.0`), and every empty container (`""`, `[]`, `{}`, `()`, `set()`); everything else is truthy. This is why `if items:` means "if the list is non-empty."
- TTL Day 16
- Time to live: on a DNS record, how many seconds a resolver may cache the answer; on an IP packet, the hop limit that traceroute exploits.
- tuple Day 54
- An ordered, immutable sequence of items, written with commas and usually parentheses, e.g. `(3, 4)`. It supports indexing and iteration like a list but cannot be changed after creation, which makes it a safe fixed record and lets it serve as a dict key or set member.
- Tuple Day 85
- One row, in the vocabulary of the relational model: a fixed sequence of values, one per column, each drawn from that column's domain. "Row" and "tuple" name the same thing from two traditions; a tuple is usually thought of as ordered by position, a row as addressed by column name.
- tuple unpacking Day 54
- Assigning the items of a tuple to several names at once, e.g. `row, col = (2, 5)`. It also powers the clean swap `a, b = b, a` and the way a function returns multiple values.
- Two-Layer Multi-Layer Perceptron Day 203
- A neural network architecture with one hidden layer and one output layer, capable of learning non-linear classification boundaries.
- two's complement Day 4
- The standard representation of signed integers, in which −n is the bit pattern of 2ᵏ − n (flip the bits, add 1); it gives one unique zero and lets a single adder circuit perform both addition and subtraction.
- Type affinity Day 85
- A column's declared type in SQLite, understood correctly: a preference the engine applies when a conversion is lossless and abandons when it is not. Insert the text '1970' into an INTEGER column and it becomes the integer 1970; insert 'not-a-number' and it is stored as text, in that same column, with no error.
- type alias Day 69
- A name bound to a type expression, such as `Scores = dict[str, list[float]]`. Written once, it replaces a repeated and unreadable expression across many signatures, and is among the cheapest readability wins available.
- type checker Day 37
- A static tool that verifies the kinds of values fit together — that text is not passed where a number is required, or a possibly-missing value read as if present — without running the code.
- type checker Day 75
- A separate program that reads your annotated source without executing it and reports where an expression contradicts the annotations around it. mypy is the reference implementation; Pyright, ty and pyrefly are others. It produces a report and an exit status, and changes nothing about how your program behaves.
- type conversion Day 44
- Turning a value of one type into another by calling the target type, such as int("42"), float("3.14"), or str(42). Can raise ValueError on invalid input.
- type hint Day 61
- An optional annotation stating the expected type of a variable, parameter, or return value, such as `def mean(scores: list[float]) -> float:`. Python does not enforce hints at runtime, but they document intent for readers and let tools (type checkers, editors) catch mismatches before the code runs.
- type hint Day 69
- An annotation used to describe types, in the sense standardised by PEP 484. Its audience is offline checkers, editors and human readers; the PEP states explicitly that Python will not enforce it at runtime.
- Type I error Day 118
- Rejecting a true null hypothesis -- a false positive. Its rate is controlled directly by alpha, by design, for a single test run exactly once at a fixed sample size.
- Type II error Day 118
- Failing to reject a false null hypothesis -- a false negative. Its rate, beta, is not controlled by alpha alone; it depends on the true effect size and the sample size too, which is exactly what power measures.
- type inference Day 75
- The checker working out the type of an expression you never annotated. Write `total = 0` and mypy knows it is an `int`; write a comprehension over a `list[Model]` and it knows what comes out. Inference is why annotating function signatures buys checking of hundreds of lines you did not annotate.
- type inference Day 121
- The process by which read_csv() decides, per column, what dtype the file's plain text should become -- int64, float64, bool, str, a date -- based on what the values in that column look like, without being told. It is a guess, made once, silently, and it is usually right.
- type: ignore Day 75
- A comment suppressing a mypy error on one line. Always write it with its error code — `# type: ignore[union-attr]` — because a bare ignore silences every error on that line forever, including the different one that appears next year. mypy reports when the code you named does not cover the error found.
- TypeAdapter Day 94
- Validation and serialization for a type that is not a BaseModel — list[int], dict[str, Reading], a Union, a plain datetime. TypeAdapter(list[Reading]).validate_python(rows) validates a whole batch in one call, and the errors it raises carry the element index as the first component of loc, so the report names which row failed.
- TypedDict Day 69
- An annotation describing a dictionary with known keys and a type per key. It is how you type JSON-shaped data that must stay a dict rather than becoming a class.
- TypedDict Day 75
- An annotation describing a dictionary with known keys and a type for each key — how you type JSON-shaped data that must stay a dict rather than becoming a class. Misspell a key and the checker reports both halves of the story: the required key that is missing and the unexpected key that appeared.
- TypeError Day 48
- An error raised when an operation receives a value of the wrong type, such as trying to add a string to an integer.
- typeshed Day 75
- The community-maintained collection of stub files for the Python standard library and for third-party packages that ship none. It is bundled with mypy and read by every checker, and it is why `json.load` is known to return `Any` and `Path.read_text` is known to return `str` without you writing anything.
- TypeVar Day 75
- A placeholder type variable meaning "whatever type came in, that same type goes out". It is what `Any` cannot express, because `Any` forgets: a function annotated with a TypeVar returns a known type that depends on its arguments, so the checker keeps tracking values through it.
- typing.NamedTuple Day 69
- An annotated, immutable tuple subclass. It unpacks and indexes like a tuple and compares equal to a plain tuple with the same values — convenient in some code, confusing in others. A frozen dataclass gives immutability without the tuple-ness.
- Ubiquitous language Day 70
- The shared vocabulary of the domain expert and the code. If the owner says member, plan, tier and check in, the code says Member, Plan, PlanTier and check_in — every translation between the two vocabularies is a place a misunderstanding can hide.
- UDP Day 17
- User Datagram Protocol: a connectionless, best-effort transport that sends packets with no handshake, ordering, or delivery guarantee — fast and low-overhead.
- UMAP Day 186
- Uniform Manifold Approximation and Projection: a dimension reduction technique founded on Riemannian geometry and algebraic topology.
- Unbiasedness Day 149
- An estimator's average value, over many independent datasets, equals the true parameter. Confirmed separately from efficiency here: both OLS and Huber stayed within 0.01 of the true slope of 3.0 in both error settings, so bias was never what changed between them.
- Uncertainty Sampling Day 191
- An active learning query strategy that selects unlabeled samples where the current model has highest prediction entropy or lowest confidence.
- Underfitting Day 145
- The model class being unable to represent the truth, so the error survives however good the fit is. It is the bias term. No amount of optimisation, tuning or data helps, because the constraint is what the class can express at all.
- Unicode Day 5
- A universal standard that assigns a unique number (a code point) to every character in every writing system, plus emoji.
- UnicodeDecodeError Day 64
- The error raised when bytes on disk are not valid under the encoding you asked for. It is a feature, not a nuisance: it is the file telling you it is not what you assumed, usually that an older program wrote it in Latin-1.
- unified memory Day 3
- A design in which CPU and GPU share one physical memory pool, so a model or dataset can be large without being copied between separate CPU and GPU memories.
- Uniform distribution Day 114
- Every value in an interval [a, b] is equally likely. Mean (a+b)/2, variance (b-a)^2/12. Its density is the constant 1/(b-a), which exceeds 1 whenever the interval is narrower than 1 — the standard example that a density is not a probability.
- union Day 54
- The set operation `a | b` that returns every item appearing in either set, with duplicates collapsed — e.g. `{1, 2} | {2, 3}` is `{1, 2, 3}`.
- union type Day 75
- A type meaning "one of these", written `str | list[str]` or `Model | None`. Anything you do with a union must be valid for every member unless you narrow first, which is why unions and narrowing are always learned together.
- uniq Day 10
- A command that collapses adjacent identical lines into one, and with -c prefixes each with a count of how many times it repeated — usually paired with a preceding sort.
- Unique index Day 89
- An index that additionally refuses a duplicate key, which is how a UNIQUE constraint enforces itself. It is the one case where an index is not purely a speed change: it also changes which writes are allowed. Every PRIMARY KEY and UNIQUE constraint quietly creates one.
- Unit ball Day 107
- The set of points at distance exactly 1 from the origin under a given norm — the picture that makes the p-norm family click. L1 gives a diamond, L2 a circle, L-infinity a square, with areas 2, pi and 4. The shapes are strictly nested, which is the same fact as the p-norm falling as p rises, said the other way round: a bigger p is a more forgiving norm, so more points fit inside its ball. A single point such as (0.6, 0.8) sits outside the diamond, on the circle and inside the square, and measures 1.4, 1.0 and 0.8 under the three.
- Unit direction Day 109
- A vector of length exactly 1, used to specify a direction without also specifying a distance. Obtained by dividing a vector by its magnitude, which is undefined for the zero vector — a zero vector has no direction to preserve, and today's lab raises ValueError rather than returning NaNs that would surface somewhere harder to diagnose. Every directional derivative is taken along a unit direction so that the answer depends on the bearing alone.
- Unit of a metric Day 152
- What RMSE and MAE are stated in -- the same units as the target. A metric you cannot state a unit for is a metric you cannot explain to a stakeholder; the diabetes target itself has no physical unit, being a composite disease-progression score, which this lesson states plainly rather than fabricating one.
- Unit of independence Day 144
- The thing you want to generalise to, which is the thing you must split by. The row is the unit only when rows are independent, and deciding this is a question about the domain rather than about the data.
- Unit of work Day 93
- The pattern the Session implements: accumulate every change an operation makes, then write them all at once, in an order the pattern works out for you so that foreign keys resolve. It is why there is no save() method to call — you change objects, and the Session decides what SQL that implies and when to send it.
- Unit test Day 71
- A test that exercises one function or one object in isolation, in milliseconds, with no files, network or clock involved. Contrast an integration test, which exercises several parts together and is slower and more fragile by nature.
- Unit vector Day 99
- A vector whose magnitude is 1. It carries direction and nothing else, which is why a unit vector is the natural way to say which way without saying how far. Because floating-point arithmetic is approximate, the magnitude of a computed unit vector is 1 to within a small error and not always exactly the float 1.0 — a fact this day proves rather than asserts.
- Unit vector Day 103
- A vector of length exactly 1, carrying direction and nothing else. Every vector except the zero vector has one pointing the same way, obtained by dividing by its own length. Two unit vectors compared with the dot product give their cosine similarity directly, with no division left to do — which is the whole reason a vector store normalises on the way in.
- Universal function Day 104
- A NumPy function that applies elementwise to an array of any shape and returns an array of the same shape — np.sqrt, np.exp, np.abs, np.sign, np.maximum and the arithmetic operators are all ufuncs. Usually shortened to ufunc. The equivalent list comprehension gives the same answer and takes roughly a hundred times as long, because the ufunc's loop is compiled rather than interpreted. math.sqrt is not a ufunc and raises TypeError when handed an array.
- Unix Day 6
- The operating system begun at Bell Labs in 1969 by Ken Thompson and Dennis Ritchie, whose portable C implementation and licensed source code made its design the ancestor or model for macOS, Linux, and most server systems.
- Unix philosophy Day 10
- A design approach that favors small programs each doing one job well, built to work together, communicating through text streams as a universal interface.
- Unsafe fix Day 76
- An autofix that might change behaviour or discard something, so it is opt-in behind `--unsafe-fixes`. "Unsafe" does not mean "wrong": rewriting `basket=[]` into `basket=None` plus a guard is the correct fix precisely because it changes behaviour — the old behaviour was the bug. Preview with `--diff` before applying, and re-run your tests after.
- Unsupervised learning Day 142
- The setting in which only inputs are available and no target exists. Because no error is computable, every evaluation is a proxy for a judgement somebody has to make and own -- which is the setting's real difficulty, and it is not a computational one.
- untyped arrival Day 135
- The fact that every value decoded from a JSON API response is, until explicitly parsed, one of JSON's six native types -- and numeric-looking or date-looking values are frequently serialized as plain strings by the API on purpose, to avoid floating-point precision loss on the wire. A DataFrame built directly from such a response inherits that string-ness until dtypes are pinned.
- unwinding Day 66
- The interpreter's outward walk from the raising frame toward the top of the stack, asking each frame in turn whether it has a matching handler and running each abandoned frame's finally block on the way.
- Update anomaly Day 87
- The failure where a fact stored in several rows is corrected in some of them and not others, leaving the database contradicting itself with no error raised. The most dangerous of the three anomalies precisely because it is silent: nothing marks which of the two values is the right one.
- upgrade Day 13
- Moving installed software to a newer version while preserving the surrounding dependency tree, as opposed to reinstalling the same version.
- upsert Day 135
- A merge operation that inserts a new row for a key not already present, and replaces the existing row for a key that is already present, rather than appending a duplicate. The mechanism this lesson uses to make ingestion idempotent.
- Upsert Day 88
- An INSERT that becomes an UPDATE or a no-op when it would violate a uniqueness constraint, written as ON CONFLICT (column) DO UPDATE or DO NOTHING. Added to SQLite in version 3.24.0 in 2018. Its advantage over insert-then-update is atomicity: there is no window between checking and acting for another connection to use.
- upstream Day 32
- The specific remote branch a local branch is paired with, so that a bare git push or git pull knows where to send and receive commits.
- URL Day 15
- A Uniform Resource Locator — the full address of a resource on the web, made of a scheme (such as https), a host name, and a path, plus any query.
- Usage message Day 80
- The short synopsis argparse prints when a command line is malformed, showing the shape of a correct invocation followed by the specific error, on standard error, with exit code 2. It is generated from the same declarations that do the parsing, so it cannot drift out of date with the behaviour.
- USE TEMP B-TREE FOR ORDER BY Day 89
- The line in a query plan meaning SQLite built a throwaway tree and sorted every candidate row into it to satisfy an ORDER BY. Measured here at 13.978 ms to return twenty rows from four hundred thousand. An index that already supplies the requested order removes the line and the work with it — 0.007 ms for the same twenty rows.
- user space Day 6
- The unprivileged world where all ordinary programs run, confined to their own memory and required to request every hardware service from the kernel through system calls.
- User-Agent Day 21
- A request header identifying the client software making the request; curl sends a value like `curl/8.7.1`, while a browser sends a long string naming itself and its version.
- User-Agent Day 78
- The header saying who is making the request. Identify yourself honestly with a tool name, a version and ideally a contact address; some services block empty or default agents outright. Impersonating a browser to evade a block is the subject of the next lesson's ethics section, and it is not a technical question.
- User-Agent Day 79
- The HTTP header identifying the client making a request. An honest one names your program and gives a way to contact you, so an operator who notices you can send an email rather than a block. Copying a browser's string to disguise a scraper tells the operator something about your intentions, and it is not the something you want.
- UTC Day 95
- Coordinated Universal Time — the reference against which every offset is stated. It has no daylight saving and never jumps, which is what makes it the right storage format: an instant recorded in UTC means the same thing on every machine, in every year, under every government. In Python it is timezone.utc, and datetime.now(timezone.utc) is the correct way to ask for the current instant.
- UTF-8 Day 5
- The dominant variable-length encoding of Unicode: it stores common characters in one byte and others in two to four bytes, staying backward-compatible with ASCII.
- UTF-8 Day 64
- The dominant character encoding of the web, designed by Ken Thompson and Rob Pike in September 1992. The 128 ASCII characters keep their single-byte values, so every ASCII file is already valid UTF-8, while other characters expand to two, three, or four bytes — which is why "café" is 4 characters but 5 bytes.
- Vacuous test Day 71
- A test that passes no matter what the implementation does — `assert result is not None`, `assert isinstance(result, list)`, `assert True` after a call. It is the go/no-go gauge every part fits through: it documents a quality process that certifies nothing. The cure is to break the code on purpose and confirm the test goes red.
- Valid but wrong Day 98
- A record that satisfies every rule the gate can express and is nonetheless untrue — 41.3 Celsius five minutes after 15.0 Celsius from a station that has not moved. No field-level rule catches it, because every field is legal; only a rule about the sequence or the context can. The right response is to store it and flag it, never to drop it: a visible anomaly somebody must look at is strictly better than an invisible gap nobody will.
- validate Day 124
- A merge() keyword accepting "one_to_one", "one_to_many", "many_to_one" or "many_to_many", each stating a cardinality assumption about the merge key on each side. If the assumption is false, pandas raises pandas.errors.MergeError before producing any output, rather than silently completing an unintended Cartesian product.
- validate_assignment Day 94
- The model_config setting that re-runs validation when a field is assigned after construction, so an object that was legal when built cannot be made illegal afterwards. Off by default, because it costs a validation on every write. frozen=True is the stronger version: no assignment at all, reported as frozen_instance.
- validation Day 82
- Checking incoming data against declared rules at the boundary, before any of your logic sees it. In an API it is not optional, because the caller is a stranger. It also canonicalises: `HttpUrl` does not merely accept a URL, it normalises it, so downstream code sees one spelling rather than five.
- Validation Day 88
- A check performed in application code before a write is attempted — a friendly message for a user, in one program. Distinct from a constraint in scope rather than in intent: validation protects the writes that go through your application, a constraint protects all of them. You want both, and when they disagree the schema is right.
- Validation Day 94
- Checking, at runtime, that a value satisfies the rules you declared for it, and refusing it when it does not. Distinct from parsing, which turns bytes into objects and asks nothing about whether the objects make sense, and from type checking, which happens before the program runs and never sees a byte of real data.
- Validation Curve Day 177
- A plot showing training and validation scores as a function of a single model hyperparameter (such as max depth or regularization lambda).
- Validation set Day 144
- The rows you choose between candidates on. Many looks are permitted and every look costs something measurable: the score on this set is inflated by the expected maximum of K noise draws, where K is how many things you tried.
- ValidationError Day 94
- The exception pydantic raises when input does not satisfy a model. Its defining property is that it reports every problem it found in one pass rather than the first, so a caller fixes a file in one round trip instead of ten. exc.errors() returns a list of entries, each carrying loc, type, msg and input.
- value Day 53
- The data stored under a key in a dictionary. Values can be any Python object at all — including a list or another dictionary — and, unlike keys, may repeat.
- Value object Day 70
- An object defined entirely by its values, so two with identical values are interchangeable. Immutable (a frozen dataclass in Python), compared and hashed by value — Money, DateRange, a membership number.
- ValueError Day 48
- An error raised when a value is the right type but unacceptable for the operation, such as calling int("hello").
- Vanishing gradient Day 110
- A gradient that becomes too small to move a weight, because the product of many local rates below 1 collapses towards zero. Fifty factors of 0.25 — the sigmoid maximum slope — give about 7.9e-31, which changes a weight of 1 not at all. The arithmetic is correct; the answer is useless, and those are different complaints.
- Vanishing Gradient Problem Day 198
- A pathology in deep networks where backpropagated error gradients decay exponentially toward zero as they pass through saturating activation layers.
- Vanishing Gradients Day 209
- A condition where gradients shrink exponentially as they propagate backward through layers, stalling parameter updates in early layers.
- variable Day 12
- A named holder for a value in a script, assigned with `name=value` (no spaces around `=`) and read with `$name` or `${name}`.
- variable Day 44
- A name that refers (is bound) to an object. In Python a variable is a tag on an object, not a box that stores a value.
- Variance Day 114
- Var[X] = E[(X - E[X])^2], the expected squared distance from the mean. Unlike expectation, variance does not distribute over a sum unless the variables involved are independent (or, more precisely, have zero covariance): Var[X+Y] = Var[X] + Var[Y] + 2*Cov(X,Y).
- Variance Day 116
- The average squared distance of every value from the mean. For a full known population it is exact; for a sample, the naive divide-by-n formula is biased low, which is what Bessel's correction fixes.
- Variance Day 145
- How much individual predictions scatter around their own average across training sets. An error that changes with the data you happened to draw. Measured here at 0.7112 at degree 1 and 452183.1336 at degree 12.
- Variance inflation factor Day 150
- 1 / (1 - R2), where R2 comes from regressing one predictor on all the others. A VIF of 1 means a predictor is unrelated to the rest; measured here at 59.2025 for the most entangled predictor against 1.2173 for the least.
- Variance-limited versus noise-limited Day 141
- A problem is variance-limited when the boundary is learnable and the sample is too small to reveal it; more data helps decisively, measured here as a 39.8-point gain. It is noise-limited when the labels themselves are wrong; more data moves it barely, measured here as 2.1 points against a ceiling it already sat within 3.5 points of.
- VarianceThreshold Day 172
- A baseline filter that removes all features whose empirical variance does not meet a specified minimum threshold.
- Vector Day 99
- An ordered list of numbers where position carries meaning, and equivalently an arrow with a direction and a length. Both pictures describe the same object, and the whole skill of this day is holding them together: the list is what you type, the arrow is what you picture. A colour with three channels, a house with four measurements, a document with three hundred embedding numbers — all vectors, whether or not anyone used the word.
- Vector database Day 92
- A specialised key-value store in which the key is an embedding and the lookup is nearest-neighbour rather than exact match. Everything true of key-value stores transfers: it is excellent at the one question it was built for, and any other question — such as filtering by publication date — is a secondary concern that must be bolted on, which is why metadata filtering interacts awkwardly with the index.
- vector image Day 5
- An image described as shapes and coordinates (for example SVG) that scales to any size without losing sharpness.
- vector image Day 128
- An image format (SVG, PDF, EPS) stored as a description of shapes, paths and text -- resolution-independent, and, for SVG, literally XML markup you can open in a text editor. A vector chart's axis label appears as a literal <text> element you can search for in the file; the file can be zoomed or printed at any size without pixel artifacts.
- Vector index Day 89
- A structure for finding the nearest points to a query point in a high-dimensional space, used for similarity search over embeddings. Most are approximate — they trade a small chance of missing a true nearest neighbour for a large reduction in work, a trade a B-tree never makes. What carries over from this lesson is that a real retrieval query is a similarity search plus a filter on tenant, permission or date, and that filter is an ordinary WHERE clause wanting an ordinary index.
- vectorisation Day 120
- Expressing a computation as one operation over a whole array or Series, which runs inside compiled code, rather than looping over elements in interpreted Python (as .apply(lambda ...) does). Covered first for bare NumPy arrays on Day 104.
- Vectorisation Day 104
- Expressing an operation on a whole array at once rather than element by element in Python. The loop does not disappear — NumPy's broadcasting documentation puts it exactly: "Broadcasting provides a means of vectorizing array operations so that looping occurs in C instead of Python." What you gain is speed and expressiveness; what you give up is the ability to put a print, a breakpoint or an early exit inside the loop, and the option of a step that depends on the one before it.
- venv Day 43
- Python's built-in module for creating virtual environments, used as python3 -m venv .venv; also a common name for the environment folder it creates.
- verbose mode Day 21
- curl's `-v` option, which prints the entire conversation: the request sent (lines starting with >), the response headers (lines starting with <), and connection notes (lines starting with *).
- Verdict Day 147
- The end product of a properly run classification project: a test score, an interval around it, a statement of whether it clears the baseline given that interval, and an honest account of the specific errors the model makes -- not a single accuracy number quoted alone.
- Verdict Day 154
- The end product of a properly run regression project: a test RMSE, a bootstrap interval around its margin over baseline, a statement of whether the margin clears that interval, residual diagnostics, a fairness check by target level, and a prediction interval with measured coverage -- not a single RMSE quoted alone.
- Verdict refusal Day 119
- The deliberate choice to return no effect estimate at all once a precondition check (here, the sample-ratio mismatch check) has failed, rather than computing and reporting a number anyway with a caveat attached. Used in this lesson's `verdict()` function: dataset B's verdict carries no `estimate_pp` key, because randomization that cannot be trusted makes any downstream number untrustworthy too.
- version control Day 29
- A system that records the full history of a set of files over time so you can recall any earlier version, see what changed, and let many people change the files without losing work.
- version control Day 42
- Tracking every change to your work with git so you can commit, branch, merge, share, and undo almost anything — a domain that wraps the whole stack (days 29-35).
- version pinning Day 13
- Requesting a specific version of a package rather than "the latest," so a silent upgrade cannot change a project's behavior.
- View Day 91
- A saved query, given a name. It buys a name for a piece of reasoning and consistency between reports that use it. It does not buy speed: it stores the query text, not the result, and is expanded into whatever query uses it and run afresh every time. A materialized view does store the result, and SQLite does not have them.
- View Day 100
- An array that shares memory with another array rather than owning its own. Writing through a view changes what the other name sees, and nothing in either name says so. Reshaping, basic slicing with colons, transposing and ravel all give views when they can. This is why NumPy is fast — a reshape of a 300 MB array moves no bytes — and why a function that receives an array can modify the caller's data without returning anything.
- View Day 104
- An array that shares its data with another array, differing only in the header. Slicing, transposing, reshaping and ravel all return views when they can. NumPy's guide is explicit that this differs from a list: "slice indexing of a list copies the elements into a new list, but slicing an array returns a view ... The original array can be mutated using the view." Writing through a view writes through to the original, which is the hardest NumPy bug to find because the damage appears nowhere near its cause. np.shares_memory answers the question directly.
- virtual environment Day 43
- A lightweight, isolated folder that gives one project its own private set of installed packages, kept separate from the global Python and from other projects.
- Virtual environment Day 83
- An isolated directory with its own `site-packages` and its own `bin/`, created with `python3 -m venv`. Introduced on Day 43 as the place you install things into; today it is the place your package gets installed TO. Packaging and virtual environments are complements: one makes code installable, the other gives it somewhere to go.
- virtual memory Day 3
- The illusion, maintained by the OS and the memory management unit, that each program has its own private address space, translated to real RAM in fixed-size pages.
- virtual memory Day 6
- The memory-management scheme that gives each process a private, contiguous-looking address space mapped by page tables onto physical RAM, with less-used pages evicted to disk when memory runs short.
- Voronoi Tessellation Day 157
- A partitioning of a plane into convex polygonal cells such that every point in a cell is closer to that cell generator point than to any other generator.
- Voronoi Tessellation Day 183
- A partitioning of metric space into convex polyhedral cells, where each cell contains all points closer to its generating seed than to any other.
- Waiting work versus computing work Day 96
- The classification that decides everything on this day. Work that WAITS — on a socket, a disk, a database, a subprocess, a human — leaves the CPU idle, so overlapping it is nearly free: use threads or an event loop. Work that COMPUTES — arithmetic, parsing, encoding, CPU inference — occupies the CPU fully, so there is no idleness to overlap and the only route to speed is more CPUs: use processes. Measured here: the same three-line change gave 12.2x on the first and 1.01x on the second.
- Walk-Forward Validation Day 192
- A temporal cross-validation scheme where training datasets expand sequentially forward in time, testing strictly on subsequent horizons.
- Wall clock Day 95
- time.time() and the local clock generally: the reading a person would see, adjustable by NTP, by an administrator, by a laptop waking from sleep and by daylight saving. time.get_clock_info("time") reports it as adjustable and not monotonic, which is the documented statement of exactly that hazard. Correct for recording when something happened; wrong for measuring how long anything took.
- Wall-clock arithmetic Day 95
- Adding a timedelta to an aware datetime, which adds to the calendar fields and then re-derives the offset from the result. Two hours of wall-clock arithmetic can be one, two or three hours of elapsed time across a transition. It is the correct behaviour for "the meeting is at 09:00 next Tuesday" and the wrong one for "the token expires in one hour" — for elapsed time, convert to UTC, add, and convert back.
- Ward Linkage Day 184
- An agglomerative linkage objective that minimizes the total within-cluster variance increase resulting from merging two clusters.
- warn_unused_ignores Day 75
- The setting that reports an ignore comment which no longer suppresses anything, with the code `[unused-ignore]`. Without it, ignores written for real problems outlive those problems and accumulate for years until nobody dares remove one, because nobody can tell which still do something.
- watch expression Day 37
- A value or expression you ask the debugger to re-evaluate and display continuously as you step, so you can watch a single quantity change over the course of execution.
- Watch it fail Day 73
- The rule that a test must be seen failing, for a stated reason, before it is trusted. It is the only moment at which evidence exists that the test is connected to the behaviour it names; after it passes, a well-wired test and a vacuous one look identical.
- Watchdog Day 81
- A separate check, on its own schedule and in its own process, that asks whether the thing that should have happened has happened. It must be separate, because a watchdog inside the job it watches cannot report that the job never started.
- Watchdog Day 84
- A second, much simpler scheduled check that reads the last-success timestamp and raises the alarm when it is too old — including when there has never been one. It catches the failure nothing else can: the run that never happened, which produces no event for any supervisor to report. It must run on its own schedule, because a watchdog that shares a fate with the thing it watches is not a watchdog.
- waterfall Day 21
- A timeline view in the Network tab where each request is a horizontal bar showing when it started and how long each phase took, making slow or late requests easy to spot.
- watermark Day 135
- The timestamp (or other ordering value, such as a cursor) of the most recently seen record in an incremental fetch, used as the lower bound for the next fetch so that only new or updated records are requested rather than the entire dataset every time.
- WCSS (Inertia) Day 183
- Within-Cluster Sum of Squares: the sum of squared Euclidean distances between each point and its assigned cluster centroid.
- Weak Learner Day 164
- A base model (such as a depth-3 decision tree stump) that performs only slightly better than random guessing on its own, but combines into a strong learner when boosted.
- Weak Supervision Day 191
- A framework where noisy, higher-level, or programmatic sources of supervision are algorithmically combined to generate training labels.
- web API Day 22
- An API reached over HTTP across the network — a service on another computer your program calls with requests and reads responses from, instead of a local function.
- web API Day 82
- An interface over HTTP whose client is a program rather than a person. Because nothing on the other end can read, the field names and status codes are a contract: rename `title` to `name` and every caller breaks at once. That is the single difference from a web page, and everything else about API design follows from it.
- Web scraping Day 79
- Writing a program that reads a web page and extracts structured data from it. It exists because the data is visible to a human but is not offered in a machine-readable form — it is a workaround for a missing interface, not a right and not a technique of first resort.
- webhook Day 26
- An HTTP request that a server sends to a URL you registered in advance, to notify you that an event happened; because the server calls you, it is often described as a "reverse API."
- WebSocket Day 26
- A persistent, two-way connection over which client and server can both send messages at any time, used for interactive real-time applications.
- Weight decay Day 151
- The L2 penalty applied to a neural network's weights during training, and ridge regression's direct descendant. Shrinks every weight toward zero but, by the same geometry measured in this lesson, never produces an exact zero -- getting a sparse network needs an L1-style term or pruning on top.
- Weight Gradient (dW) Day 200
- The matrix of partial derivatives dL/dW indicating the direction of steepest increase in loss for each weight parameter.
- weighted mean Day 123
- A mean where each value contributes proportionally to an associated weight rather than equally -- computed here with np.average(values, weights=weights), either inside a per-group apply call or via a vectorised sum-of-products-over-sum-of-weights route that avoids apply entirely.
- Welch's t-test Day 118
- The small-sample-correct cousin of this lesson's large-sample two-sample z-test: uses a t rather than a normal reference distribution, with Welch-Satterthwaite degrees of freedom, and does not assume the two groups share a common variance. Implemented as scipy.stats.ttest_ind(a, b, equal_var=False), described but not run in this lesson.
- well-known port Day 17
- A port in the range 0–1023 reserved for a standard service, such as 22 for SSH, 53 for DNS, 80 for HTTP, and 443 for HTTPS.
- Wheel Day 83
- A built distribution: a zip archive with a defined layout, holding the importable package, its package data, and a `.dist-info` metadata directory. Installing one means unpacking it — no build, no compiler, and none of the publisher's build code executed. Specified by PEP 427 in 2012, and the single largest improvement in the history of Python packaging.
- while loop Day 51
- A loop that repeats its body as long as a condition is true and stops when the condition becomes false; the tool for indefinite iteration, where the number of repetitions is not known in advance.
- Whitening Day 185
- A linear transformation scaling principal components to unit variance, producing an uncorrelated identity covariance matrix.
- wide format Day 124
- A table layout with one column per measurement or category -- for example, separate math, reading and science score columns for each student. Natural to read but usually the wrong shape for groupby-based aggregation or most plotting libraries.
- Wide-column store Day 92
- A store whose unit is a row identified by a partition key, where the columns present may differ per row and rows are grouped physically by that key. Cassandra and HBase are the well-known ones. Its distinguishing design rule is that you model the table around the query rather than around the data — so two query patterns mean writing the same data twice, on purpose.
- wide-form data Day 129
- A table shaped with one row per group and multiple columns representing different conditions or time points (for example, one column per quarter). seaborn's long-form interface cannot read a variable that is spread across several column names, which is why hue= and similar arguments fail on wide data until it is melted into long form.
- Window function Day 91
- A function that computes a value across a set of related rows WITHOUT collapsing them — which is the entire difference from an aggregate. It is computed after WHERE and after GROUP BY, so filtering on its result requires an outer query or a CTE. Standardised in SQL:2003; added to SQLite in version 3.25.0 (2018).
- winget Day 13
- The Windows Package Manager, Microsoft's first-party command-line tool for installing, upgrading, and removing software on Windows 10 and 11.
- Winner's curse Day 142
- The systematic optimism of an argmax taken over noisy estimates. Whichever option is most inflated wins, and thinly-sampled options have the most room to inflate -- which is how an arm with 274 pulls beat one with 1524. The same effect appears in model selection on Day 144.
- Winner's curse Day 144
- The systematic upward bias of an argmax taken over noisy estimates: the winner is whichever estimate was most inflated. Named in 1971 for sealed-bid oil leases, met on Day 142 as a bandit arm, and met today as a validation score.
- Winner's curse (in this context) Day 136
- The tendency for a result selected because it looked best among many candidates to have both an inflated p-value's apparent extremity and an inflated effect size, simply because of the selection itself -- not because the underlying effect is actually that large.
- Winner's curse, applied to a real sweep Day 147
- The same argmax-over-noisy-estimates mechanism Day 142 and Day 144 measured on bandit arms and coin flips, checked here against real, skilled, correlated candidates -- and found to overestimate the real effect by roughly thirty-fold on average, because the assumptions behind the formula do not hold for this kind of sweep.
- word Day 4
- The natural chunk of bits a processor handles in one operation, typically 32 or 64 bits on modern machines.
- workflow Day 35
- A team's shared set of rules for how changes flow from an idea into the main line of a project — which branches exist, how changes are reviewed, and how releases are marked.
- workflow runner Day 126
- Software such as Prefect or Dagster that schedules pipeline runs, retries failed steps, and gives operational visibility into what ran and when -- solving a genuinely different problem from the correctness a pipeline's own idempotence, determinism and contracts provide. Not installed in this lesson's environment; described from documentation only.
- working directory Day 9
- The directory a shell is currently "in," from which relative paths are interpreted; printed by the pwd command.
- working directory Day 30
- The live files on disk that you see and edit right now — the in-progress version of the project, before anything is staged or committed.
- World-to-pixel transform Day 112
- The function that maps a data-space point (x, y) to an image-space pixel (column, row). x needs no flip because it grows rightward in both spaces; y needs one, because y grows upward in data space while pixel row 0 is the top of the image, so pixel row is computed from (ymax - y) rather than (y - ymin).
- Wrapper Method Day 172
- A feature selection approach (e.g. RFE, SFS) that uses a predictive model as an evaluation engine to search candidate feature subsets.
- Write amplification Day 89
- The general name for one logical write becoming several physical ones. With indexes it is concrete and measurable: each index is another structure every INSERT, UPDATE and DELETE has to maintain. Measured in this lesson's lab as 11.7 times slower to insert the same 100,000 rows with five indexes, and a file 2.4 times larger.
- Write-ahead log Day 85
- The alternative crash-recovery mode, enabled with PRAGMA journal_mode = WAL and stored beside the database as name-wal. It inverts the journal: new page content is appended to the log first and folded into the database later, which lets readers carry on while one writer works. It does not permit two writers.
- WSL Day 6
- The Windows Subsystem for Linux — a Windows feature whose current version runs a real Linux kernel in a lightweight virtual machine, giving Windows users a genuine Linux environment alongside Windows.
- X-RateLimit headers Day 27
- A common convention of response headers (Limit, Remaining, Reset) that tell a client its quota, how many requests are left, and when the window resets.
- x86 Day 2
- The instruction-set family descending from Intel's 1978 8086 — complex, variable-length instructions — that still dominates desktop and much server computing.
- Xavier (Glorot) Initialization Day 201
- A weight initialization scheme setting variance to 2 / (n_in + n_out), designed for Tanh and Sigmoid activations.
- xfail Day 72
- A marker recording that a test is expected to fail, with a written reason. The test still runs, is reported as xfailed rather than failed, and does not turn the suite red. With strict=True, an unexpected pass fails the run — so the day somebody fixes the gap, the stale marker cannot survive unnoticed.
- XGBoost (Extreme Gradient Boosting) Day 165
- An open-source library implementing exact second-order Taylor boosting, sparsity-aware split finding, and explicit L1/L2 leaf regularization.
- XML Day 24
- The Extensible Markup Language, a tag-based text format for structured data that predates JSON and suits document-style and legacy enterprise data.
- XOR Problem Day 197
- A classic non-linearly separable binary classification task where a single-layer perceptron fails to separate (0,0) and (1,1) from (0,1) and (1,0).
- XPath Day 79
- A query language for tree documents, available in Python through lxml. It can express things CSS selectors cannot — selecting an element by its text content, and walking back up or sideways in the tree — which makes it the right tool for label-and-value layouts where the value cell has no class of its own.
- YAGNI Day 63
- Short for "You Aren't Gonna Need It": build only what the current spec requires, and resist adding options, layers, or abstractions for futures that may never arrive. A guard against over-engineering, from the Extreme Programming movement of the late 1990s.
- YAML Day 24
- A text data format that uses indentation instead of braces, favored for configuration files that people edit by hand.
- year-over-year overlay Day 131
- A chart that plots multiple years of a seasonal series on a shared calendar axis (day or month of year) so that comparable periods -- the same month or the same day -- line up directly across years. Correct alignment requires matching by calendar month and day, not by raw ordinal day-of-year, or a leap year silently shifts every date after Feb 29 out of alignment.
- Yeo-Johnson Transformation Day 170
- A parametric power transformation that normalizes continuous features with positive, zero, or negative values.
- yield Day 55
- The keyword that turns a function into a generator: it hands out one value and pauses the function, remembering all its local state, so execution resumes right after the `yield` on the next `next()` call.
- Yield fixture Day 72
- A fixture written as a generator: everything before the yield is setup, the yielded value is what the test receives, and everything after it is teardown. Since pytest 3.0 this is the ordinary way to write any fixture that needs cleanup.
- z-score outlier detection Day 125
- An outlier-detection rule flagging any value more than a chosen number of standard deviations from the mean. Sensitive to the same fragility as the mean itself (Day 116's zero breakdown point): extreme values inflate the standard deviation used to detect them, which can mask the very outliers being searched for.
- Zero vector Day 99
- The vector whose components are all 0. It is the additive identity — adding it moves nothing — it is what you get when you scale any vector by 0 or subtract a vector from itself, its magnitude is 0, and it is the one vector with no direction at all. In code it is the case that breaks normalisation, and a function that does not handle it will either raise or, worse, quietly return a vector of NaNs that poisons everything downstream.
- Zero vector Day 103
- The vector whose every component is 0. It has length 0 and therefore no direction, so there is no unit vector pointing the same way and no angle between it and anything else. Cosine similarity is genuinely undefined for it, and the honest implementation raises rather than returning NaN — an empty document is a real thing that happens in a pipeline, and a NaN sorts unpredictably and spreads through every average it touches.
- zip Day 51
- A built-in that walks two or more iterables in lockstep, handing one item from each per pass and stopping when the shortest runs out; used to march related sequences together.
- zombie process Day 7
- A process that has exited but whose exit code has not yet been collected by its parent, leaving a dead entry in the process table until it is reaped.
- Zone map Day 89
- A summary of the minimum and maximum values in a block of rows, kept by columnar engines such as DuckDB. It lets a query skip whole blocks without any index at all: if a block's dates run from January to March and the query asks for June, the block is never read. It is why the answer to "which index should I create" in an analytical engine is often "none".
- zoneinfo Day 95
- The standard-library module, added in Python 3.9 through PEP 615, that reads the system IANA database. ZoneInfo("Europe/London") loads and caches a zone, zoneinfo.TZPATH lists the directories searched in order, available_timezones() returns every key available, and ZoneInfoNotFoundError — a subclass of KeyError — is raised when nothing on the path provides the requested zone.
- zsh Day 8
- The Z shell, released by Paul Falstad in 1990; the default shell on macOS since Catalina (2019), offering richer completion and customization while staying broadly bash-compatible.