torch.tx.ParseExprPattern
export type ParseExprPattern<P extends string> =
// Level 1: Ternary (lowest precedence)
P extends `${infer Cond} ? ${infer Then} : ${infer Else}`
? { op: '?:'; cond: ParseExprPattern<Cond>; then: ParseExprPattern<Then>; else: ParseExprPattern<Else> }
: // Level 2: Logical OR
P extends `${infer L} | ${infer R}`
? { op: '|'; left: ParseExprPattern<L>; right: ParseExprPattern<R> }
: // Level 3: Logical XOR
P extends `${infer L} ^ ${infer R}`
? { op: '^'; left: ParseExprPattern<L>; right: ParseExprPattern<R> }
: // Level 4: Logical AND
P extends `${infer L} & ${infer R}`
? { op: '&'; left: ParseExprPattern<L>; right: ParseExprPattern<R> }
: // Level 5: Comparison operators
P extends `${infer L} == ${infer R}`
? { op: '=='; left: ParseExprPattern<L>; right: ParseExprPattern<R> }
: P extends `${infer L} != ${infer R}`
? { op: '!='; left: ParseExprPattern<L>; right: ParseExprPattern<R> }
: P extends `${infer L} <= ${infer R}`
? { op: '<='; left: ParseExprPattern<L>; right: ParseExprPattern<R> }
: P extends `${infer L} >= ${infer R}`
? { op: '>='; left: ParseExprPattern<L>; right: ParseExprPattern<R> }
: P extends `${infer L} < ${infer R}`
? { op: '<'; left: ParseExprPattern<L>; right: ParseExprPattern<R> }
: P extends `${infer L} > ${infer R}`
? { op: '>'; left: ParseExprPattern<L>; right: ParseExprPattern<R> }
: // Level 6: Addition/Subtraction
P extends `${infer L} + ${infer R}`
? { op: '+'; left: ParseExprPattern<L>; right: ParseExprPattern<R> }
: P extends `${infer L} - ${infer R}`
? { op: '-'; left: ParseExprPattern<L>; right: ParseExprPattern<R> }
: // Level 7: Multiplication/Division/Matmul
P extends `${infer L} // ${infer R}`
? { op: '//'; left: ParseExprPattern<L>; right: ParseExprPattern<R> }
: P extends `${infer L} * ${infer R}`
? { op: '*'; left: ParseExprPattern<L>; right: ParseExprPattern<R> }
: P extends `${infer L} / ${infer R}`
? { op: '/'; left: ParseExprPattern<L>; right: ParseExprPattern<R> }
: P extends `${infer L} % ${infer R}`
? { op: '%'; left: ParseExprPattern<L>; right: ParseExprPattern<R> }
: P extends `${infer L} @ ${infer R}`
? { op: '@'; left: ParseExprPattern<L>; right: ParseExprPattern<R> }
: // Level 8: Power (right-associative, but pattern matching handles it)
P extends `${infer L} ** ${infer R}`
? { op: '**'; left: ParseExprPattern<L>; right: ParseExprPattern<R> }
: // Level 9: Unary operators
P extends `-${infer X}`
? { op: 'neg'; arg: ParseExprPattern<X> }
: P extends `~${infer X}`
? { op: '~'; arg: ParseExprPattern<X> }
: // Function call: name(args...)
IsFunctionCall<P> extends true
? {
fn: ExtractFunctionName<P>;
args: ParseFunctionArgs<ExtractFunctionArgsRaw<P>>;
}
: // Parentheses (must come after function call check)
P extends `(${infer Inner})`
? ParseExprPattern<Inner>
: // Trim whitespace
P extends ` ${infer X}`
? ParseExprPattern<X>
: P extends `${infer X} `
? ParseExprPattern<X>
: // Number literal
IsNumber<P> extends true
? { literal: P }
: // Identifier
IsIdentifier<P> extends true
? { var: P }
: { unknown: P };Pextends stringParse an expression pattern into an AST at the type level.
Supports:
- Ternary: x ? y : z
- Logical: |, ^, &
- Comparison: ==, !=, <, <=, >, >=
- Arithmetic: +, -, *, /, //, %, @
- Power: ** (right-associative)
- Unary: -x, ~x
- Parentheses: (x + y)
- Function calls: relu(x), sigmoid(x @ w)
- Identifiers: input, weights, z_gate, etc.
- Number literals: 1, 2, 0.5
Precedence (lowest to highest):
- Ternary ? :
- Logical |
- Logical ^
- Logical &
- Comparison ==, !=, <, <=, >, >=
- Addition +, -
- Multiplication *, /, //, %, @
- Power **
- Unary -, ~