Sari la conținut
16/30Capitolul 16 din 30

Context window, token și factura, măsurate

O conversație de 40 de ture costă de 22 ori propria lungime în token de input. Caching reduce 68%; un timestamp greșit adaugă 20%.

Pe această pagină

Iată o conversație de suport de patruzeci de ture, facturată tură cu tură. Nu e nimic neobișnuit în ea: un dezvoltator întreabă despre un API, un assistant răspunde într-un paragraf sau două. Întregul schimb are 5.090 token de text — cam opt pagini.

turăprompt tokenstext nououtputcostul acestei turetotal curent
121318183$0.002622$0.002622
589214123$0.003260$0.014354
101.65619114$0.004680$0.035530
202.86818103$0.006972$0.094426
303.9412099$0.009070$0.174170
404.94717142$0.011598$0.274386

Citește împreună a doua și a treia coloană. La tura 40, utilizatorul a tastat șaptesprezece token și a fost taxat pentru 4.947. Întrebarea nu era mai grea decât prima; era mai scurtă. Ce s-a schimbat este că cererea a purtat cu ea întreaga conversație, din nou, pentru a patruzecea oară.

Total input tokens facturați în cele patruzeci de apeluri: 112.617. Conversația are 5.090 token lungime. Ai plătit pentru ea de douăzeci și două de ori.

Acest capitol explică de ce se întâmplă asta, cum se numește pe factura fiecărui provider și asupra cărora dintre cele cinci lucruri pentru care ești taxat poți face ceva.

Afișează detaliile

Ce are nevoie acest capitol din Partea II.

  • Capitolul 7 a construit tokenizer-ul. Un token este unitatea și aici — aceeași unitate, acum cu preț.
  • Capitolul 9 a derivat self-attention și costul său O(n2)O(n^2), în caseta despre notația asimptotică. Costul acela este motivul pentru care există o limită, iar aici este legat, nu explicat din nou.
  • Capitolul 13 a măsurat prefill față de decode și a calculat cât ocupă un KV cache. Cele două faze sunt ceea ce cumpără, de fapt, coloanele de input și output de mai sus.

Restul este TypeScript, pentru că aceasta este contabilitate pentru un apel remote, nu matematică despre un model.

Cea mai scumpă confuzie din acest business este ideea că un model își amintește o conversație.

Nu o face, iar mecanismul din Capitolul 13 spune exact de ce. Starea unui transformer în timpul generării este KV cache: cheile și valorile calculate pentru fiecare token din secvență. Acest cache trăiește pe durata unei singure cereri. Când cererea se termină, procesul care îl ținea este liber să servească pe altcineva, iar cache-ul a dispărut. Nu există un spațiu de stocare per utilizator de cealaltă parte și nici o sesiune.

Așa că următoarea cerere trebuie să vină purtând tot ce ar trebui să știe modelul, iar modelul reconstruiește acea stare rulând un forward pass peste întregul prompt înainte să emită un singur token nou. Capitolul 15 a numit prompt „întreaga stare”. Acesta este motivul fizic: prompt este starea completă pentru că nimic altceva nu supraviețuiește apelului.

Context window este lungimea maximă a acelui prompt plus răspunsul său. Este un plafon pentru câtă stare poți reconstrui, nu un container care păstrează ceva între cereri. Să o numești „memoria modelului” inversează cauzalitatea — nu umpli o memorie, plătești ca să restabilești una.

De acolo vine acel douăzeci și doi. Tura nn poartă toate cele n1n-1 ture anterioare, deci input-ul total într-o conversație de nn ture este suma unei serii crescătoare, adică este pătratic:

total input  =  i=1n(s+hi)  =  Θ(n2)\text{total input} \;=\; \sum_{i=1}^{n} \big(s + h_i\big) \;=\; \Theta(n^2)

unde ss este system prompt, iar hih_i istoricul la tura ii. Potrivirea input-ului cumulativ măsurat la an2+bnan^2 + bn pe cele patruzeci de ture dă 60.22n2+432.25n60.22\,n^2 + 432.25\,n, care prezice 113.645 token la tura 40, față de 112.617 măsurați. Termenul pătratic domină, iar termenul liniar este ceea ce a tastat efectiv utilizatorul.

Consecința este propoziția de reținut din acest capitol: factura ta crește cu pătratul conversației, nu cu ultima întrebare. Aceleași patruzeci de întrebări puse fără niciun istoric costă $0.066036. Păstrarea istoricului costă $0.274386. Istoricul a înmulțit factura cu 4,2 și va continua să o înmulțească, pentru că multiplicatorul este lungimea conversației.

Fereastra este finită din două motive care trag în aceeași direcție. Primul este cel din Capitolul 9: attention compară fiecare token cu fiecare alt token, așa că munca acelui strat crește cu pătratul lungimii secvenței. Al doilea este memoria: KV cache crește liniar cu lungimea secvenței, iar Capitolul 13 a făcut acea aritmetică — la secvențe lungi este mai mare decât greutățile.

Ambele limite au fost atacate și niciuna nu a fost eliminată. FlashAttention1 reorganizează calculul astfel încât citește și scrie mult mai puțin în memoria cu lățime mare de bandă, ceea ce face secvențele lungi practice fără să schimbe costul asimptotic. Position Interpolation2 și YaRN3 extind fereastra utilizabilă a unui model antrenat prin rescalarea encodărilor poziționale din Capitolul 9, nu prin reantrenare. Împreună, ele explică de ce ferestrele au trecut de la 2K la 1M în cinci ani.

Ce nu au făcut este să facă gratuit contextele lungi. Au ridicat plafonul și au îmblânzit panta. Panta încă există, iar ea este ceea ce măsoară nivelurile de preț de mai târziu din acest capitol.

Aproape fiecare calculator de costuri de pe internet modelează un apel API ca input tokens înmulțiți cu un preț de input plus output tokens înmulțiți cu un preț de output. Era adevărat în 2023. Acum este greșit într-un mod care produce facturi eronate cu un factor de doi sau mai mult, în ambele direcții.

Există cinci categorii de token facturabile:

găleatăce estepreț tipic, relativ la input
uncached inputprompt tokens pe care modelul a trebuit să îi proceseze proaspăt
cache readprompt tokens serviți dintr-un prefix stocat0,1×
cache writeprompt tokens stocați în cache la acest apel1,25× până la 2×
outputtokens generați de model și trimiși către tine5× până la 6×
reasoningtokens generați de model și netrimiși către tinetarif de output

Trei dintre cele cinci nu existau ca linii separate acum doi ani, iar cele două linii de cache sunt cele pe care oamenii le greșesc, pentru că un cache write costă mai mult decât input obișnuit, nu mai puțin. Plătești o primă ca să stochezi ceva, astfel încât să poți plăti un discount ca să îl citești înapoi, iar dacă schimbul merită depinde complet de câte ori îl citești.

Găleata de reasoning este cea din Capitolul 12, acum cu preț, și poartă un detaliu care merită spus limpede: documentația Google spune că prețul „se bazează pe toți thought tokens pe care modelul trebuie să îi genereze, deși doar rezumatul este output din API.”4 Ești facturat pentru tokens care nu îți sunt transmiși niciodată. Este singura găleată ale cărei conținuturi nu le poți număra, inspecta sau verifica.

Acum partea care face din asta o problemă de normalizare, nu una de înmulțire. Fiecare provider raportează aceste găleți sub nume diferite și — aceasta este capcana — doi folosesc același cuvânt pentru două cantități diferite.

Ia un apel: 4.837 tokens citiți din cache, 110 proaspeți, 142 output tokens vizibili, 300 reasoning tokens.

three usage payloads, one callJSON
// OpenAI-compatible
{ "usage": { "prompt_tokens": 4947,
             "prompt_tokens_details": { "cached_tokens": 4837 },
             "completion_tokens": 442,
             "completion_tokens_details": { "reasoning_tokens": 300 } } }

// Anthropic
{ "usage": { "input_tokens": 110,
             "cache_read_input_tokens": 4837,
             "cache_creation_input_tokens": 0,
             "output_tokens": 442 } }

// Gemini
{ "usageMetadata": { "promptTokenCount": 4947,
                     "cachedContentTokenCount": 4837,
                     "candidatesTokenCount": 142,
                     "thoughtsTokenCount": 300 } }

Uită-te la prompt_tokens: 4947 și input_tokens: 110. Ambele câmpuri sunt numărul de input tokens pentru același prompt. Cel de la OpenAI include tokens din cache; cel de la Anthropic îi exclude — documentația sa afirmă identitatea explicit, total_input_tokens = cache_read_input_tokens + cache_creation_input_tokens + input_tokens.5 input_tokens la Anthropic înseamnă „tokens de după ultimul tău cache breakpoint”.

Și uită-te la output. OpenAI și Anthropic raportează ambele 442, care include deja cei 300 reasoning tokens. Gemini raportează 142 și pune cei 300 într-un câmp separat. Capitolul 12 a semnalat asta ca incompatibilitate între două moduri de a număra aceeași muncă; aici este cât costă.

Un normalizator are treizeci de linii și nu este opțional:

normalise.tsTS
export interface Usage {
  promptTokens?: number;        // input, NOT cached
  cachedInputTokens?: number;   // read from cache
  cacheWriteTokens?: number;    // written to cache on this call
  completionTokens?: number;    // output
  reasoningTokens?: number;     // billed apart from output (Gemini only)
}

const num = (v: unknown) => (typeof v === "number" && isFinite(v) ? v : 0);

export const fromOpenAI = (raw: any): Usage => {
  const u = raw.usage ?? {}, d = u.prompt_tokens_details ?? {};
  const cached = num(d.cached_tokens), write = num(d.cache_write_tokens);
  return {
    promptTokens: Math.max(0, num(u.prompt_tokens) - cached - write), 
    cachedInputTokens: cached,
    cacheWriteTokens: write,
    completionTokens: num(u.completion_tokens),   // reasoning already inside
    reasoningTokens: 0,
  };
};

export const fromAnthropic = (raw: any): Usage => {
  const u = raw.usage ?? {};
  return {
    promptTokens: num(u.input_tokens),            // already excludes cache
    cachedInputTokens: num(u.cache_read_input_tokens),
    cacheWriteTokens: num(u.cache_creation_input_tokens),
    completionTokens: num(u.output_tokens),
    reasoningTokens: 0,
  };
};

export const fromGemini = (raw: any): Usage => {
  const m = raw.usageMetadata ?? {}, cached = num(m.cachedContentTokenCount);
  return {
    promptTokens: Math.max(0, num(m.promptTokenCount) - cached),
    cachedInputTokens: cached,
    cacheWriteTokens: 0,
    completionTokens: num(m.candidatesTokenCount), // EXCLUDES thinking
    reasoningTokens: num(m.thoughtsTokenCount),    // billed at output rate
  };
};

Rulează cele trei payload-uri de mai sus prin cei trei cititori și toate trei produc același Usage și, prin urmare, același număr: $0.006491. Acel acord este întregul scop al scrierii stratului.

Dacă greșești, iată cât costă, pe același apel:

greșealăfacturateroare
tratezi cached_tokens ca suplimentar față de prompt_tokens$0.0161652,49× — taxezi prompt de două ori
tratezi cache reads ca gratuite în loc de 0,1×$0.0055240,85× — înghiți 15 %
citești candidatesTokenCount și ignori thoughtsTokenCount$0.00289155 % din apel dispare

A treia este cea periculoasă, pentru că eșuează tăcut în direcția veștilor bune. Dashboard-ul tău arată că un reasoning model costă mai puțin de jumătate din cât costă de fapt și nicăieri nu apare vreo eroare.

Cu gălețile normalizate, funcția de cost este scurtă. Singura parte mai puțin evidentă este căutarea nivelului, pe care o explică secțiunea următoare:

cost.tsTS
export interface Tier { maxPromptTokens: number | null; price: number }
export interface Pricing {
  input: Tier[]; output: Tier[];
  cachedInput?: Tier[]; cacheWrite?: Tier[]; reasoning?: Tier[];
}

const tierPrice = (tiers: Tier[] | undefined, contextSize: number, fallback?: Tier[]) => {
  const table = tiers ?? fallback;
  if (!table?.length) return 0;
  const sorted = [...table].sort(
    (a, b) => (a.maxPromptTokens ?? Infinity) - (b.maxPromptTokens ?? Infinity));
  for (const t of sorted)
    if (t.maxPromptTokens === null || contextSize <= t.maxPromptTokens) return t.price;
  return sorted[sorted.length - 1].price;
};

export function computeCost(pricing: Pricing, usage: Usage): number {
  const fresh = usage.promptTokens ?? 0;
  const read  = usage.cachedInputTokens ?? 0;
  const write = usage.cacheWriteTokens ?? 0;
  const out   = usage.completionTokens ?? 0;
  const think = usage.reasoningTokens ?? 0;
  const contextSize = fresh + read + write;   // the tier depends on the WHOLE prompt
  return fresh * tierPrice(pricing.input, contextSize)
       + read  * tierPrice(pricing.cachedInput, contextSize, pricing.input)
       + write * tierPrice(pricing.cacheWrite,  contextSize, pricing.input)
       + out   * tierPrice(pricing.output, contextSize)
       + think * tierPrice(pricing.reasoning, contextSize, pricing.output);
}

Două decizii de design de acolo merită apărate. Fallback-urile — prețurile de cache care cad înapoi la input, reasoning la output — codifică ce înseamnă un tabel lipsă: reasoning tokens pe Gemini sunt facturați la tariful de output, deci un preț reasoning absent nu este zero, este prețul de output. Iar contextSize însumează toate cele trei găleți de input, nu doar pe cele proaspete, pentru că nivelul este ales după cât de lung este prompt, nu după cât din el ți s-a taxat la preț întreg.

Un prompt cache stochează starea calculată de model pentru un prefix al prompt-ului tău, astfel încât o cerere ulterioară cu același prefix sare peste recalculare. Patru proprietăți decurg din cuvântul „prefix” și toate patru îi surprind pe oameni.

Cache-ul potrivește de la începutul prompt-ului randat înainte și se oprește la primul byte care diferă. Nu există credit parțial pentru conținut care apare mai târziu într-o ordine diferită. OpenAI o spune direct: „reutilizarea cache-ului cere ca întregul prefix randat să se potrivească.”6

Sub ea, nimic nu este cached și nu se întoarce nicio eroare. Pe OpenAI minimul este 1.024 tokens pentru GPT-5.6 și ulterior și 2.048 pentru modelele mai vechi. Pe Anthropic variază de la 512 la 4.096 în funcție de model — 1.024 pentru Claude Sonnet 4.5, 4.096 pentru Claude Haiku 4.5. Dacă ambele câmpuri de cache revin zero, de obicei acesta este motivul.

Scrierea costă mai mult decât citirea și mai mult decât lipsa caching

Link către secțiunea: Scrierea costă mai mult decât citirea și mai mult decât lipsa caching

Pe OpenAI și Anthropic, un cache write este 1,25× tariful de uncached input pentru cache-ul cu viață scurtă, iar cache-ul de o oră de la Anthropic este 2×. Un read este 0,1×. Google nu taxează scrierea, dar închiriază stocarea: $4.50 per milion de tokens pe oră pe Gemini 2.5 Pro.

Intrarea implicită de la Anthropic trăiește cinci minute, reîmprospătată gratuit la fiecare hit. Cea de la OpenAI este de cel puțin treizeci de minute după cea mai recentă scriere sau reutilizare. Iar OpenAI notează că stările cached trăiesc pe mașini individuale, deci o cerere lovește cache-ul doar dacă este rutată către mașina care ține intrarea — ceea ce influențează prompt_cache_key, fără să garanteze.

Punctul de break-even este destul de mic ca să îl ții minte, iar documentația OpenAI face aritmetica: să scrii un prefix o dată și să îl reutilizezi o dată costă 1,35× costul său obișnuit de input, față de 2× pentru procesarea lui de două ori uncached; pe zece cereri, o scriere și nouă citiri costă 2,15× față de 10×. O singură reutilizare plătește scrierea. Anthropic ajunge în același loc: o citire pentru cache-ul de cinci minute, două pentru cache-ul de o oră.

Acum conversația de patruzeci de ture din nou, cu caching activ și prefixul stabil:

uncached inputcache readscache writestotal
fără cache112.617$0.274386
caching2.887104.7834.947$0.088250

Cu șaizeci și opt la sută mai ieftin, iar trei numere din acel tabel merită atenție.

Cache-ul nu intră în joc până la tura 6. Prompt nu ajunge la 1.024 tokens până atunci, deci primele cinci ture sunt facturate exact ca înainte — iar a șasea este facturată mai rău, cu prima de scriere de 1,25×, pentru că este tura care umple cache-ul. Prima citire sosește la tura 7. Cei 2.887 uncached tokens din tabel sunt aritmetica: valoarea a cinci ture, nu șase. Caching este un discount pentru prompt-uri lungi, iar o conversație scurtă nu câștigă nimic din el.

Prima de scriere este $0.002474, adică 2,8 % din factura cached. Fiecare tură își scrie coada nouă, de patruzeci de ori, iar întreaga primă de scriere este o eroare de rotunjire față de ce au economisit citirile. Merită să înțelegi precis taxa de scriere ca să nu te mai îngrijorezi pentru ea.

Doar 2.887 tokens au fost taxați la preț întreg de input din 112.617. Așa arată un cache care funcționează: aproape totul este un read.

Ordinea prompt-ului decide dacă se întâmplă ceva din toate acestea

Link către secțiunea: Ordinea prompt-ului decide dacă se întâmplă ceva din toate acestea

Iată eșecul care costă bani reali și este un bug de o singură linie.

Pune ceva care se schimbă la fiecare apel aproape de începutul prompt-ului — un timestamp, un id de cerere, numele utilizatorului, o linie „astăzi este”, un document proaspăt recuperat — și prefixul diferă de la primul byte. Nimic nu se potrivește. Fiecare apel este un miss. Și pentru că fiecare apel prezintă un prefix nou, fiecare apel și scrie.

Aceeași conversație, aceleași patruzeci de ture, caching activ, cu un timestamp per apel în partea de sus a system prompt:

totalfață de
fără caching deloc$0.274386
caching, prefix stabil$0.088250−67,8 %
caching, prefix volatil$0.329251+20,0 %

Activarea prompt caching a făcut conversația cu douăzeci la sută mai scumpă decât fără el. Ai plătit prima de scriere de 1,25× pe 109.730 tokens și ai citit înapoi zero. Nu există eroare, nu există avertisment, iar funcția este pornită.

Deci regula, și este tot prompt caching într-o singură linie: conținut stabil în față, conținut variabil în spate. Instrucțiuni de sistem, definiții de tool și materiale de referință primele; timestamp-uri, identitatea utilizatorului și întrebarea curentă ultimele. Anthropic face ierarhia explicită — cache-ul urmează toolssystemmessages, iar o schimbare la orice nivel invalidează acel nivel și tot ce vine după el, așa că editarea unei singure descrieri de tool invalidează întregul cache.5

Două consecințe de care oamenii se împiedică. Schimbarea tool-urilor activate schimbă definițiile de tool, deci un feature flag care adaugă un tool pentru unii utilizatori îți împarte cache-ul în două. Iar pe Anthropic, activarea sau dezactivarea căutării web ori a citărilor modifică system prompt, ceea ce invalidează cache-urile de sistem și de mesaje fără să atingi o linie din propriul text.

Răspunsul evident la o factură pătratică este să nu mai trimiți tot istoricul: păstrezi ultimele douăsprezece mesaje și le arunci pe restul. Reduce factura, și de obicei este mișcarea greșită, iar măsurătoarea arată de ce.

strategietotalfață de istoric complet + cache
istoric complet, fără cache$0.274386+211 %
istoric complet, caching$0.088250
ultimele 12 mesaje, fără cache$0.118712+35 %
ultimele 12 mesaje, caching pornit$0.122546+39 %

Trunchierea la o fereastră de douăsprezece mesaje este cu 57 % mai ieftină decât trimiterea tuturor mesajelor uncached — comparația pe care o face toată lumea și motivul pentru care tehnica este populară. Dar este cu 39 % mai scumpă decât trimiterea tuturor mesajelor cu un cache funcțional, iar pornirea caching alături de trunchiere o face puțin mai rea, nu mai bună.

Mecanismul este din nou prefixul. O fereastră glisantă aruncă cel mai vechi mesaj la fiecare tură, deci prompt nu mai începe de unde începea data trecută și fiecare tură prezintă un prefix nou. Ghidul OpenAI spune exact asta: „sumarizarea, compactarea sau context truncation pot schimba prefixul și reseta reutilizarea cache-ului.”6 La tura 40, prompt-ul cu fereastră are 813 tokens, sub minimul de 1.024 tokens, deci nu poate fi cached deloc.

Iar banii sunt jumătatea ieftină a costului. Ce ai aruncat este instrucțiunea pe care utilizatorul a dat-o la tura 2 și de care modelul avea nevoie la tura 40. Trunchierea schimbă o factură pe care o poți vedea pe un eșec pe care nu îl poți vedea, iar să o faci corect — compactare, note structurate ținute în afara ferestrei, recuperarea istoricului la cerere — este subiectul Capitolului 24.

Trecerea unui nivel reprețuiește întreaga cerere

Link către secțiunea: Trecerea unui nivel reprețuiește întreaga cerere

Contextele lungi nu sunt mai scumpe doar pentru că sunt mai lungi. După un prag, sunt mai scumpe per token, iar pragul se aplică retroactiv întregului prompt.

Pagina de model OpenAI pentru gpt-5.6-terra o spune într-o propoziție: „Prompt-urile cu >272K input tokens sunt prețuite la 2x input și 1.5x output pentru întreaga cerere.”7 Nu pentru exces. Pentru tot.

the most expensive token you will ever sendTEXT
prompt 271,999 + 500 output  ->  $0.5500
prompt 272,000 + 500 output  ->  $0.5500
prompt 272,001 + 500 output  ->  $1.0970

Un token, cincizeci și cinci de cenți. Dacă serviciul tău construiește prompt-uri din documente recuperate a căror dimensiune nu o controlezi, ai o prăpastie în modelul de cost la o limită pe care nimeni din echipa ta nu a notat-o.

Prețurile Google funcționează la fel cu un prag de 200.000 de token: Gemini 2.5 Pro este $1.25 per milion de input tokens pentru prompt-uri până la 200K și $2.50 peste, output trecând de la $10.00 la $15.00.8 Anthropic a mers în direcția opusă — la 6 septembrie 2026 documentația sa spune că Claude 4.6 și modelele ulterioare includ fereastra completă de un milion de token la preț standard, deci „o cerere de 900k-token este facturată la același tarif per-token ca o cerere de 9k-token.”9 Modelele anterioare păstrau suprataxa.

De aceea un preț nu este un număr. Un preț este un tabel de niveluri indexate după lungimea prompt-ului, ceea ce explică rolul lui Tier[] în funcția de cost, și de aceea computeCost selectează nivelul folosind întregul prompt, nu fiecare găleată separat.

Prefill, decode și de ce output costă de șase ori mai mult decât input

Link către secțiunea: Prefill, decode și de ce output costă de șase ori mai mult decât input

Cele cinci găleți se mapează pe cele două faze din Capitolul 13, iar odată ce vezi maparea, rapoartele de preț nu mai par arbitrare.

Input tokens sunt prefill. Întregul prompt trece prin model într-o singură trecere, procesat în paralel — înmulțiri mari de matrice, limitate de compute. Costul per token este mic, iar aceasta este faza care stabilește time to first token: un prompt de 4.947 tokens are 4.947 tokens de prefill de făcut înainte să apară primul cuvânt.

Output tokens sunt decode. Sunt produși unul câte unul, fiecare un forward pass complet care citește întregul KV cache, cu GPU-ul mai mult așteptând memoria decât calculând. Aceasta este faza care stabilește tokens per second, nu poate fi paralelizată în interiorul unui răspuns și explică de ce output costă cam de șase ori input pe modelul prețuit aici: $12.00 față de $2.00 per milion de tokens.

Trei consecințe decurg direct. Un cache read înlocuiește munca de prefill, deci cumpără latență și bani în același timp — același discount apare ca factură mai mică și așteptare mai scurtă până la primul token. Reasoning tokens sunt decode pe care nu îl vezi, motiv pentru care un reasoning model nu transmite nimic timp de câteva secunde și apoi răspunde repede: Capitolul 12 a avertizat despre consecința de interfață, iar aceasta este consecința de factură. Și oprirea unui stream nu oprește generareaCapitolul 14 a construit anularea și a lăsat prețul pentru acest capitol, iar prețul este numărul complet de output, pentru că tokens sunt produși și facturați indiferent dacă ascultă cineva. Același lucru este valabil pentru răspunsul pe care nu îl păstrează nimeni: regenerarea de cinci ori a unui răspuns de la tura 40 costă $0.057990 pentru cel rămas pe ecran.

Tokenizer-ul din Capitolul 7 era Python și a rămas acolo. Bugetarea se întâmplă în serverul care construiește cererea, deci trebuie să se întâmple aici, iar exact trei niveluri de acuratețe sunt disponibile.

Nivelul unu: numără local. js-tiktoken livrează aceleași tabele BPE merge ca tiktoken din Python, deci oferă un număr identic byte cu byte pentru encodările OpenAI, fără apel de rețea:

count.tsTS
import { getEncoding } from "js-tiktoken";

const enc = getEncoding("o200k_base");
const PER_MESSAGE = 4;   // role and delimiters added by the chat template
const PER_REPLY = 3;     // priming for the assistant turn

export function promptTokens(messages: { role: string; content: string }[]) {
  return messages.reduce(
    (sum, m) => sum + enc.encode(m.content).length + PER_MESSAGE, PER_REPLY);
}

Cele două constante contează și sunt locul unde numărătorile locale deviază. Textul tău nu este ceea ce ajunge tokenized — chat template din Capitolul 11 învelește mai întâi fiecare mesaj în markeri de rol, iar aceia sunt tokens pentru care plătești. Patru per mesaj și trei pentru pregătirea răspunsului este aproximația convențională pentru modelele de chat OpenAI; peste cele optzeci și unu de mesaje ale conversației de mai sus adună 324 tokens, 6,4 % din lungimea ei. Numărătorile de aici au fost verificate încrucișat cu tiktoken din Python din Capitolul 7 pe toate cele optzeci și unu de stringuri și sunt identice.

Nivelul doi: întreabă provider-ul. Anthropic expune /v1/messages/count_tokens, iar Google expune count_tokens, ambele acceptând aceeași formă de cerere ca un apel real și întorcând gratuit un număr de input tokens. Folosește-le când nu poți număra local — iar pentru Anthropic nu poți număra local, pentru că tokenizer-ul său nu este publicat. Documentația Anthropic este atentă la ce îți oferă: numărul „este o estimare” și „poate include tokens adăugați automat de Anthropic pentru optimizări de sistem”, pentru care „nu ești facturat”.10

Nivelul trei: citește usage în răspuns. Acela este adevărul și sosește după ce banii au fost cheltuiți. Exact de aceea există primele două niveluri — ca să decizi dacă trimiți cererea, nu ca să facturezi pentru ea.

Lucrurile pentru care plătești și pe care nu ți le arată nimeni

Link către secțiunea: Lucrurile pentru care plătești și pe care nu ți le arată nimeni

Patru elemente care nu apar ca elemente separate.

System prompt, plătit la fiecare apel. Cel de mai sus are 192 tokens cu overhead-ul de template inclus. În patruzeci de apeluri înseamnă 7.680 tokens — 5,6 % din întreaga factură a acestei conversații, pentru opt linii scrise o singură dată. Este și cel mai bun candidat posibil pentru cache, fiind și stabil, și primul.

Definițiile de tool. Numele, descrierea și schema JSON ale fiecărui tool pleacă la fiecare cerere, iar provider-ii adaugă scaffolding deasupra. Anthropic publică numărul: activarea tool-urilor adaugă un system prompt ascuns de 496 tokens pe Claude Sonnet 4.5 cu tool_choice setat la auto, sau 588 cu any ori un tool numit.9 Asta înainte de propriile tale scheme. Capitolul 18 construiește catalogul; Capitolul 24 măsoară cât mănâncă.

Fiecare generare, inclusiv cele pe care le arunci. Cinci regenerări costă de cinci ori. Chat-ul arată una.

Gânduri care nu îți sunt arătate. Facturarea se bazează pe toți thought tokens, deși doar un rezumat este returnat, iar nicio contabilitate a ta nu poate audita acel număr.

Să ai 200K token nu înseamnă să îi folosești

Link către secțiunea: Să ai 200K token nu înseamnă să îi folosești

Un avertisment de final, pentru că este următorul gând natural și răspunsul nu este cel evident.

O fereastră de un milion de token nu înseamnă un milion de tokens utilizabili. Acuratețea recuperării se degradează cu poziția: Liu et al. au constatat că modelele localizează informația fiabil la începutul și la finalul unui input lung și mult mai puțin fiabil la mijloc.11 O fereastră mai mare cumpără abilitatea de a trimite mai mult, nu certitudinea că va fi citit.

Fenomenul acesta este măsurat o dată în acest curs — rata de retrieval în nouă poziții din același prompt de 853 tokens — și aparține Capitolului 24, unde schimbă ce face un agent. Este citat aici pentru că schimbă ce ar trebui să cumperi: cel mai ieftin token este cel pe care nu l-ai trimis.

Acum poți prezice cât va costa un apel înainte să îl faci, poți citi cât a costat după și poți face diferența între cele două. Asta acoperă totul despre cerere, mai puțin partea pe care nu ai atins-o: butoanele.

Capitolul 17 este despre sampling — temperature, top-p, top-k, penalizările și determinismul pe care nu îl ai. Începe prin a demonta cea mai răspândită eroare din domeniu: că temperature este un cadran al creativității. Nu este: temperature împarte logits din Capitolul 4 înainte de softmax, iar creșterea ei nu face modelul imaginativ, ci crește probabilitatea tokens pe care modelul însuși i-a evaluat ca mai slabi. De acolo, de ce greedy decoding produce text măsurabil mai prost decât sampling, de ce top-k și top-p eșuează pe forme opuse de distribuție și experimentul care încheie capitolul: douăzeci de forward passes identice la temperature 0 se întorc identice bit cu bit când modelul rulează singur, iar punerea aceluiași prompt într-un batch alături de cererile altcuiva mută 97 % din logits.

Nu toate se potrivesc. Motivul începe cu caseta despre virgulă mobilă din Capitolul 2.


Toate prețurile, pragurile și multiplicatorii din acest capitol au fost citiți de pe paginile proprii ale provider-ilor la 6 septembrie 2026 și sunt declarate cu acea dată pentru că se vor schimba. Metoda contează mai mult decât numerele: gălețile, regula prefixului și aritmetica nivelurilor au fost stabile timp de doi ani, în timp ce fiecare cifră din ele s-a mișcat.

Cursul Stanford CS336, prelegerea 2, Resource accounting, este cel mai apropiat tratament academic al acestui material și următoarea lectură potrivită: face aceeași aritmetică pe partea de training pe care acest capitol o face pe partea de inference. Numărătorile de token de aici au fost produse cu js-tiktoken 1.0.21 folosind encodările o200k_base și cl100k_base, pe o conversație de patruzeci de ture cu 5.090 tokens; overhead-ul de template per mesaj este aproximația convențională patru-plus-trei și este menționat oriunde este inclus. Cifrele de cache, niveluri și trunchiere sunt regulile de preț documentate aplicate acelor numărători de token măsurate, nu observații ale unor răspunsuri API live — nu a fost făcut niciun apel plătit pentru a produce acest capitol, ceea ce este și motivul onest pentru care afirmațiile despre latență sunt calitative, iar cele despre costuri nu.

  1. Dao, T., Fu, D. Y., Ermon, S., Rudra, A. and Ré, C. FlashAttention: Fast and Memory-Efficient Exact Attention with IO-Awareness. arXiv:2205.14135 (2022). De ce plafonul s-a mutat fără ca prețul asimptotic să se schimbe.

  2. Chen, S., Wong, S., Chen, L. and Tian, Y. Extending Context Window of Large Language Models via Positional Interpolation. arXiv:2306.15595 (2023).

  3. Peng, B., Quesnelle, J., Fan, H. and Shippole, E. YaRN: Efficient Context Window Extension of Large Language Models. arXiv:2309.00071 (2023).

  4. Google, Thinking, ai.google.dev/gemini-api/docs/thinking, și Token counting, ai.google.dev/gemini-api/docs/tokens, ambele accesate 2026-09-06. „Prețul se bazează pe toți thought tokens pe care modelul trebuie să îi genereze, deși doar rezumatul este output din API.” Obiectul de usage raportează total_input_tokens, total_output_tokens, total_thought_tokens, total_cached_tokens, total_tool_use_tokens și total_tokens — șase găleți, cu gânduri și tool use în afara numărului de output. Numele anterior al câmpului pentru aceeași cantitate, încă returnat de suprafața generateContent, este thoughtsTokenCount, documentat pe o a treia pagină, ai.google.dev/gemini-api/docs/generate-content/thinking.

  5. Anthropic, Prompt caching, docs.anthropic.com/en/docs/build-with-claude/prompt-caching, accesat 2026-09-06. Sursa pentru ierarhia de invalidare toolssystemmessages și tabelul său; lungimile minime cacheable per model; identitatea total_input_tokens = cache_read_input_tokens + cache_creation_input_tokens + input_tokens; și durata de viață implicită de cinci minute reîmprospătată fără taxă la fiecare hit. 2

  6. OpenAI, Prompt caching, platform.openai.com/docs/guides/prompt-caching, accesat 2026-09-06. Sursa pentru: regula întregului prefix randat; prefixul minim cacheable (1.024 input tokens vizibili pe GPT-5.6 și ulterior, 2.048 mai devreme); multiplicatorii 1,25× pentru scriere și 0,1× pentru citire și absența oricărei taxe de scriere pe GPT-5.5 și anterior; durata de viață de 30 de minute; limitele de patru scrieri per cerere și cincizeci de breakpoint-uri; nota despre afinitatea de mașină și prompt_cache_key; exemplele de break-even calculate 1,35×, 2,15× și 10×; și afirmația că sumarizarea, compactarea sau trunchierea resetează reutilizarea cache-ului. 2

  7. OpenAI, Prețuri (platform.openai.com/docs/pricing) și pagina de model pentru gpt-5.6-terra, ambele accesate 2026-09-06. gpt-5.6-terra, nivel de serviciu standard, per milion de tokens: input $2.00, cached input $0.20, cache writes $2.50, output $12.00; long context input $4.00, cached $0.40, writes $5.00, output $18.00; „prompt-urile cu >272K input tokens sunt prețuite la 2x input și 1.5x output pentru întreaga cerere”; context window 1.050.000 tokens cu un maxim de 922.000 input tokens. Același tabel listează gpt-6-astra la $10.00/$1.00/$12.50/$50.00 și gpt-5.6-luna la $0.20/$0.02/$0.25/$1.20. Fiecare cost calculat din acest capitol folosește tarifele standard de context scurt gpt-5.6-terra.

  8. Google, Prețurile Gemini Developer API, ai.google.dev/gemini-api/docs/pricing, accesat 2026-09-06. Gemini 2.5 Pro, per milion de tokens: input $1.25 pentru prompt-uri până la 200K și $2.50 peste; output $10.00 și $15.00, în ambele cazuri etichetate „including thinking tokens”; context caching $0.125 și $0.25, plus o taxă de stocare de $4.50 per milion de tokens pe oră. Gemini 3.1 Pro Preview folosește același prag de 200K la $2.00/$4.00 input și $12.00/$18.00 output.

  9. Anthropic, Prețuri, docs.anthropic.com/en/docs/about-claude/pricing, accesat 2026-09-06. Per milion de tokens, input de bază / cache write 5 minute / cache write 1 oră / cache read / output: Claude Sonnet 4.5 $3 / $3.75 / $6 / $0.30 / $15; Claude Haiku 4.5 $1 / $1.25 / $2 / $0.10 / $5; Claude Opus 5 $5 / $6.25 / $10 / $0.50 / $25. Multiplicatori: 1,25× pentru scrierea de cinci minute, 2× pentru scrierea de o oră, 0,1× pentru o citire. Tot de aici vine afirmația despre long-context („Claude 4.6 și modelele ulterioare... includ context window complet de 1M token la preț standard”), numărul de tokens pentru system prompt la tool-use (496 tokens pe Claude Sonnet 4.5 cu tool_choice de auto sau none, 588 cu any sau un tool numit) și nota că Claude 4.7 și ulterior folosesc un tokenizer mai nou care produce „aproximativ 30 % mai mulți tokens pentru același text”. 2 3

  10. Anthropic, Token counting, docs.anthropic.com/en/docs/build-with-claude/token-counting, accesat 2026-09-06. Endpoint-ul /v1/messages/count_tokens primește aceleași input-uri ca un mesaj și întoarce un număr de input tokens; documentația spune că numărul este o estimare, că poate include tokens pe care Anthropic îi adaugă pentru optimizări de sistem și că aceia nu sunt facturați.

  11. Liu, N. F., Lin, K., Hewitt, J., Paranjape, A., Bevilacqua, M., Petroni, F. and Liang, P. Lost in the Middle: How Language Models Use Long Contexts. arXiv:2307.03172 (2023). Citat aici, măsurat în Capitolul 24.

Gata să lași LIA să aleagă?

Construiește cu toate modelele AI într-un singur loc — începe gratuit azi.