DocumentationWriting your own problems

Guides

Writing your own problems

Add the problems you want to drill: cstudy new scaffolds them, cstudy verify checks them, and they join the catalog for every command.

On this page
  1. Where your problems live
  2. Scaffold one with cstudy new
  3. The files of a problem
  4. The workflow
  5. Checking with cstudy verify

Where your problems live

Problems you write go in your workspace’s problems/ directory, numbered from 5001, so new catalog problems never take your ids. cstudy overlays them on the catalog: cstudy list, next, start, test and verify treat them like any other problem.

If one of your problems uses the slug of a catalog problem, yours wins and hides the catalog one entirely, so your practice files and progress always match the problem you wrote.

Scaffold one with cstudy new

shell
cstudy new max-gap --from-template array --pattern arrays-hashing --difficulty medium

cstudy new creates the problem’s directory with status: draft, every required file with TODO placeholders, and prints the next steps with the check for each. The title defaults to one made from the slug (max-gap becomes Max Gap), the difficulty to medium.

cstudy new templates
TemplateShapeDefault track
arrayA function taking an int array and an int, returning an int (the default)dsa
treeA function taking and returning a binary treedsa
designA class with a constructor and 2 methods, tested with operation sequencesdsa
progressiveA class with 4 levels, one method per levelpractical
concurrentA thread-safe class with a blocking method, one stress case and one broken referenceconcurrency
project-pythonA project folder with an entry class and 2 levels; also project-typescript, project-go, project-java, project-kotlin and project-rustpractical
cstudy new flags
FlagEffect
--from-template NAMEOne of the templates above
--track Tdsa, practical, lld, concurrency or debugging; lld also writes a rubric.md
--pattern PThe primary pattern; a dsa problem needs one, from this flag or the template
--difficulty Deasy, medium or hard
--title TEXTThe title

The files of a problem

Files in a problem directory
FileHolds
problem.mdThe statement: Statement, Input, Output, Examples, Constraints and Hints sections, in your own words
meta.yamlTitle, difficulty, track, patterns, the signature in a small type language, the comparator, approaches and performance settings
tests.jsonThe cases, as language-neutral JSON: visible examples, hidden cases, and generated ones
generator.pyGenerates random inputs, for oracle checks and benchmarks
solutions/explanation.md, one section per approach, and a reference file per approach and language

A languages line in meta.yaml lists the languages the problem supports; cstudy new writes it explicitly.

The workflow

Write a problem in this order, running the check after each step:

Authoring workflow
StepActionCheck
1cstudy new with a templateThe directory exists, as a draft
2Write problem.md in your own wordscstudy verify <slug> --static
3Set the signature and comparator in meta.yaml--static
4Add visible examples and hidden edge cases to tests.json--static
5Write a brute-force approach in Python, marked as the oraclecstudy verify <slug>
6Write generator.pycstudy verify <slug> --oracle
7Write the optimal approach in each language--oracle
8Write solutions/explanation.md--static
9Add the performance block and a generated case at the largest size--ladder
10Set status: readycstudy verify <slug> --oracle --ladder --require-ready

Concurrent problems replace the oracle and ladder steps with stress cases and broken references that the stress cases must catch. Project problems shape a starter folder and a reference overlay instead. A draft is fully practicable, but cstudy next skips it until it is ready.

Checking with cstudy verify

cstudy verify checks problems statically (schema, sections, types of the test values against the signature) and by running every reference solution against the cases in every language.

terminal
$ cstudy verify
0001-two-sum      static ok · py 2/2 ok · ts 1/1 ok · java 1/1 ok · kt 1/1 ok · oracle 200/200
0014-koko-eat...  static ok · py 2/2 ok · ts - · java 1/1 ok · kt -      draft (coverage 2/4)
0031-word-break   FAIL static: solutions/explanation.md missing "### Correctness" in approach memo-dp
0190-bounded-...  static ok · py 2/2 ok · ts 1/1 ok · java 2/2 ok · kt 2/2 ok · stress 10/10 · slowest 8% · broken caught 11/11

coverage  python 31/31 · typescript 29/31 · java 31/31 · kotlin 28/31
result    1 failed · 30 passed
cstudy verify flags
FlagEffect
--staticSchema and static checks only; nothing runs
--oracle [--oracle-cases N]Cross-check every approach against the oracle on N random small inputs (default 200)
--ladderBenchmark the references and check their growth against the declared complexity
--require-readyFail any problem whose status is not ready
--lang LCheck one language
--track TCheck one track
--jobs NLanguage runners in parallel
--stress NConcurrent problems: runs per stress case and variant (default 10)
--changedOnly problems changed relative to main in git

Exit code 0 means every check passed, 1 a failed check, and 5 static failures only.

Ready means

For an algorithms problem: at least 2 approaches, a Python oracle, a generator, at least 2 visible and 8 hidden cases, a generated case at the largest size, and an optimal reference in every language the problem lists.

The authoring spec has the full workflow and ready criteria, and the problem format spec defines every file.

Written for cstudy 0.8.0. The specs in the cstudy repository are the source of truth for every detail.