-export type Some<T> = { _tag: "Some"; value: T };
-export type None = {_tag: "None"};
-
-
-/**
- * wrap a x in a `Some(T)`
- * @param x : variable to be wrapped.
- * @returns wrapped `x`.
- */
-function toSome<T>(x: T): Some<T>{
- return { _tag: "Some", value: x};
-}
-/**
- * @description Like the `Some(a)` and `None` in Rust.
- *
- * @example
- * ```ts
- * let exam1 : Maybe<Number> = { _tag: "Some", value: 12 };
- * let exam2 : Maybe<Number> = None;
- * ```
- */
-export type Maybe<T> = Some<T> | None;
-
-
-/**
- * @description
- * the pair of the string to be matched later and the string that have been matched
- * @var matched : have been matched
- * @var remained : will be tested whether it'll be matched.
- * @var matched_type (optional): the type of the matched string
-*/
-export interface MatcheePair {
- matched : string
- remained : string
- matched_type?: TokenType
-}
-
-/**
- * The types of Token
- * NL, // newline
- *
- * SP, // half-width space and tab
- *
- * ID, // identifier
- *
- * STR, // string
- *
- * OP, // operator or something like it
- *
- * FLO, // float num
- *
- * INT, // Integer
- */
-export enum TokenType{
- NL, // newlinw
- SP, // half-width space and tab
- ID, // identifier
- STR, // string
- OP, // operator
- FLO, // float num
- INT, // integer
-}
-
-/**
- * tokenized token.
- * @var text : the content text
- * @var type (optional): the type of the token
- * @var col : the column number
- * @var ln : the line number
- */
-export interface Token{
- text: string,
- type?: TokenType,
- col: number,
- ln: number,
-}
-
-/**
- * @description
- * it returns a function which test if the first char of the `remained` part of
- * the argument of the function is `c`, if it's true, update the `MatchedPair` wrapped
- * in `Some`. Otherwise, it returns `None`.
- * * @param c : the char to be test.
- * @returns the updated `MatchedPair` wrapped in `Some(x)` or `None`.
- */
-export function match1Char(c : string) : (m: MatcheePair) => Maybe<MatcheePair> {
- return (m : MatcheePair)=>{
- if (m.remained.length == 0){
- return { _tag: "None" };
- }
- const charToBeMatched = m.remained[0];
- if (charToBeMatched === c){
- return {_tag: "Some", value :{
- matched : m.matched + charToBeMatched,
- remained : m.remained.substring(1)}};
- }
- else{
- return {_tag: "None"};
- }
- }
-};
-
-/**
- *
- * @param m : the `MatcheePair` to be consumed.
- * @returns if the length of `m.remained` >= 1; consumes the matchee by 1 char and wraps it in `Some`,
- * otherwise, returns `None`.
- */
-export function matchAny(m : MatcheePair) : Maybe<MatcheePair>{
- if (m.remained.length >= 1){
- return {_tag: "Some", value :{
- matched : m.matched + m.remained[0],
- remained : m.remained.substring(1)}};
- }else{
- return {_tag: "None"};
- }
-}
-
-/**
- * @description
- * it returns a function which test if the first char of the `remained` part of
- * the argument of the function is between `l` and `u`, if it's true, update the `MatchedPair` wrapped
- * in `Some`. Otherwise, it returns `None`.
- * * @param l : lower bound char, 1-char string
- * * @param u : upper bound char, 1-char string
- * @returns the updated `MatchedPair` wrapped in `Some(x)` or `None`.
- */
-export function matchRange(l : string, u : string) : (m: MatcheePair) => Maybe<MatcheePair> {
- let lCodepoint = charToCodepoint(l);
- let uCodepoint = charToCodepoint(u);
- if (l > u){
- throw new Error("Error: the codepoint of `"+l+"` is not smaller than `"+u+"`)");
- }
- return (m : MatcheePair)=>{
- if (m.remained.length < 1){
- return {_tag : "None"};
- }
- const charToBeMatched = m.remained[0];
- const codePointToBeMatched = charToCodepoint(charToBeMatched);
- if (codePointToBeMatched >= lCodepoint && codePointToBeMatched <= uCodepoint){
- return {_tag: "Some", value :{
- matched : m.matched + charToBeMatched,
- remained : m.remained.substring(1)}};
- }
- else{
- return {_tag: "None"};
- }
- }
-};