# Chars `chars/*` is the character-classification namespace: predicates that answer how a character is classified, plus two explicit character-granular string verbs. The predicates cover the ASCII conventions the language uses for identifiers and word-like tokens, while `chars/count` and `chars/slice` are self-documenting spellings of the codepoint-based `len` and `slice` — a reminder that string indexing is character-based, not byte-based (see Strings). Every `chars/*` function is registered in all hosts and needs no import; the identifier predicates mirror the lexical rules in Syntax and Style. ## Functions | Function | Purpose | |---|---| | `chars/word? ch` | Word character: alphanumeric or `_ - ? ! /` | | `chars/digit? ch` | Digit (`0`-`9`) | | `chars/alpha? ch` | Letter (`a`-`z`, `A`-`Z`) | | `chars/upper? ch` | Uppercase letter (`A`-`Z`) | | `chars/lower? ch` | Lowercase letter (`a`-`z`) | | `chars/space? ch` | Whitespace: space, tab, newline, carriage return | | `chars/ident-start? ch` | Identifier start: letter or `_` | | `chars/ident-cont? ch` | Identifier continuation: alphanumeric or `_ - ? ! /` | | `chars/count s` | Number of codepoints (same as `len`) | | `chars/slice s a b` | Codepoint range `[a, b)` (same as `slice`) | Notes: - The eight predicates take a single-character string and return a boolean. Empty strings are `false`. When given a longer string they classify its first character (`[chars/digit? "42"]` is `true`), so pass one character at a time. - Classification is ASCII-only — `[chars/upper? "É"]` is `false`, and non-ASCII letters are never word characters. - `chars/word?` and `chars/ident-cont?` accept the same set: letters, digits, `_`, `-`, `?`, `!`, and `/`. `chars/ident-start?` is stricter: letters and `_` only. - `chars/count` is identical to `len` on a string; `bytes/len` is the UTF-8 byte size. `chars/slice` clamps: `b` to the string end, `a` to 0, and `a >= b` yields `""`. ## Examples ### Classifying characters
echo [chars/digit? "7"]          # true
echo [chars/alpha? "x"]          # true
echo [chars/space? "\t"]         # true
echo [chars/upper? "É"]          # false — ASCII only
echo [chars/word? "/"]           # true — namespace separators are word chars
### Identifier rules
echo [chars/ident-start? "_"]    # true
echo [chars/ident-start? "-"]    # false
echo [chars/ident-cont? "?"]     # true
echo [chars/ident-cont? " "]     # false

set code "x9"
echo [chars/ident-start? [char-at $code 0]]   # true
echo [chars/ident-cont? [char-at $code 1]]    # true
### Codepoints vs bytes
set s "a中c"
echo [chars/count $s]            # 3 codepoints
echo [bytes/len $s]              # 5 UTF-8 bytes
echo [chars/slice $s 1 2]        # 中
echo [chars/slice $s 2 99]       # c — b clamps to the end
## See Also - Strings — `len`, `slice`, `split ""`, and byte-level access - Syntax and Style — identifier rules and call forms - Regex — pattern matching over whole strings