~/satyajit

Nanbeige4.3-33B: a teacher first, and a cache you pay for

mdjsonmcp

2026-10-26 · 14 min · agents · agentic-coding · distillation · kv-cache · on-device · benchmarks · small-models

A 1:49 narrated explainer, drawn in code. Every number and picture in it is this article's own; the sources are below.

› transcript

Hi, I'm Painter! Nanbeige four point three is a thirty-three billion parameter model, released first so it can teach smaller ones. Let's open it up. Build the strongest agent you can first, then use it to teach small models. The teacher is out now. The student is not. A token goes up through fifty-two identical blocks. No experts, no loops, no sliding windows. The feed-forward layer holds about four fifths of every block's weights. Seven query heads share each key and value head, so only eight heads are cached. But every layer keeps a cache. That is two hundred eight kilobytes a token, over three times Qwen's hybrid. At long context the cache, not the weights, is the bill. The chat template shows how it acts. It thinks first, then names a function in XML. Results come back as a user turn. Think inside think tags. Name the function. Give each parameter a tag. Results return as a user turn. A base model goes through post-training. The recipe, the data and the environments are not published. Out comes the thirty-three billion teacher, with open weights. It is then meant to teach a three billion student. How, the team has not said. The card reports it leading on seventeen of twenty benchmarks against three rivals. Those are the publisher's own runs. A teacher is a claim about the future. The cache is a bill you pay today. To recap: a plain dense model, a heavy cache, and a teacher whose student has not arrived. Every source is in the full article. I'm Painter. Bye!

Why read this

Notabletop 60%

Reads the 33B from headers and config: 208 KiB of cache per token, the tokenizer shared with 4.2-3B, and what the card leaves unsaid about the teacher recipe.

  • Original analysis
  • Concrete numbers to act on
  • Open code or weights

LLM architectureNeeds a workstation GPUApache-2.0Practitioner model

How this was scored
Is it new?
1 of 3: An incremental tweak
Can I trust it?
2 of 3: Measures key facts from files, code or configs
Can I run it?
2 of 3: Open code or weights with real limits
Will I understand it?
2 of 3: Mechanism from first principles with figures
Can I act on it?
2 of 3: A concrete recipe, numbers or comparison
Will it last?
1 of 3: Relevant for months
Does it affect many?
1 of 3: A specialist community
Only here?
2 of 3: A teardown or measurement few others did

Score 60 of 100, ranked 356 of 613 rated articles. Each question is answered 0–3 by hand, and a 3 is rare. How articles are scored

On 25 October the Nanbeige LLM Lab (Boss Zhipin, Kanzhun) posted Nanbeige4.3-33B: "SOTA agentic performance among open models at ~30B parameters", reached by "building a powerful teacher first". The 33B is meant to teach smaller models, "starting with Nanbeige4.3-3B". The post has no thread. Its replies add community quantizations, a lot of requests for a mixture-of-experts version, and a few people asking whether anyone has verified the numbers. The two links in the post are the model repository and its Base. There is no technical report, which the 4.2-3B had.

So this article does what a model card allows. I read the safetensors headers by range request, the config, the tokenizer and the chat template, and I ran the template and tokenizer on a CPU. The weights themselves I did not download, and I did not run the model. Every number below is tagged measured (I computed it from a file), reported (the publisher or a community poster said it) or reasoned (my arithmetic on the other two).

Nanbeige/Nanbeige4.3-33B@c1093c5 · snapshot 2026-10-26
parameters
33.12B
repo size
66.26 GB
architecture
LlamaForCausalLM
task
text-generation
library
transformers
license
apache-2.0
safetensors
14 shards
largest file
5.00 GB
files
27
downloads
0
likes
467
languages
en, zh
parameters by dtype
BF1633.12B
llmnanbeige

repo last modified 2026-10-25

Nanbeige/Nanbeige4.3-33B-Base@e061add · snapshot 2026-10-26
parameters
33.12B
repo size
66.24 GB
architecture
LlamaForCausalLM
task
text-generation
library
transformers
license
apache-2.0
safetensors
14 shards
largest file
4.99 GB
files
23
downloads
0
likes
51
languages
en, zh
parameters by dtype
BF1633.12B
llmnanbeige

repo last modified 2026-10-25

What is in the files

The architecture is LlamaForCausalLM, the plainest thing a 2026 model can be. The header sum is 33,118,977,024 parameters, all bfloat16, in 14 shards of about 66.2 GB (measured; the 471 tensors are 52 layers times 9, plus the embedding, the head and the final norm). Rebuilding that number from the config closes it to the digit (measured):

piececount
attention per layer: q 7,168², o 7,168², k and v 1,024 × 7,168 each117,440,512
feed-forward per layer: three matrices of 7,168 × 22,016473,432,064
52 layers with norms30,726,119,424
input embedding, 166,912 × 7,1681,196,425,216
output head, untied, same shape1,196,425,216

Two things follow. The feed-forward layer holds 80% of each layer's weights, the usual dense profile. And "33B" counts both embedding tables. Without them it is 30.7B, which is what "~30B class" means in the post (reasoned). The Hugging Face tags show a text model, and the tensor list agrees: no vision tower. One replier said so within the hour.

Nothing here loops. The 4.2-3B was a two-pass looped transformer, and its depth came from running the same layers twice (see the looped-transformer explainer). The 33B has 52 distinct layers and a model_type of llama, so a loop would need custom code the repository does not ship. Whatever carried over from 4.2, it is not the loop.

The cache is the bill

Attention uses 56 query heads over 8 key-value heads, so seven queries share each cached head. That is grouped-query attention, 7:1. The cache per token is

2×52×8×128=106,496 values2 \times 52 \times 8 \times 128 = 106{,}496 \text{ values}

which is 212,992 bytes, 208 KiB, at f16 (reasoned from the config). At the 128K positions the Base config allows that is 26 GiB. At the 512K the chat model's config allows it is 104 GiB. Full multi-head attention would be seven times worse.

Every one of the 52 layers keeps a cache; no layer is sliding-window or linear. Qwen3.8-27B, the card's main comparator, is a hybrid that caches only 16 of its layers, at 64 KiB a token by that article's arithmetic (reasoned). So Nanbeige's cache is 3.25 times Qwen's per token. Muse Glimmer and Gemma 4 are both built the other way, spending architecture to shrink the cache. The 33B spends nothing on it. That is a legitimate choice, and it is what the "cost-efficient inference" line has to be weighed against.

This widget does the arithmetic for any file, cache type, context and chip. The file sizes are the real ones from the Hugging Face listings; the chip bandwidths are spec-sheet numbers I typed in, not measured.

Three readings of it (all reasoned). A Q4_K_M file is 20.79 GB. On a 24 GB card that leaves about 3.2 GB, which is roughly 15,000 tokens of f16 cache before the runtime takes its share. IQ4_XS is 18.64 GB and leaves 5.4 GB, about 25,000 tokens, or about 47,000 with a q8_0 cache. And at 128K, a Q4_K_M file with an f16 cache is 48.7 GB of memory, with q4_0 cache 28.6 GB.

The tokenizer is Nanbeige's own, unchanged

The tokenizer.model in the 33B has the same SHA-256 as the one in Nanbeige4.2-3B and in Nanbeige4-3B-Base (fb41d047…), and the chat model's tokenizer.json is byte-identical to the 4.2-3B's (measured). It is a SentencePiece BPE with 166,100 pieces plus seven chat tokens, padded to a 166,912-row embedding. So the whole family shares one vocabulary, and the 3B student can share the teacher's tokens, which matters for logit-level distillation (reasoned; the lab has not said what kind it uses).

Is it a copy of someone else's? I compared the piece strings, mapping SentencePiece's ▁ to a space and byte-level tokens to text. Of its 166,100 pieces, 58% also appear in DeepSeek-V3's vocabulary (76% of DeepSeek's), 51% in Qwen3's and 39% in Llama 3.1's (measured). That is overlap from common words, not lineage: a byte-for-byte copy would be near 100%. The tokenizer has its own merges. On three short samples it used 25 tokens on an English line like every comparison tokenizer, 22 on a Chinese line against Qwen3's 24, and 31 on a Python snippet against 25 to 27 (measured, tiny sample). Roughly: good on Chinese, a little heavier on code.

Base to chat: what changed in the weights

I fetched small slices of both repositories to see what post-training touched (measured, range requests).

That is a model whose post-training changed a lot, not a light fine-tune. How much compute, on what data, is not disclosed.

What "teacher first" says, and does not

The strategy in the card is one sentence: build "a high-capacity teacher agent first, which will subsequently anchor the distillation of advanced agentic capabilities into smaller models." Click through what is on the record at each stage.

The unknowns are the point. The card names no pretraining token count, no data mix, no RL method, no agent environments and no distillation recipe. The 4.2-3B report described a synthesized-environment SFT pipeline and agentic RL with process rewards, and it is tempting to assume 4.3 inherits it. I would not write that down as fact: the 4.3 pages say none of it. Replies on the post ask the right questions. Does the student see tool failures and recoveries, or only clean trajectories? Does distillation copy the next token, which says little about long-horizon behaviour? No answer yet (reported as questions, unknown as answers).

One more check. A Hugging Face search for "Nanbeige4.3" on 26 October lists no 3B repository (measured). The student is announced, not released.

The benchmark claim

All four models were "evaluated at their highest thinking effort," with "the same inference hyperparameters and harness across models" on each benchmark (reported). The comparators are Qwen3.8-27B, Muse-Glimmer-30B and Gemma4-31B. Reading the card's table, Nanbeige is first on 17 of 20 rows (measured by counting the table). It is behind on three: SWE-Bench Pro (60.3 against Qwen's 61.7), GDPval (84.8 against 86.4) and GPQA Diamond (89.5 against Gemma's 91.3).

Eight bar charts: Terminal-Bench 2.1, Terminal-Bench 4.0, DeepSWE, SWE-Atlas-QnA, NL2Repo, Automation, JobBench and Toolathlon-Verified. Each compares Gemma4-31B, Muse-Glimmer-30B, Qwen3.8-27B and Nanbeige4.3-33B, and Nanbeige is the tallest bar in every panel.
The card's headline chart: Nanbeige4.3-33B (teal) against three ~30B models on eight agentic benchmarks (Nanbeige4.3-33B model card, benchmark figure).

The margins are uneven, and that is the useful part. The big wins are on the newest, hardest agent suites: Terminal-Bench 4.0 is 23.8 against Qwen's 6.3, DeepSWE 65.5 against 42.5, Automation Bench 54.2 against 38.3. The small ones are where the benchmark is saturated or noisy: Tau3-Bench is 48.8 against 48.5, EnterpriseOps-Gym 41.0 against 40.2, AIME 2026 95.2 against 94.5, Toolathlon-Verified 70.4 against 68.5 (all reported; gaps reasoned). A 0.3 gap on one run is not a lead.

The footnotes tell you where each score came from, and they differ by row. Terminal-Bench 2.1 uses Terminus 2. Terminal-Bench 4.0, DeepSWE and SWE-Atlas-QnA use mini-swe-agent v2.4.6. NL2Repo uses Claude Code, and JobBench uses Claude Code with a search tool. DeepPlanning, EnterpriseOps-Gym and Tau3-Bench use their official repositories. So "mainstream agent harnesses" means these. Two caveats. Nanbeige is scored with preserve_thinking=true; the card does not say whether the others got an equivalent setting. And GDPval uses "revised rubrics" and SWE-Atlas-QnA a GPT-6 judge, so the rows are not on public leaderboard terms (reported).

A heatmap table of JobBench scores for 35 occupations in eight groups, with columns for Nanbeige4.3-33B, Qwen3.8-27B and Muse-Glimmer-30B. Overall scores are 44.80, 34.51 and 16.60. Nanbeige is bold in most rows.
JobBench by occupation, 35 occupations (Nanbeige4.3-33B model card, occupation figure).

I counted the occupation figure against Qwen: Nanbeige is ahead in 26 occupations, behind in 8 and tied in one (measured from the image). The losses cluster in healthcare managers, secretaries, customer service and data entry, and the wins in technical writing, web administration and online merchants. It is the most informative view the card gives. It still reads one benchmark, with three models.

Two small inconsistencies, both measured against the card itself: the chart prints 18.3 for Muse-Glimmer on JobBench where the table and the occupation figure say 16.6, and 33.7 for Gemma on NL2Repo where the table says 33.8. Neither changes a conclusion. They do say the chart was not generated from the table.

The cost claim has no number behind it

The post says the model "tackles real-world tasks with cost-efficient inference" in mainstream harnesses. The card gives no tokens per task, no dollars per task and no latency. It does give the recommended settings: temperature 1.0, top-p 0.95 and 65,536 new tokens for agentic work. "Cost" in the post can only mean per-token price on a 33B dense model, or fewer tokens per task than peers. The first is arithmetic about size. The second is unmeasured. The cache section above is why I would not assume the first: a long agentic session pays for 208 KiB per token held. A cost claim needs tokens per solved task next to the benchmark score, which is exactly what the Qwen3.8-27B variants article does for that model. I could not verify this one.

How it calls a tool

The chat template is where agent behaviour becomes concrete. I rendered it with a sandboxed Jinja environment and the model's own tokenizer, with one tool, one tool call, its result and a follow-up. This is the real output from the first user message on, with preserve_thinking=true (measured). Above it the template writes a Chinese tool-use preamble and the tool schema, 274 tokens in this case, and the preamble runs directly into # Tools with no line break:

<|im_start|>user
Fix the failing test in src/.<|im_end|>
<|im_start|>assistant
<think>
I should run the tests first.
</think>
 
<tool_call>
<function=run_tests>
<parameter=path>
src/
</parameter>
</function>
</tool_call><|im_end|>
<|im_start|>user
<tool_response>
1 failed: test_parse
</tool_response><|im_end|>
<|im_start|>assistant
<think>
The parser drops a trailing newline.
</think>
 
Patched parse().<|im_end|>
<|im_start|>user
Now run them again.<|im_end|>
<|im_start|>assistant
<think>

Four facts from it. <tool_call> and <think> are single added tokens (ids 166105 and 166103), while <function= and <parameter= are three ordinary tokens each. The format is the XML shape that vLLM and SGLang call qwen3_coder, which is the parser the card tells you to launch. So compatibility with existing harnesses comes from reusing a parser, not from a new one (reported flags, measured format). Tool results come back as a user turn wrapped in <tool_response>. And the default system prompt for tool use is in Chinese, which would be a surprise to someone who only reads the English card.

The flag with a real cost is preserve_thinking. I expected it to drop reasoning from every earlier turn, including the tool loop. It does not. The template drops reasoning only from assistant messages before the latest user message; inside one task's tool loop it is always kept (measured: I rendered a two-step loop with the flag off and both thoughts survived). So the flag matters across follow-up requests in one session. With it on, the old reasoning stays in the prompt. With it off, each earlier assistant message carries an empty <think> wrapper of 6 tokens. The card recommends on for tool use, and scores the model that way. The slider shows the price.

At 800 reasoning tokens a step, six steps a request and eight requests, request 8 starts at 35,218 prompt tokens with the flag on and 1,870 with it off (reasoned). That is cheap to state and expensive to run. The card reports no ablation of the flag, or of XML against JSON calls, so what each is worth is unknown.

Running it locally

The community moved fast, because the architecture is stock Llama. Within a day a search finds dozens of quantized repositories. File sizes come from the Hugging Face listings (measured):

formatsizebits per weight
BF16 safetensors (official)66.2 GB16
Q8_0 GGUF (bartowski)35.2 GB8.50
Q6_K29.0 GB7.01
Q5_K_M25.1 GB6.06
Q4_K_M20.8 GB5.02
IQ4_XS18.6 GB4.50
MLX 4-bit (pratikgx)18.6 GB4.50
Q3_K_M15.9 GB3.85
IQ2_M12.2 GB2.94

Bits per weight is file size over the 33.1B header count, so it includes the embeddings and any higher-bit tensors (reasoned).

Decoding a dense model is bandwidth-bound: each token reads every weight, plus the cache so far. The ceiling is bandwidth over bytes read (reasoned). The community gives me four measurements to test that against (reported, M5 Pro 64 GB Mac mini, MLX 4-bit): 14.4 tok/s at 512 tokens of context, 13.9 at 4K, 11.7 at 16K and 9.9 at 32K, with peak memory 22.8 GB at 16K and 26.4 GB at 32K. Multiply each speed by the bytes read per token (18.63 GB of weights plus 208 KiB times the context) and you get 270, 271, 259 and 254 GB/s. That is close to flat, which is what a bandwidth-bound decoder should do, and it shows the cache is what slows it at 32K (reasoned). The memory peaks also match: 18.63 GB plus 6.98 GB of f16 cache at 32K is 25.6 GB, and the reported peak is 26.4 (reasoned). A second report, 13.7 tok/s for a 17 GB 4-bit build on an M4 Pro, is 85% of the 273 GB/s spec-sheet ceiling of about 16 tok/s (reasoned; the bandwidth is the vendor's).

A 12 GB RTX 3060 owner tried it and reported 24K of context and "definitely not usable for agentic work" (reported; no quant or speed given). That matches the ledger: even IQ2_M is 12.2 GB before any cache.

Licence

The card metadata says Apache-2.0 on both repositories, and there is no separate LICENSE file in either file listing (measured). That is a permissive licence for weights. The training data and the evaluation harness are not released.

The take

Nanbeige4.3-33B is a competent-looking dense agent model whose strongest claims are on benchmarks the lab ran itself, against three rivals, on rows where some margins are under a point. The files back the parts they can: a plain 52-layer Llama, a tokenizer inherited unchanged from the 3B line, a re-based 512K context and a template that reuses the Qwen tool format. The files cannot back the part in the headline. "Teacher first" is a plan. The recipe, the distillation and the cost-per-task claim are unpublished, and the 3B student does not exist yet.

What you can use today is a 33B you can run on a 24 GB card at modest context, with a cache that is more expensive than its peers'. What to wait for is the technical report and an independent run of Terminal-Bench 4.0 and DeepSWE. If the student arrives and holds up, the strategy is proved. Until then the interesting number is not a score. It is 208 KiB.


Sources: the Nanbeige4.3-33B and Base repositories (card, config, tokenizer, safetensors headers, file listings), the announcement post and its replies, and the community repositories named above. Figures are the lab's; the interactives are mine. Not verified: any benchmark score, the tokens-per-task claim, the 512K context, and the distillation plan. I ran the tokenizer and chat template on a shared 4-core CPU, and never loaded the weights.

Cite this article

For attribution, please use the following reference or BibTeX:

Satyajit Ghana, "Nanbeige4.3-33B: a teacher first, and a cache you pay for", ai.thesatyajit.com, October 2026.

bibtex
@misc{ghana2026nanbeige4333b,
  author = {Satyajit Ghana},
  title  = {Nanbeige4.3-33B: a teacher first, and a cache you pay for},
  url    = {https://ai.thesatyajit.com/articles/nanbeige-4-3-33b},
  year   = {2026}
}
share