cd /news/ai-tools/i-stopped-asking-ai-to-count-now-it-… · home › topics › ai-tools › article
[ARTICLE · art-152400] src=dev.to ↗ pub= topic=ai-tools verified=true sentiment=↑ positive

I stopped asking AI to count. Now it catches 95.6% of the mistakes in crochet patterns, on a laptop

A developer built StitchProof, a laptop-based tool that catches 95.6% (43/45) of stitch-count errors in crochet patterns by having a fine-tuned 4B open-weight model only read each row and translate it into a small program, while plain Python does all the arithmetic. The split approach followed a baseline in which an open-weight model shown 60 patterns with 45 hidden wrong rows found just 20 errors and flagged 78 correct rows, and a model 30 times larger still missed nearly half. The tool runs offline on a MacBook, shows the arithmetic behind each flag, and is aimed at designers who pay per pattern check while makers use it free.

by read12 min views2 publishedOct 18, 2026

This is a submission for the Hacktoberfest Open-Source AI Challenge Week 2: Side Hustle

Round 5 says 31 stitches. You've counted three times. You keep getting 30.

Somewhere tonight, someone is pulling out an evening's work because of a number like that. They will blame their own hands. Sometimes they're right. Sometimes the pattern itself is wrong, and there's no way to tell which.

So I gave the job to an AI. I showed an open-weight model 60 crochet patterns with 45 wrong rows hidden in them and asked it to find the mistakes. It found 20. Along the way it flagged 78 rows that were perfectly fine. Then I tried a model 30 times bigger on some of the same patterns. It still missed almost half.

The problem wasn't crochet. The problem was that I was asking a language model to do arithmetic.

So I stopped. In StitchProof, the model only reads the pattern and turns each row into a tiny program. Plain Python does all the counting. With that split, and a 4B model fine-tuned on Tinker to do the reading, StitchProof caught 95.6% (43/45) of the same mistakes, runs on a laptop with the Wi-Fi off, and shows the arithmetic behind every flag:

Rnd 5 says (31), but '(sc 3, inc) x6' uses 24 of 24 stitches and makes 30.

This post is about crochet. The idea in it is for anyone who has watched an LLM confidently get a number wrong: let the model translate, and let code count.

StitchProof is a private tech editor for crochet patterns.

Crochet is bigger than it looks. Ravelry, the main home for knitters and crocheters, had almost 9 million registered users by 2020, and independent designers sell their patterns there and on Etsy as PDFs. Before a pattern goes on sale, many designers pay a human tech editor to check every stitch count, because one wrong number in round 5 means every maker who buys it tears out their work.

StitchProof does the stitch-math part of that job:

Who What they do What they get
Designers (would pay) Paste a draft, open a .txt ,.md or.pdf , or photograph a printed page Every row marked OK, ERROR, WARNING or CAN'T CHECK, the exact numbers behind each flag, a silhouette chart of the piece and a downloadable report
Makers (free) Type the stitches they had and paste the row they're stuck on "The pattern says 31. These instructions make 30 from your 24 stitches. The pattern itself doesn't add up here, so it's not you."

The side hustle: makers use it free, which is how designers hear about it. Designers pay per pattern check, or a small monthly fee if they publish often. A per-check price only works if each check costs nothing to run, which is exactly what a small local model gives me. (That's my business hypothesis, not a claim about revenue.)

The waits for the model and for Gemma are sped up 3x in the video. Everything you see runs on one MacBook.

1. Start. Paste a pattern, open a file, or photograph a printed page.

2. Check a pattern. The sample has two deliberate mistakes. Rows are annotated in place as the model reads them, like a spellchecker. Select a row and the panel shows the stitches available, used, made and stated.

3. The second mistake. Rnd 11 repeats (sc 2, dec) 5 times instead of 6, so it makes 15, not 18, and leaves 4 stitches unworked. StitchProof reports both problems.

The silhouette plots stitches per round. For amigurumi it traces the outline of the finished piece, so a mistake shows up as a spike or a dent, hatched and labelled.

4. Fix and check again. Edit Rnd 5 and re-run. Unchanged rows come straight from a local cache, so only the edited row goes back to the model.

5. Light or dark.

6. Printed patterns. Plenty of patterns live in books and on paper. Drop in a photo and Gemma 4 transcribes it on your computer.

7. Review before checking. The photo sits beside the editable transcription, so you can fix any misread before a single stitch is counted.

8. Stuck on a row. The maker mode: one row, one plain answer.

A local tech editor for crochet patterns. A small fine-tuned model reads every row. Plain code checks every stitch count. Nothing leaves your computer.

Demo video · Results · How it works · Architecture · Run it

You've unravelled it twice. Is the pattern wrong, or are you?

Crochet designers sell their patterns as PDFs on Etsy and Ravelry. Before publishing, many pay a human tech editor to check every single stitch count, because one wrong number in round 5 means hundreds of makers tearing out an evening's work. Errata are a fact of life.

So why not ask an AI? We tried. Given 60 test patterns and asked directly to find the rows whose counts are wrong, the open-weight Qwen3.5-4B caught 44.4% (20/45) of the mistakes. Chatbots are famously bad at crochet. They "count" stitches they never counted.

StitchProof never asks…

MIT licensed. 149 Python tests, plus frontend tests, run in CI on every push. Every result in this post comes from files in eval/results/, and every rate is shown with its count.

Built on open source: Qwen3.5 (Qwen team), Gemma 4 (Google DeepMind), Tinker and tinker-cookbook (Thinking Machines), llama.cpp, Ollama, FastAPI and React. Full credits are in the README.

LineProgram JSON object: work, increase, decrease, skip, "to end", turning chain, repeat, plus the row label and the stated count, Rnds 6-9. It reports COUNT_MISMATCH, OVERFLOW, LEFTOVER, REPEAT_REMAINDER, NO_STATED_COUNT or CANT_CHECK. The model's instructions say it plainly (prompts.py):

- Transcribe exactly. Never fix or compute counts. stated_count = the count
  written ("(18)", "[18 sts]", "- 18 st", "you should have 18"), even if wrong.

And this is what "counting" looks like on the other side, straight from simulate.py. No model anywhere near it:

def op(self, op: Op, tail: int = 0) -> None:
    if isinstance(op, Work):          # "sc 3": 1 stitch into each of the next 3
        self.take(op.n)
        self.made += op.n
    elif isinstance(op, IntoOne):     # "inc": 2 stitches into 1
        self.take(1)
        self.made += op.k
    elif isinstance(op, Together):    # "dec": 2 stitches worked together into 1
        self.take(op.k)
        self.made += 1
    ...

When the code can't be sure (lace, multi-size patterns, UK terms, short rows, a line the model couldn't read), the row says CAN'T CHECK with a reason. It never guesses. After a wrong row, the engine re-syncs to the designer's stated count, so one mistake is reported once instead of cascading down the whole pattern.

127.0.0.1, fonts and icons are bundled, there's no telemetry, and uploaded photos are read from a temp file and deleted.llama-server, Metal), Ollama for Gemma 4, pypdf, Jinja2 and Matplotlib for reports. No published patterns were used anywhere. Real patterns are someone's copyrighted work, so every training example is generated by my own code:

shapes.py builds pattern structures: spheres, tubes, cones, flat pieces, triangles, mixed stitches.errors.py seeds known mistakes (wrong stated count, wrong repeat count, wrong run length, wrong foundation chain, a repeat that doesn't divide "around"). Every seeded pattern is checked: the simulator must flag exactly the seeded rows.render.py writes the notation in many styles. paraphrase.py asks two teacher models on Tinker, gpt-oss-120b and Qwen3.5-397B-A17B, to rewrite some patterns in a natural designer's voice. Code then checks that every number and row label survived the rewrite.ood.py asks a third family, Training was a LoRA on Qwen/Qwen3.5-4B with tinker-cookbook's supervised loop: rank 32, one epoch, 1,410 line examples, thinking disabled. Validation loss went from 0.303 to 0.0028.

The whole build cost US$1.62 of Tinker credit (costs.md):

Model on Tinker Used for US$
Qwen3.5-4B LoRA training (1 epoch + validation) 1.018
Qwen3.5-4B sampling for baselines, the fine-tuned eval, the export check 0.359
Kimi-K2.6 writing the out-of-generator test set 0.099
Qwen3.5-397B-A17B training-data rewrites 0.084
gpt-oss-120b training-data rewrites + the large-model baseline 0.041
storage checkpoints 0.017
Total 1.619

Four approaches, the same eval sets, the same prompt and the same parser, at temperature 0:

A: base, asked directly C: base + simulator D: StitchProof
Held-out: errors caught 44.4% (20/45) 75.6% (34/45) 95.6% (43/45)
Held-out: false alarms 13.7% (78/571) 42.6% (243/571) 22.2% (127/571)
Other model family: errors caught 61.1% (11/18) 100.0% (18/18) 100.0% (18/18)
Other model family: false alarms 11.2% (23/205) 50.7% (104/205) 8.3% (17/205)
Other model family: whole pattern right 32.0% (8/25) 16.0% (4/25) 80.0% (20/25)
Valid JSON (held-out) 86.7% (52/60) 78.0% (663/850) 100.0% (850/850)
Stated count copied faithfully (held-out) n/a 67.4% (415/616) 100.0% (616/616)

What the table says, in plain words:

Almost all of D's false alarms on the held-out set come from one notation it never saw: *sc, inc; rep from * 4 more times, which means 5 repeats in total. The model writes 4. On rows in that style it raises false alarms on 97.5% (115/118) of clean rows, and it's also why D catches only 66.7% (4/6) of the wrong-repeat-count mistakes. On rows in the other three unseen styles, D parses 99.8% (466/467) exactly, with 2.7% (12/438) false alarms.

I didn't retrain on that style, because that would be tuning on the test set. It goes into the next version's training templates, with fresh held-out styles to test against.

Patterns are a designer's unreleased work, so the fine-tuned model had to run locally. I exported the LoRA with Tinker's weights API, converted it for llama.cpp and run it on a 4-bit base:

Disk RAM Load time Per row (M4 MacBook) Agreement with Tinker
2.93 GB 3.18 GB 2.5 s 2.36 s mean 100.0% (50/50)

One gotcha worth sharing with anyone fine-tuning Qwen3.5 on Tinker:

Tinker trains the linear-attention Q, K and V projections as separate LoRAs, but Qwen3.5 stores them as one fused in_proj_qkv weight, so llama.cpp can't load the adapter as-is. An exact fused LoRA stacks the A matrices and puts the B matrices on a block diagonal (export.py):

for prefix, g in groups.items():
    a = torch.cat([g["qA"], g["kA"], g["vA"]], dim=0)            # rank r -> 3r
    b = torch.block_diag(g["qB"], g["kB"], g["vB"]) * 3.0       # llama.cpp scales by alpha / rank
    out[f"{prefix}.linear_attn.in_proj_qkv.lora_A.weight"] = a.contiguous()
    out[f"{prefix}.linear_attn.in_proj_qkv.lora_B.weight"] = b.to(g["qB"].dtype).contiguous()

The * 3.0 matters: the fused LoRA has rank 3r, and llama.cpp divides by rank, so without it every update would be a third of what Tinker trained. The equivalence check (50 validation lines, same prompt and parser, local vs Tinker) is what proved the conversion exact.

Gemma 4 (gemma4:e4b-it-qat in Ollama) has one job: turn a photo of a printed pattern into text, locally. It never counts either. On 12 held-out patterns rendered as a clean scan and as a phone-style photo (slight rotation, uneven light, noise, JPEG):

Typed text Scan → Gemma Photo → Gemma
Numbers kept n/a 98.9% (357/361) 98.1% (354/361)
Errors caught, end to end 100.0% (12/12) 91.7% (11/12) 100.0% (12/12)
False alarms, end to end 23.2% (22/95) 25.3% (24/95) 22.1% (21/95)
Lines character-perfect n/a 50.3% (81/161) 42.2% (68/161)

Gemma keeps the numbers but likes to drop separators like " - ". That's why the app always puts the photo next to the editable transcription before anything is checked.

I wrote a spec with milestones and checkpoints, then built StitchProof with Claude Code against it, stopping at each checkpoint to review the counting rules, the baselines and the results before moving on. The spec is in the repo as SPEC.md, and the counting rules are in CONVENTIONS.md, each with its own test.

Every one of these would have been impossible, or worse, with a closed API:

My first user is a family member who sells handmade hexagon cardigans and oversized patchwork sweaters on Etsy, made from her own patterns.

Her work shows why stitch math matters to a seller. A hexagon cardigan is dozens of identical motifs, each worked in rounds that have to land on the same count, and a patchwork sweater is panels that have to line up with their neighbours. One wrong number in her pattern doesn't cost one piece. It costs every motif made from it.

She ran StitchProof on one of her own patterns, on her own laptop. The pattern never left the machine, and it isn't in the training data or in any of the results above, which were all measured on generated patterns.

Her patterns also show exactly where v1 stops. Hexagons with chain-space corners and sweaters written for several sizes come back as CAN'T CHECK today, so those two are first on the list below. If you design or sell crochet pieces and have a draft you'd let me check, I'd love to hear from you in the comments.

I'm entering Best Use of Tinker, Best Use of Gemma and Best Use of GitHub Copilot.

The category asks for a fine-tune with a clear improvement over a baseline. StitchProof's case:

gemma4:e4b-it-qat through Ollama, on the same laptop. The photo is read from a temp file and deleted. The category includes automating your project with GitHub Actions. StitchProof uses two workflows:

Eval (synthetic sets)): it runs approaches C and D on Tinker with a hard spending cap (--max-usd 3 per run), writes the results table into the job summary and uploads the raw results as artifacts. It never touches the private data/real/ folder.CONVENTIONS.md Next: support chain-space corners and multi-size patterns, since both show up in my first user's work; add the missing notation styles to training and test on fresh held-out ones; check more real drafts with designers; package the model for Ollama; and try the same translate, simulate, verify design on knitting.

If you crochet, design patterns, or just have opinions about LLMs and arithmetic, I'd love to hear what you think in the comments.

── more in #ai-tools 4 stories · sorted by recency
── more on @stitchproof 3 stories trending now
sponsored brought to you by zahid.host 4,200+ EU-deployed projects
reading about agents? ship yours in a single git push.

Run your AI side-project on zahid.host

EU-based hosting, git-push deploys, automatic HTTPS, no cold starts. Free tier with a custom domain — perfect for shipping the agent you just read about.

$git push zahid main
→ Live at https://your-agent.zahid.host ✓
Get free account → Pricing
from €0/mo · no card required
LIVE [news/i-stopped-asking-ai-…] indexed:0 read:12min 2026-10-18 · —