Watch regular expressions come to life as automata.
RegVizz compiles a regular expression into its NFA and DFA and renders both as interactive, side-by-side graphs — so you can see every state, transition, and ε-move instead of just reading about them.
Live Demo · Features · How It Works · Getting Started · API
RegVizz is a teaching-oriented visualizer for the theory behind pattern matching. Type a regular expression, and it walks the full compilation pipeline — from raw pattern to non-deterministic automaton to its deterministic equivalent — and draws the result as a graph you can pan, zoom, and explore.
It's built for students and anyone learning automata theory who wants an intuition for Thompson's Construction and Subset Construction by watching them run, not by tracing them on paper.
Try it: enter
a(b|c)*and compile to see a compact example of alternation and the Kleene star.
- Regex → NFA using Thompson's Construction, with explicit ε-transitions.
- NFA → DFA using Subset Construction over the ε-closure of each state set.
- Side-by-side graphs — the NFA and DFA render together so you can compare structure at a glance.
- Interactive rendering powered by React Flow — pan, zoom, and drag nodes.
- Two-layer validation — the pattern is checked in the browser and on the server before compilation, with clear, specific error messages.
- Postfix insight — the intermediate postfix (Shunting-yard) form and extracted alphabet are computed as part of the response.
- Single-deploy architecture — frontend and backend ship together on Vercel behind one domain.
| Operator | Symbol | Example | Meaning |
|---|---|---|---|
| Concatenation | (implicit) | ab |
a followed by b |
| Alternation | | |
a|b |
a or b |
| Kleene star | * |
a* |
zero or more a |
| Grouping | ( ) |
a(b|c)* |
precedence control |
Any other character is treated as a literal symbol of the alphabet.
The engine transforms a pattern through four deterministic stages:
flowchart LR
A["Regex<br/>a(b|c)*"] --> B["Explicit concat<br/>a.(b|c)*"]
B --> C["Postfix<br/>abc|*.<br/><i>(Shunting-yard)</i>"]
C --> D["NFA<br/><i>Thompson's Construction</i>"]
D --> E["DFA<br/><i>Subset Construction</i>"]
D --> F["Graph JSON"]
E --> F
F --> G["React Flow<br/>visualization"]
- Insert explicit concatenation. Implicit adjacency (
ab) is rewritten with an explicit.operator (a.b) so the pattern can be parsed unambiguously. - Convert to postfix. A Shunting-yard pass reorders the expression by operator
precedence (
* > . > |) into postfix notation. - Build the NFA. Thompson's Construction folds the postfix stream into a single NFA fragment with one start and one accept state, wiring literals and ε-transitions.
- Determinize into a DFA. Subset Construction explores ε-closures of NFA state sets, producing a minimal-by-construction deterministic transition table.
Both automata are then serialized into a { nodes, edges } graph payload and rendered by
the frontend.
| Layer | Technologies |
|---|---|
| Backend | Python 3.13 · FastAPI · Uvicorn · Pytest |
| Frontend | React 19 · Vite · Vis.Js (vis-network/standalone) · Lucide icons |
| Deployment | Vercel (static frontend + Python serverless backend) |
| Tooling | uv (Python) · ESLint (JS) |
- Python 3.13+
- Node.js 18+
- Optional: uv for faster, reproducible Python installs
cd backend
# Install dependencies (pick one)
pip install -r requirements.txt # or: uv sync
# Run the API on http://127.0.0.1:8000
uvicorn app.main:app --reloadThe interactive API docs are then available at http://127.0.0.1:8000/docs.
cd frontend
npm install
npm run dev # serves on http://localhost:5173In development the frontend targets the local backend at http://127.0.0.1:8000; in
production it uses relative /api paths that Vercel proxies to the backend.
Base URL: http://127.0.0.1:8000 (local) · https://regvizz.vercel.app (production)
| Method | Endpoint | Description |
|---|---|---|
GET |
/api/health |
Service health check. |
GET |
/api/compile/nfa?regex=<pattern> |
Compile a regex to its NFA graph. |
GET |
/api/compile/dfa?regex=<pattern> |
Compile a regex to its DFA graph. |
GET |
/api/compile/both?regex=<pattern> |
Compile to both, plus the postfix form. |
Example
curl "http://127.0.0.1:8000/api/compile/both?regex=a(b|c)*"Each node carries id, label, isStart, and isAccept; each edge carries
source, target, and a transition label (ε for epsilon moves). Invalid patterns
return HTTP 400 with a descriptive detail message.
RegVizz/
├── backend/
│ └── app/
│ ├── main.py # FastAPI app + routes
│ ├── regex_engine/ # Compilation pipeline
│ │ ├── helper.py # validation, concat, regex → postfix, alphabet
│ │ ├── postfix_2_nfa.py # Thompson's Construction + NFA serialization
│ │ ├── nfa_2_dfa.py # Subset Construction + DFA serialization
│ │ ├── nfa_state.py # NFA state model
│ │ └── fragement_state.py # NFA fragment (start/accept pair)
│ └── tests/
│ └── test_regex.py # Pytest suite for the engine
├── frontend/
│ └── src/
│ ├── App.jsx # UI, input, client-side validation
│ ├── AutomatonGraph.jsx # React Flow graph component
│ └── api.js # Backend client
└── vercel.json # Combined build + routing config
The regex engine is covered by a Pytest suite (concatenation insertion, postfix conversion, and alphabet extraction):
cd backend
pytestRegVizz deploys to Vercel from a single vercel.json:
- the frontend builds as a static site (
@vercel/static-build), and - the backend runs as a Python serverless function (
@vercel/python).
All /api/* requests are routed to the FastAPI app; everything else is served from the
built frontend, so the whole app lives behind one domain.
- Regex → NFA (Thompson's Construction)
- NFA → DFA (Subset Construction)
- Interactive graph rendering
- Combined Vercel deployment
- Step-by-step animated construction
- DFA minimization
- Shareable pattern links and example gallery
Status: actively developed. The core conversion pipeline is deployed and working; APIs and UI may still evolve.
Built for learning automata theory — one state at a time.
{ "regex": "a(b|c)*", "postfix": "abc|*.", "nfa": { "nodes": [ /* … */ ], "edges": [ /* … */ ], }, "dfa": { "nodes": [ /* … */ ], "edges": [ /* … */ ], }, }