<?xml version="1.0" encoding="utf-8"?>
<feed xmlns="http://www.w3.org/2005/Atom">
  <generator uri="https://jekyllrb.com/" version="3.10.0">Jekyll</generator>
  <link href="https://nandan.me/writing/notes/feed.xml" rel="self" type="application/atom+xml" />
  <link href="https://nandan.me/writing/notes/" rel="alternate" type="text/html" />
  <updated>2026-05-31T14:06:15+00:00</updated>
  <id>https://nandan.me/writing/notes/feed.xml</id>
  <title type="html">Nandan Joshi — Notes</title>
  <subtitle>Shorter informal pieces — paper reading notes, conference reflections, project-status updates.</subtitle>
  
  
  
    <entry>
      <title type="html">The headline that was within noise</title>
      <link href="https://nandan.me/writing/notes/headline-that-was-within-noise/" rel="alternate" type="text/html" title="The headline that was within noise" />
      <published>2026-05-31T00:00:00+00:00</published>
      <updated>2026-05-31T00:00:00+00:00</updated>
      <id>https://nandan.me/writing/notes/headline-that-was-within-noise/</id>
      <content type="html" xml:base="https://nandan.me/writing/notes/headline-that-was-within-noise/"><![CDATA[<p>Before running the ablation on my retrieval pilot, I wrote down three predictions about which of the three arms — dense vector search, lexical BM25, or their reciprocal-rank fusion — would retrieve best. Writing them first was the useful part: it stopped me from reading the results as a ranking when the data could not support one.</p>

<!--more-->

<h2 id="no-ranking-the-data-supports">No ranking the data supports</h2>

<p>The obvious question — which arm wins Recall@10 — has a numerical answer and no defensible one. Across the same twenty-nine hand-reviewed queries from <a href="/writing/notes/label-review-that-lowered-my-score/">the previous note</a>, where Recall@10, MRR and reciprocal-rank fusion are defined, dense search has the highest Recall@10 at 0.724 and the hybrid the lowest at 0.690. But the paired-difference intervals reported in the ablation all cross zero<sup id="fnref:ci" role="doc-noteref"><a href="#fn:ci" class="footnote" rel="footnote">1</a></sup>: dense over hybrid is +0.034, with an interval from −0.069 to +0.121. The two metrics do not even agree on direction — the hybrid is lowest on Recall@10 and highest on MRR, and that gap is within noise too. At twenty-nine queries there is no ordering to report.</p>

<p>My three predictions were that lexical search would beat the hybrid on queries with one strong single-arm answer, that dense would beat lexical on broad topic questions, and that the hybrid would win on average while losing on the tails. The middle one held in direction only — dense edged lexical on the broad queries, 0.625 to 0.583, well inside its interval. The “wins on average” prediction is exactly the averaged claim this sample cannot settle. The first prediction is the one that survived, and it survived as a single query.</p>

<h2 id="two-results-that-survive-a-small-sample">Two results that survive a small sample</h2>

<p>First, the depth-ten ranking does not survive to depth fifty. Measured at Recall@50 the order inverts: the hybrid moves from last to first, 0.966, and dense from first to last, 0.897. I am not claiming the hybrid significantly wins at depth — same small sample — but a ranking that flips when you move the cutoff is not one to trust at either cutoff.</p>

<p>Second, and more durable because it does not lean on an average, is query 12. Its landmark paper for WASP-96b sits at rank 4 in lexical search and rank 338 in dense — effectively invisible to the dense arm. Fusion then buries it anyway. Reciprocal-rank fusion at k=60 rewards papers that both arms return: a paper one arm ranks, say, 8th and the other 15th scores about 0.028 (1/68 + 1/75), enough to outrank a paper only one arm rates highly — like the WASP-96b result, about 0.016 from its lexical rank of 4. So for query 12 a paper lexical search alone would have placed fourth never reaches the hybrid’s top ten. That one query is the cleanest case for keeping a lexical arm, and a concrete reminder that fusion can bury a paper exactly one arm is sure of.</p>

<h2 id="what-i-will-actually-change">What I will actually change</h2>

<p>The complementarity is real but thin. Pool the top fifty from each arm and 42 of the 49 relevant documents are found by both; only five are unique to one arm, and of those only query 12 is genuinely blind to the other — the rest sit just past the cutoff, at ranks in the fifties to nineties, reachable rather than missed. Two relevant papers neither arm surfaced at depth fifty at all.</p>

<p>I am keeping the hybrid as the stage-one candidate generator regardless. The job of stage one is to land the relevant papers somewhere in the pool a reranker will read, not to order them perfectly — so the number I should be optimising is candidate-set recall at the pool depth, not Recall@10. Recall@10 was the wrong target for a stage that feeds a second stage; it was measuring the reranker’s job before the reranker existed.</p>

<p>This is all still 500 abstracts. The question I am carrying into the corpus-widening work is whether the dense-blind class — papers like query 12’s — grows as the corpus grows, or stays a handful of edge cases. That is the next note.</p>

<div class="footnotes" role="doc-endnotes">
  <ol>
    <li id="fn:ci" role="doc-endnote">
      <p>Each interval comes from ten thousand bootstrap resamples of the per-query scores (seed 20260531). An interval that spans zero means the data are consistent with no difference between the arms. <a href="#fnref:ci" class="reversefootnote" role="doc-backlink">&#8617;</a></p>
    </li>
  </ol>
</div>]]></content>
      <author>
        <name>Nandan Joshi</name>
      </author>
      <category term="AstroLLM" /><category term="Retrieval" /><category term="Evaluation" /><category term="Ablation" />
      <summary type="html">I wrote down three predictions about which retrieval arm would win, then watched the aggregate Recall@10 ranking dissolve into noise at twenty-nine queries. The findings that held up were single queries, not averages.</summary>
    </entry>
  
    <entry>
      <title type="html">The label review that lowered my score</title>
      <link href="https://nandan.me/writing/notes/label-review-that-lowered-my-score/" rel="alternate" type="text/html" title="The label review that lowered my score" />
      <published>2026-05-31T00:00:00+00:00</published>
      <updated>2026-05-31T00:00:00+00:00</updated>
      <id>https://nandan.me/writing/notes/label-review-that-lowered-my-score/</id>
      <content type="html" xml:base="https://nandan.me/writing/notes/label-review-that-lowered-my-score/"><![CDATA[<p>The first pass at my retrieval pilot scored Recall@10 = 0.812 over sixteen graded queries, against 500 real exoplanet-atmosphere abstracts. Then I reviewed the relevance labels those scores were measured against, and the figure fell to 0.690 across twenty-nine queries. The drop is the part of the exercise I trust.</p>

<!--more-->

<h2 id="what-the-pilot-does">What the pilot does</h2>

<p>AstroLLM is meant to cite real papers instead of inventing them, which makes retrieval the grounding layer: given an astronomy question, return the abstracts most likely to answer it. The pilot corpus is 500 abstracts from NASA ADS — the query <code class="language-plaintext highlighter-rouge">abs:"exoplanet atmosphere"</code>, 2018 onward, 500 of 4,845 matches. Two engines run in parallel and are then fused: a dense vector search (BGE-small, 384 dimensions, in pgvector) that matches on meaning, and a lexical BM25 index (SQLite FTS5) that matches on words. Reciprocal-rank fusion<sup id="fnref:rrf" role="doc-noteref"><a href="#fn:rrf" class="footnote" rel="footnote">1</a></sup> merges their two ranked lists. I grade the merged list with Recall@10<sup id="fnref:recall" role="doc-noteref"><a href="#fn:recall" class="footnote" rel="footnote">2</a></sup> and MRR<sup id="fnref:mrr" role="doc-noteref"><a href="#fn:mrr" class="footnote" rel="footnote">3</a></sup>.</p>

<h2 id="why-the-number-moved-down">Why the number moved down</h2>

<p>Three things happened in the review, and only the first was flattering. Re-reading query 06, I found I’d labelled a transmission-spectrum paper relevant to a question about dayside thermal emission — a different observable. Removing it pushed the headline up to 0.844. Had I stopped there, the review would have “confirmed” a score better than the one I started with, which is exactly the kind of review to distrust.</p>

<p>Continuing honestly pulled it back. I graded the conceptual queries I’d skipped on the first pass, and I stopped rounding away real misses: query 11 (WASP-121b) has no correct paper in its top ten, which is a 0.00 and belongs in the denominator. Twenty-nine of thirty queries ended up scored — one had no correct paper anywhere in the corpus — and the corpus-wide figure settled at Recall@10 0.690 and MRR 0.623.</p>

<h2 id="labels-track-relevance-not-rank">Labels track relevance, not rank</h2>

<p>The rule I held to: a label records whether a paper answers the query, not whether the ranker found it. Query 08’s top fused result — ranked first by the system — got marked irrelevant, because the abstract did not address what was asked. Queries 03, 05, and 18 stayed at 0.50, genuine partial misses I could have rationalised away. One correction went the other way: I’d overlooked that a sodium-detection paper was a valid second answer for query 07, which raised its reciprocal rank from 0.17 to 1.00. Corrections in both directions, judged from the abstract, never from where the ranker had placed it.</p>

<h2 id="where-it-is-actually-weak">Where it is actually weak</h2>

<p>Split by query type, the result that matters shows up. On named-target queries — a specific planet, a specific measurement — Recall@10 is 0.794. On broad known-item queries — topic-shaped questions whose answer key is one or two landmark papers — it is 0.542. Lexical search is good with identifiers like WASP-39b; dense search handles paraphrase; the current hybrid first-stage baseline is weaker on topic-shaped questions with no single string to match. A cross-encoder reranker is the next hypothesis for closing that gap, because it reads the query and abstract together instead of scoring them apart.</p>

<p>Two caveats keep me honest about the 0.542. There are only twelve broad known-item queries and seventeen named-target ones — small on both sides. And because those answer keys are landmark papers rather than exhaustive topical relevance, 0.542 is the optimistic reading; true topical recall is likely worse. The corpus is 500 abstracts, too: an earlier 14-document synthetic fixture scored a perfect 1.000/1.000, which only demonstrates that a number without a real, confusable corpus is theatre.</p>

<p>Before building the reranker, though, I wanted to know whether hybrid fusion was even the right first-stage baseline. So I ran an ablation, switching each engine off in turn to see what it contributed. That is the <a href="/writing/notes/headline-that-was-within-noise/">next note</a>.</p>

<div class="footnotes" role="doc-endnotes">
  <ol>
    <li id="fn:rrf" role="doc-endnote">
      <p>Reciprocal-rank fusion — combine two ranked lists using only each document’s rank in each, scoring 1 ÷ (60 + rank) and summing. Because it ignores the raw similarity scores, it needs no normalisation between the dense and lexical engines. <a href="#fnref:rrf" class="reversefootnote" role="doc-backlink">&#8617;</a></p>
    </li>
    <li id="fn:recall" role="doc-endnote">
      <p>Recall@10 — of the papers labelled relevant for a query, the fraction that land in the top ten results, averaged over queries. With a single target paper per query it reduces to whether the right paper made the top ten. <a href="#fnref:recall" class="reversefootnote" role="doc-backlink">&#8617;</a></p>
    </li>
    <li id="fn:mrr" role="doc-endnote">
      <p>MRR, mean reciprocal rank — 1 ÷ (rank of the first relevant hit), averaged over queries: first place scores 1.0, third place 0.33, not found 0. It rewards ranking the answer high rather than merely surfacing it. <a href="#fnref:mrr" class="reversefootnote" role="doc-backlink">&#8617;</a></p>
    </li>
  </ol>
</div>]]></content>
      <author>
        <name>Nandan Joshi</name>
      </author>
      <category term="AstroLLM" /><category term="Retrieval" /><category term="Evaluation" />
      <summary type="html">A retrieval pilot over 500 real exoplanet papers scored Recall@10 in the low 0.8s; reviewing my own relevance labels pulled it down to 0.69. The drop is the part worth trusting.</summary>
    </entry>
  
  
</feed>
