Command Palette

Search for a command to run...

Hectal
Back to the lesson: Topic 6.2 — Mixing Scores (and Why It Is Hard)
RAG and Vector Search · Example 1 of 2

Two score scales side by side

BM25 here uses the same formula and constants as the search lab (k1 = 1.2, b = 0.75). The cosine column is the toy embedder's.

The obvious way to combine BM25 and cosine is to add the scores. They live on different scales, so you must normalise first, and even then the weights you tuned stop working when the data changes.

Change the code and press Run (Ctrl+Enter). Predict what will happen first, then break it on purpose and read what changes. Your edits are saved and match the lesson page.

Ready for more? This phase has 5 hands-on exercises with automatic checks.

Practice questions

Write the code in the editor, run it, then open the model answer to compare.

01

Write mix(keyword, vector, alpha) that takes two lists of scores already scaled to 0..1 and returns the list of mixed scores. Print the result for [1.0, 0.0], [0.0, 1.0] and alpha = 0.7.

02

Write min_max(scores) that returns zeros when all scores are equal. Print it for [2, 4, 6] and for [3, 3].

Explain it without notes

01

Why can't you simply add a BM25 score and a cosine similarity?

02

How does min-max normalisation work, and what is one weakness?

03

Explain how adding a single document can change the order of two unrelated documents in a weighted-sum hybrid.

04

Why can't a min-max normalised score be used to decide that no passage is good enough?

Two score scales side by side
Sign in to run this example in your browser.

Expected output

passage  bm25   cosine
D1       0.000   0.743
D2       0.000   0.000
D3       0.642   0.000
D4       0.000   0.000
D5       0.563   0.316
D6       0.458   0.436
D7       0.000   0.000
D8       5.231   0.816
D9       0.480   0.000
D10      2.430   0.229
D11      0.438   0.000
D12      0.636   0.487
bm25 runs from 0.000 to 5.231; cosine from 0.000 to 0.816
best passage: bm25 says D8, cosine says D8