> ## Documentation Index
> Fetch the complete documentation index at: https://docs.truemath.ai/llms.txt
> Use this file to discover all available pages before exploring further.

# Input formats

> How calculation inputs are expressed — natural language prose, structured text key/value lines, or a JSON object. Natural language and structured text work in the Playground and over the API; JSON is API-only.

Every calculation is submitted as a **prompt** in one **input format**, chosen per request.

TrueMath accepts three input formats:

* **Natural language** — prose describing what you want.
* **Structured text** — explicit `key: value` lines.
* **JSON** — a structured object carrying the same values as structured text. Available over the [API](/api/calculate) only.

Natural language and structured text apply the same way in the [Playground](/playground/tour) and over the [API](/api/calculate) — only the surface differs. JSON is accepted over the API only.

For how natural language fits into TrueMath's use of language models, see [How TrueMath fits with LLMs](/introduction/how-it-fits-with-llms).

A completed calculation returns its full result, and a structured-text request also gets that result serialized back as structured text, so it round-trips: capture a result, change a value, and resubmit it. See [Round-trip](#round-trip).

## Natural language

Natural language is free-form prose. TrueMath uses a language model to parse your intent into the [variables](/concepts/variables) to set and the variable to solve for, then executes the calculation deterministically. Use it for exploration, or when you do not know a domain's exact keys.

```nlp theme={null}
What is the monthly payment on a $400,000 loan at 6% over 30 years?
```

Because natural language must be interpreted, a request may be processed asynchronously — see [In progress](/api/calculate#in-progress).

## Structured text

Structured text is one instruction per line, in `key: value` form. It is precise and fast: there is no language to interpret, so the same input always produces the same request. Use it when you know the [variables](/concepts/variables) you want to set and the target you want to solve for.

```yaml theme={null}
# A mortgage payment
scenario: new
home_price: $500,000
down_payment: $100,000
interest_rate: 6.5%
loan_term: 30 yr
calculate: monthly_payment
```

### Lines

Each line is one instruction:

* **`<key>: <value>`** — set a variable. `<key>` is the variable's [key](/concepts/variables).
* **`calculate: <key> [<unit>]`** — name the variable to solve for, optionally with the unit you want the result in (`calculate: monthly_payment USD`).
* **`scenario: <selector>`** — choose the [scenario](/concepts/scenarios) to calculate against (see [Scenarios](#scenarios)).
* **`# ...`** — a comment; the whole line is ignored.

`calculate:` and `scenario:` are optional. When omitted, they are inferred from the prior request in the conversation.

### Values

Write a value the way you would by hand; the unit travels with it (see [Units and precision](/concepts/units-and-precision)).

* **Numbers** — `3000.54` or `3,000.54`; thousands separators are optional.
* **Units inline** — `30 yr`, `5.2 m`, `1500 USD`; abbreviations or full names both work (`yr` or `years`, `m` or `meters`). See [Units](/math/units).
* **Currency** — a leading `$` is shorthand for USD: `$1,000.00` is the same as `1000.00 USD`.
* **Percent** — a trailing `%` is converted to a rate: `6.5%` becomes `0.065`.

Units are written plainly here — no backticks. Backticks are only needed when a unit appears in an [activity equation](/authoring/writing-equations#units-in-equations), where it could otherwise be read as a variable name.

### Tables

A [table](/math/types/tables) value uses **semicolons** to separate cells — never commas, which collide with decimal and thousands separators.

A one-dimensional table is a list on a single line; brackets are optional:

```yaml theme={null}
costs: 1500; 1600; 1700
costs: [1500; 1600; 1700]
```

Each cell may carry its own unit; an outer unit after the table fills only the cells that lack one — a cell's own unit always wins:

```yaml theme={null}
lengths: 3 in; 4 ft; 5 m       # each cell carries its own unit
lengths: [3; 4; 5] ft          # ft fills every cell
lengths: [3; 4 in; 5] ft       # ft fills cells 1 and 3; 4 in keeps its own
```

Cells follow the same value conventions as scalars — `[$3; $4]` is two currency amounts, and `[5%; 10%]` becomes `[0.05; 0.1]`.

A two-dimensional table is written as bracketed rows. Put the rows on one line, or one row per line:

```yaml theme={null}
schedule: [1500; 12][1600; 12][1700; 12]

schedule: [1500; 12]
          [1600; 12]
          [1700; 12]
```

See [Tables](/math/types/tables) for the underlying model and how tables are returned.

### Scenarios

`scenario:` selects which [scenario](/concepts/scenarios) the calculation runs against:

* **`scenario: new`** — start a new scenario.
* **`scenario: last`** — the most recent scenario.
* **`scenario: first`** — the first scenario in the conversation.
* **`scenario: <index>`** — a specific scenario by its index.

When `scenario:` is omitted, the calculation continues the conversation's current scenario.

### Persistence

Values persist within a [conversation](/concepts/scenarios). A variable you set but do not use in the current calculation is retained and stays available until a later calculation needs it. Likewise, when you omit `calculate:`, the prior target is retained. You can build up inputs across several requests and solve for different targets without restating values.

## JSON

JSON expresses the same request as structured text, but as a structured object rather than `key: value` lines. It is available over the [API](/api/calculate) only — set `input_format` to `json` and pass the object as a JSON string in `prompt`. Like structured text, it is precise and deterministic: there is no language to interpret, so the same input always produces the same request, and the calculation runs synchronously.

The object has three fields:

```json theme={null}
{
  "inputs": [
    { "key": "home_price", "value": "500000 USD" },
    { "key": "down_payment", "value": "100000 USD" },
    { "key": "interest_rate", "value": "6.5%" },
    { "key": "loan_term", "value": "30 yr" }
  ],
  "calculate": { "key": "monthly_payment", "unit": null },
  "scenario": "new"
}
```

* **`inputs`** — an array of `{ "key", "value" }` objects, one per [variable](/concepts/variables) to set. `key` is the variable's [key](/concepts/variables).
* **`calculate`** — `{ "key", "unit" }` naming the variable to solve for, with the optional [unit](/math/units) you want the result in (`null` for the variable's own unit). Set `calculate` to `null` to infer the target from the prior request in the conversation.
* **`scenario`** — the [scenario](/concepts/scenarios) selector as a string: `"new"`, `"first"`, `"last"`, or an index such as `"2"`. Set it to `null` to continue the conversation's current scenario.

### Values in JSON

Each `value` is a string, following the same conventions as a structured-text [value](#values) — the unit travels inside the string:

* **Scalars and units** — `"3000.54"`, `"30 yr"`, `"1500 USD"`. A leading `$` is shorthand for USD (`"$1,000.00"`), and a trailing `%` becomes a rate (`"6.5%"` → `0.065`).
* **A 1-D [table](/math/types/tables)** — an array of cell strings: `["1500 USD", "1600 USD", "1700 USD"]`.
* **A 2-D table** — an array of row arrays: `[["1500", "12"], ["1600", "12"]]`.

Table cells are separate array elements, so JSON uses no semicolons or brackets within a value. Each cell carries its own unit; there is no outer unit that fills cells lacking one.

### Nothing recognized

A request that resolves to no inputs and no calculation target — `{ "inputs": [], "calculate": null, "scenario": null }` — is treated as "nothing recognized" and returns the [`input.llm_no_parsed_data`](/api/errors#calculation-error-codes) error. This is the same signal used across every input format.

## Round-trip

A completed calculation always returns its full result in the `results` object. A structured-text request additionally gets that result serialized back as a `structured_text` string, so you can capture it, change a value, and resubmit. See [Calculate](/api/calculate#completed) for the response fields each input format returns.
