14188-hard-run-length-encoding

Back

namespace RLE {
  // 将归如 3A ηš„ε­—η¬¦δΈ²θ½¬δΈΊ AAA
  type TransformString<
    N extends number,
    Ch extends string,
    Count extends Ch[] = []
  > = number extends N
    ? ""
    : N extends Count["length"]
    ? ""
    : `${Ch}${TransformString<N, Ch, [...Count, Ch]>}`;
  export type Encode<
    S extends string,
    Count extends string[] = [],
    C extends string = ""
  > = S extends `${infer Ch}${infer Rest}`
    ? Ch extends C
      ? Encode<Rest, [...Count, Ch], Ch>
      : C extends ""
      ? Encode<Rest, [...Count, Ch], Ch>
      : `${Count["length"] extends 1
          ? `${Count[0]}`
          : `${Count["length"]}${Count[0]}`}${RLE.Encode<Rest, [Ch], Ch>}`
    : `${Count["length"] extends 1
        ? `${Count[0]}`
        : `${Count["length"]}${Count[0]}`}`;
  export type Decode<S extends string> =
    S extends `${infer N extends number}${infer Char}${infer Others}`
      ? `${TransformString<N, Char>}${RLE.Decode<Others>}`
      : S extends `${infer Char}${infer Others}`
      ? `${TransformString<1, Char>}${RLE.Decode<Others>}`
      : "";
}

Solution by Vampirelee #32697

namespace RLE {
  type EncodeBuffer<B extends string[]> = `${B["length"] extends 1 ? "" : B["length"]}${B[0]}`

  export type Encode<S extends string, B extends string[] = []> = 
    S extends `${infer L}${infer R}`
      ? B["length"] extends 0 
        ? Encode<R, [L]> 
        : L extends B[0] 
          ? Encode<R, [...B, L]>
          : `${EncodeBuffer<B>}${Encode<R, [L]>}`
      : EncodeBuffer<B>;


  type DuplicateChar<N extends number, C extends string, L extends 0[] = []> =
    L["length"] extends N
      ? ""
      : `${C}${DuplicateChar<N, C, [...L, 0]>}`;
      
  export type Decode<S extends string> = 
    S extends `${infer N}${infer L}${infer R}`
      ? N extends `${infer N1 extends number}`
        ? `${DuplicateChar<N1, L>}${Decode<R>}`
        : `${N}${Decode<`${L}${R}`>}`
      : S;
}

Solution by vangie #32258


type NumberString = '1' | '2' | '3' | '4' | '5' | '6' | '7' | '8' | '9'
type _Encode<S extends string, P extends string = '', R extends any[][] = [], T extends any[] = []> = S extends `${infer U}${infer L}` ? (U extends P ? _Encode<L, U, R, [...T, U]> : _Encode<L, U, T extends [] ? R : [...R, T], [U]>) : [...R, T];
type GetCount<T extends any[][]> = T extends [infer S extends any[], ...infer O extends any[][]] ? `${S['length'] extends 1 ? '' : S['length']}${S[0]}${GetCount<O>}` : '';
type StringToArray<T extends string> = T extends `${infer S}${infer O}` ? [S, ...StringToArray<O>] : [];
type OutputStringByCount<T extends string, C extends NumberString, P extends any[] = []> = `${P['length']}` extends `${C}` ? '' : `${T}${OutputStringByCount<T, C, [1, ...P]>}`;

namespace RLE {
  export type Encode<S extends string> = GetCount<_Encode<S>>;
  export type Decode<S extends string, T extends string[] = StringToArray<S>> = 
  T extends [infer F extends string, infer U extends string, ...infer O extends string[]] 
    ? (F extends NumberString ? `${OutputStringByCount<U, F>}${Decode<S, O>}` 
    : `${F}${Decode<S, [U, ...O]>}`) 
  : T[0];
}

Solution by tarotlwei #31860

// your answers
type StringToArray<S extends string> = S extends `${infer Head}${infer Rest}` ? [Head, ...StringToArray<Rest>] : []

type ArrayToString<A> = A extends [infer H, ...infer Rest] ? H extends string ?`${H}${ArrayToString<Rest>}` : '' : ''

type GetNumber<I extends string, A, R extends number[] = []> = A extends [] ? R['length'] : A extends [infer H, ...infer Rest] ? H extends I ? GetNumber<I, Rest, [...R, 0]> :GetNumber<I, Rest, R>   : never

type GetRest<I extends string, A> = A extends [infer H, ...infer Rest] ? H extends I ? GetRest<I, Rest> : [H, ...GetRest<I, Rest>] : []

type EC<T extends string[], R extends string[] = []> = T extends [] ? R : EC<GetRest<T[0], T>, [...R, `${GetNumber<T[0], T> extends 1 ? '' : GetNumber<T[0], T>}${T[0]}`]>

type NumberString = ['1', '2', '3', '4','5','6', '7', '8', '9', '0'][number]

type GetNumberString<N, S extends string, R extends string[] = []> = `${R['length']}` extends N ? ArrayToString<R> : GetNumberString<N, S, [...R, S]>

type DString<S extends unknown[], N extends string = ''> = 
S extends [infer H, ...infer Rest] 
  ? H extends NumberString 
    ? DString<Rest, `${N}${H}`> 
    : H extends string 
      ? [N extends '' ? H : GetNumberString<N,H>, ...DString<GetRest<H, S>>]
    : []
  : []

namespace RLE {
  export type Encode<S extends string> = ArrayToString<EC<StringToArray<S>>>
  export type Decode<S extends string> = ArrayToString<DString<StringToArray<S>>>
}


Solution by 437204933 #29726

type Repeat<S extends string, N extends number, C extends 0[] = [0]> =
  N extends C['length']
  ? S
  : `${S}${Repeat<S, N, [0, ...C]>}`

namespace RLE {
  export type Encode<S extends string, C extends 0[] = [0]> = 
    S extends `${infer L}${infer R}`
    ? R extends `${L}${infer _R}`
      ? Encode<R, [0, ...C]>
      : C['length'] extends 1
        ? `${L}${Encode<R, [0]>}`
        : `${C['length']}${L}${Encode<R, [0]>}`
    : ''
  export type Decode<S extends string> =
    S extends `${infer L}${infer R}`
    ? L extends `${infer X extends number}`
      ? R extends `${infer C}${infer W}`
        ? `${Repeat<C, X>}${Decode<W>}`
        : ''
      : `${L}${Decode<R>}`
    : ''
}

Solution by RuyiLi #27891

namespace RLE {
  export type Encode<S extends string> = EncodeRaw<S, '', [never]>;
  export type Decode<S extends string> = DecodeRaw<S, ''>;

  type EncodeRaw<
    S extends string,
    SPrevSymbol extends string,
    SCount extends never[],
  > = S extends `${infer S0}${infer SReast}`
    ? S0 extends SPrevSymbol
      ? EncodeRaw<SReast, S0, [...SCount, never]>
      : `${SCount['length'] extends 1 ? '' : SCount['length']}${SPrevSymbol}${EncodeRaw<SReast, S0, [never]>}`
    : `${SCount['length'] extends 1 ? '' : SCount['length']}${SPrevSymbol}`;

  type DecodeRaw<S extends string, Count extends string> = S extends `${infer C extends number}${infer SRest}`
    ? DecodeRaw<SRest, `${Count}${C}`>
    : S extends `${infer S0}${infer SRest}`
    ? Count extends `${infer N extends number}`
      ? `${NumberToFilledString<N, S0>}${DecodeRaw<SRest, ''>}`
      : `${S0}${DecodeRaw<SRest, ''>}`
    : '';

  type NumberToFilledString<
    N extends number,
    L extends string,
    Acc extends never[] = [],
  > = Acc['length'] extends N ? '' : `${L}${NumberToFilledString<N, L, [...Acc, never]>}`;
}

Playgrond

Solution by BOCbMOU #27570

type a = RLE.Encode<'AAAAAAAAAAACDXX'> // '11ACD2X'
type b = RLE.Decode<'11ACD2X'> // 'AAAAAAAAAAACDXX'


namespace RLE {
  export type Encode<S extends string, Res extends string = "", Cnt extends 1[] = [1]> = 
  S extends `${infer L}${infer M}${infer R}`
    ? L extends M 
      ? Encode<`${M}${R}`, Res, [...Cnt, 1]>
      : Encode<`${M}${R}`, `${Res}${Cnt['length'] extends 1 ? '' :  Cnt['length']}${L}`, [1]>
    : `${Res}${Cnt['length'] extends 1 ? '' :  Cnt['length']}${S}`
  
  type Repeat<
    S extends string, N extends Number,
    Cnt extends 1[] = [], Res extends string = ""> = 
  Cnt['length'] extends N ? Res : Repeat<S, N, [...Cnt, 1], `${Res}${S}`>

  type GetPreNum<S extends string, Res extends string = ""> = 
  S extends `${infer L extends number}${infer R}`
    ? GetPreNum<R, `${Res}${L}`> : Res extends `${infer T extends number}` ? T : 1;

  export type Decode<
    S extends string, Res extends string = "",
    N extends number = GetPreNum<S>
  > = 
  S extends `${N extends 1 ? '' : N}${infer L}${infer R}`
    ? Decode<R, `${Res}${Repeat<L, N>}`> : `${Res}${S}`
}

Solution by omittee #26975

type EncodeHelper<C extends string, L extends number> = C extends ''
  ? ''
  : L extends 1
  ? C
  : `${L}${C}`;

type DecodeHelper<
  C extends string,
  L extends number,
  N extends 1[] = []
> = N['length'] extends L ? '' : `${C}${DecodeHelper<C, L, [...N, 1]>}`;

namespace RLE {
  export type Encode<
    S extends string,
    Char extends string = '',
    Counter extends 1[] = []
  > = S extends `${infer F}${infer R}`
    ? F extends Char
      ? Encode<R, Char, [...Counter, 1]>
      : `${EncodeHelper<Char, Counter['length']>}${Encode<R, F, [1]>}`
    : `${EncodeHelper<Char, Counter['length']>}`;

  export type Decode<S extends string> =
    S extends `${infer A}${infer B}${infer R}`
      ? A extends `${infer L extends number}`
        ? `${DecodeHelper<B, L>}${Decode<R>}`
        : `${A}${Decode<`${B}${R}`>}`
      : S extends `${infer A}${infer _}`
      ? A
      : '';
}

Solution by JohnLi1999 #26305

type StringLength<T extends string, _Counter extends string[] = []> = T extends `${infer F}${infer R}` ? StringLength<R, [..._Counter, F]> : _Counter[`length`];

namespace RLE {
  export type Encode<S extends string, _Recorder extends string[] = [], _Length extends number = _Recorder[`length`]> =
    S extends `${infer F}${infer R}` ?
    (
      _Length extends 0 ? Encode<R, [..._Recorder, F]> :
      _Recorder[0] extends F ? Encode<R, [..._Recorder, F]> : `${_Length extends 1 ? `` : _Length}${_Recorder[0]}${Encode<S>}`/*pop*/
    ) : `${_Length extends 1 ? `` : _Length}${_Recorder[0]}`/*return*/;

  export type Decode<S extends string, _Recorder extends string = ``, _Target extends string = S extends `${number}${infer A}${any}` ? A : ``> =
    S extends `${infer F}${infer R}` ?
    F extends `${infer N extends number}` ?
    (//Decode
      StringLength<_Recorder> extends N ? `${_Recorder}${Decode<R extends `${any/*_Target*/}${infer RR}` ? RR : ``>}` : Decode<S, `${_Recorder}${_Target}`>
    ) : `${F}${Decode<R>}` :
    ``/*pop*/;
}

// old way
// long-number version
// type MakeArray<L extends number, E, _Result extends E[] = []> = _Result[`length`] extends L ? _Result : MakeArray<L, E, [..._Result, E]>;
// type Join<T extends string[]> = T extends [infer F extends string, ...infer R extends string[]] ? `${F}${Join<R>}` : ``;

// namespace RLE {
//   export type Encode<S extends string, _Counter extends string[] = [], _Parse extends string = `${_Counter[`length`] extends 1 ? `` : _Counter[`length`]}${_Counter[0]}`> =
//     S extends `${infer F}${infer R}` ?
//     ([1] extends [(_Counter[0] extends F | undefined ? 1 : 2) & (_Counter[`length`] extends 9 ? 2 : 1)]/*optional:ι™εˆΆε•ζ¬‘εΊεˆ—ζœ€ε€š9δΈͺ*/ ?
//       Encode<R, [..._Counter, F]> :
//       `${_Parse}${Encode<S, []>}`) :  //recur
//     _Parse; //return

//   export type Decode<S extends string> = S extends `${infer F}${infer R}` ?
//     (F extends `${infer N extends number}` ?
//       (R extends `${infer RF}${infer RR}` ? `${Join<MakeArray<N, RF>>}${Decode<RR>}` : F) :
//       `${F}${Decode<R>}`) :
//     ``;
// }

Solution by E-uler #25359

type StringToArray<S extends string, Acc extends string [] = []> = S extends `${infer First}${infer Rest}`
? StringToArray<`${Rest}`, [...Acc, First]>
: Acc

type ArrayToEncodedString<
  S extends string[], 
  Counter extends unknown[] = [], 
  Result extends string = ''
> = S extends [infer First extends string, infer Second extends string, ...infer Rest extends string[]]
? First extends Second 
  ? ArrayToEncodedString<[First, ...Rest], [...Counter, ''], `${Result}`>
  : Counter['length'] extends 0
    ? ArrayToEncodedString<[Second, ...Rest], [], `${Result}${First}`>
    : ArrayToEncodedString<[Second, ...Rest], [], `${Result}${[...Counter, '']['length'] extends number ? [...Counter, '']['length'] : never}${First}`>
: Counter['length'] extends 0
  ? `${Result}${S[0]}`
  : `${Result}${[...Counter, '']['length'] extends number ? [...Counter, '']['length'] : never}${S[0]}`

type DecodeString<
  S extends string, 
  Counter extends unknown[] = [], 
  Result extends string = ''
> = S extends `${infer First}${infer Rest}`
? `${Counter['length']}` extends First
  ? Result
  : DecodeString<S, [...Counter, ''], `${Result}${Rest}`>
: never

namespace RLE {
  export type Encode<S extends string> = ArrayToEncodedString<StringToArray<S>>
  export type Decode<S extends string, Result extends string = ''> = S extends `${infer First}${infer Second}${infer Rest}`
  ? Lowercase<First> extends First
    ? RLE.Decode<Rest, `${Result}${DecodeString<`${First}${Second}`>}`>
    : RLE.Decode<`${Second}${Rest}`, `${Result}${First}`>
  : `${Result}${S}`
}

Solution by NeylonR #24674

/**
 * RunLength<[]> => ''
 * RunLength<['A']> => ''
 * RunLength<['A', 'A']> => '2'
 * RunLength<['A', 'A', 'A']> => '3'
 * ...
 */
type RunLength<T extends unknown[]> = T['length'] extends 0 | 1 ? '' : T['length']

/**
 * RepeatString<'A', 1> => 'A'
 * RepeatString<'A', 2> => 'AA'
 * RepeatString<'A', 3> => 'AAA'
 */
type RepeatString<
  S extends string,
  N extends number,
  Count extends S[] = [],
  R extends string = '',
> =
  Count['length'] extends N
    ? R
    : RepeatString<S, N, [...Count, S], `${R}${S}`>


namespace RLE {

  export type Encode<S extends string, Count extends string[] = [], R extends string = ''> =
    S extends `${infer A}${infer Rest}`
      ? Count[0] extends A | undefined
        ? Encode<Rest, [A, ...Count], R>
        : Encode<S, [], `${R}${RunLength<Count>}${Count[0]}`>
      : `${R}${RunLength<Count>}${Count[0]}`

  export type Decode<S extends string, R extends string = ''> =
    S extends `${infer A}${infer B}${infer Rest}`
      ? `${A}` extends `${infer N extends number}`
        ? Decode<Rest, `${R}${RepeatString<B, N>}`>
        : Decode<`${B}${Rest}`, `${R}${A}`>
      : `${R}${S}`
}

Solution by drylint #23125

namespace RLE {
  export type Encode<S extends string, Prev extends string[] = []> =
    Prev extends [] ? (
      `${S extends `${infer First}${infer Rest}` ? Encode<Rest, [First]> : ''}`
    ) : S extends `${Prev[0]}${infer Rest}` ? (
      Encode<Rest, [...Prev, Prev[0]]>
    ) : Prev['length'] extends 1 ? (
      `${Prev[0]}${S extends `${infer First}${infer Rest}` ? Encode<Rest, [First]> : ''}`
    ) : (
      `${Prev['length']}${Prev[0]}${S extends `${infer First}${infer Rest}` ? Encode<Rest, [First]> : ''}`
    )
  export type Decode<S extends string, Num extends string = '', C extends 1[] = []> =
    S extends `${infer First extends number}${infer Rest}` ? (
      Decode<Rest, `${Num}${First}`>
    ) : Num extends '' ? (
      S extends `${infer First}${infer Rest}` ? `${First}${Decode<Rest>}` : ''
    ) : Num extends `${C['length']}` ? (
      S extends `${string}${infer Rest}` ? Decode<Rest> : ''
    ) : (
      S extends `${infer First}${string}` ? `${First}${Decode<S, Num, [...C, 1]>}` : ''
    )
}

Playground

Solution by teamchong #22545

namespace RLE {
  type CharRep<S extends string, N extends number, C extends unknown[]=[]> = C['length'] extends N ? '' : `${S}${CharRep<S,N,[...C,0]>}`;
 
  export type Encode<S extends string, C extends string[]=[], NS extends string=`${C['length'] extends 1 ? '': C['length']}${C[0]}`> = 
    S extends `${infer F}${infer Rest}` ? C[0] extends F | undefined ? Encode<Rest, [...C, F]> : 
    `${NS}${Encode<Rest, [F]>}` : NS;
  export type Decode<S extends string> = S extends `${infer NS}${infer C}${infer Rest}` ?
    NS extends `${infer N extends number}` ? `${CharRep<C, N>}${Decode<Rest>}` : `${NS}${Decode<`${C}${Rest}`>}` : S 
}

Solution by Karamuto #22283

// your answers
namespace RLE {
  export type Encode<
    S extends string,
    PreChar extends string = "",
    Count extends 0[] = []
  > = S extends ""
    ? PreChar extends ""
      ? ""
      : Count["length"] extends 1 | 0
      ? PreChar
      : `${Count["length"]}${PreChar}`
    : S extends `${infer F}${infer R}`
    ? F extends PreChar
      ? Encode<R, PreChar, [0, ...Count]>
      : Count["length"] extends 1 | 0
      ? `${PreChar}${Encode<R, F, [0]>}`
      : `${Count["length"]}${PreChar}${Encode<R, F, [0]>}`
    : "";

  export type Decode<
    S extends string,
    PreNumStr extends string = ""
  > = S extends `${infer F}${infer R}`
    ? IsLetter<F> extends true
      ? PreNumStr extends ""
        ? `${F}${Decode<R, "">}`
        : `${Repeat<F, ToNumber<PreNumStr>>}${Decode<R, "">}`
      : Decode<R, `${PreNumStr}${F}`>
    : "";

  type Repeat<
    T extends string,
    N extends number,
    Count extends 0[] = []
  > = Count["length"] extends N ? "" : `${T}${Repeat<T, N, [0, ...Count]>}`;
  type IsLetter<T extends string> = Uppercase<T> extends Lowercase<T>
    ? false
    : true;
  type ToNumber<
    T extends string,
    Res extends number = 0
  > = T extends `${infer F}${infer R}`
    ? F extends keyof NumberMap
      ? ToNumber<
          R,
          NumberMap[F] extends 0
            ? Mul<Res, 10>
            : Add<Mul<Res, 10>, NumberMap[F]>
        >
      : never
    : Res;
  type NumberMap = {
    "0": 0;
    "1": 1;
    "2": 2;
    "3": 3;
    "4": 4;
    "5": 5;
    "6": 6;
    "7": 7;
    "8": 8;
    "9": 9;
  };
  // δΈ€ζ•°η›ΈεŠ 
  type Add<
    A extends number,
    B extends number,
    CountA extends 0[] = [],
    CountB extends 0[] = []
  > = CountA["length"] extends A
    ? CountB["length"] extends B
      ? [...CountA, ...CountB]["length"]
      : Add<A, B, CountA, [0, ...CountB]>
    : CountB["length"] extends B
    ? Add<A, B, [0, ...CountA], CountB>
    : Add<A, B, [0, ...CountA], [0, ...CountB]>;

  // δΈ€ζ•°η›ΈδΉ˜
  // 2 x 5 = 2 + 2 + 2 + 2
  type Mul<
    A extends number,
    B extends number,
    Res extends number = 0,
    Cnt extends 0[] = []
  > = Cnt["length"] extends B ? Res : Mul<A, B, Add<A, Res>, [0, ...Cnt]>;
}

Solution by acwink #22161

// ['a', 'b', 'c'] => 'abc'
type Join<T extends string[]> = 
  T extends [infer First extends string, ...infer Rest extends string[]] 
  ? `${First}${Join<Rest>}` 
  : ''

// Fill<'a', 3'> => 'aaa'
type Fill<Char extends string, N extends number, _A extends string[] = []> = 
  _A['length'] extends N
  ? _A
  : Fill<Char, N, [..._A, Char]>

// 'abc' => [['a'], ['b'], ['c']]
type SplitChars<T extends string> = 
  T extends `${infer First}${infer Rest}` 
  ? [[First], ...SplitChars<Rest>] 
  : []

// [['a'], ['a'], ['b'], ['c']] => [['a', 'a'], ['b'], ['c']]
type JoinSame<T extends string[][]> = 
  T extends [infer First extends string[], infer Second extends string[], ...infer Rest extends string[][]]
  ? First[0] extends Second[0]
    ? JoinSame<[[...First, First[0]], ...Rest]>
    : [First, ...JoinSame<[Second, ...Rest]>]
  : T

// [['a', 'a'], ['b'], ['c']] => ['2a', 'b', 'c']
type EncodeMap<T extends string[][]> = 
  T extends [infer First extends string[], ...infer Rest extends string[][]]
  ? First['length'] extends 1
    ? [First[0], ...EncodeMap<Rest>]
    : [`${First['length']}${First[0]}`, ...EncodeMap<Rest>]
  : []

// [['2'], ['a'], ['b'], ['c']] => [[2, 'a'], [1, 'b'], [1, 'c']]
type JoinCountChar<T extends string[][]> = 
  T extends [[infer First extends string], ...infer Rest extends string[][]]
  ? First extends `${infer N extends number}`
    ? Rest extends [[infer Second], ...infer RRest extends string[][]]
      ? [[N, Second], ...JoinCountChar<RRest>]
      : never
    : [[1, First], ...JoinCountChar<Rest>]
  : []

// [[2, 'a'], [1, 'b'], [1, 'c']] => ['aa', 'b', 'c']
type DecodeMap<T extends [number, string][]> = 
  T extends [[infer C extends number, infer Char extends string], ...infer Rest extends [number, string][]]
  ? [Join<Fill<Char, C>>, ...DecodeMap<Rest>]
  : []

namespace RLE {
  export type Encode<S extends string> = Join<EncodeMap<JoinSame<SplitChars<S>>>>
  export type Decode<S extends string> = Join<DecodeMap<JoinCountChar<SplitChars<S>>>>
}

playground

Time comsuming but not hard, just make a lot of type utilities.

Solution by zhaoyao91 #22091

namespace RLE {
    export type Encode<
        S,
        C extends string[] = [],
        R extends string = ''>
        = S extends `${infer A extends string}${infer B extends string}`
        ? C extends []
        ? Encode<B, [A], R>
        : A extends C[number]
        ? Encode<B, [...C, A], R>
        : Encode<B, [A], `${R}${C['length'] extends 1 ? '' : C['length']}${C[number]}`>
        : `${R}${C['length'] extends 1 ? '' : C['length']}${C[number]}`
    type Repeat<S extends string, N extends number, R extends string = '', C extends any[] = []>

        = C['length'] extends N ? R : Repeat<S, N, `${R}${S}`, [...C, unknown]>
    export type Decode<
        S extends string,
        R extends string = ''>
        = S extends `${infer A}${infer B extends string}`
        ? A extends `${infer N extends number}`
        ? B extends `${infer D extends string}${infer F extends string}`
        ? Decode<F, `${R}${Repeat<D, N>}`> : 'wocao'
        : Decode<B, `${R}${A}`>
        : R
}

Solution by goddnsgit #22040

type Build<
  T extends number,
  Result extends Array<never> = []
> = Result["length"] extends T ? Result : Build<T, [...Result, never]>;

type Add<A extends number, B extends number> = [
  ...Build<A>,
  ...Build<B>
]["length"];
namespace RLE {
  type DuplicateRemovalString<
    G extends string,
    Result extends string = "",
    Bucket extends Array<string> = []
  > = G extends `${infer A}${infer B}`
    ? A extends Bucket[number]
      ? DuplicateRemovalString<B, Result, Bucket>
      : DuplicateRemovalString<B, `${Result}${A}`, [...Bucket, A]>
    : Result;

  type TransformEncode<
    T extends string,
    Mapping extends Record<string, string>,
    Result extends string = ""
  > = T extends `${infer A}${infer B}`
    ? TransformEncode<B, Mapping, `${Result}${Mapping[A]}`>
    : Result;

  export type Encode<
    S extends string,
    Result extends Record<string, number> = {},
    C extends string = S
  > = S extends `${infer A}${infer B}`
    ? Encode<
        B,
        {
          [P in keyof Omit<Result, A>]: Omit<Result, A>[P];
        } & {
          [P in A]: A extends keyof Result ? Add<Result[P], 1> & number : 1;
        },
        C
      >
    : TransformEncode<
        DuplicateRemovalString<C>,
        {
          [P in keyof Result]: `${Result[P] extends 1 ? "" : Result[P]}${P &
            string}`;
        }
      >;

  export type RepeatString<
    T extends string,
    K extends number,
    Result extends string = "",
    Count extends Array<never> = []
  > = Count["length"] extends K ?
       Result:
       RepeatString<T,K,`${Result}${T}`,[...Count,never]>

  export type Decode<
    S extends string,
    Result extends string = ""
  > = S extends `${infer A}${infer B}`
    ? A extends `${infer G extends number}`
      ? B extends `${infer C}${infer D}`
        ? Decode<D, `${Result}${RepeatString<C,G>}`>
        : never
      : Decode<B, `${Result}${A}`>
    : Result;
}

Solution by so11y #21347

namespace RLE {
  type Compress<Tmp extends string[]> = Tmp["length"] extends 0
    ? ""
    : `${Tmp["length"] extends 1 ? "" : Tmp["length"]}${Tmp[0]}`;

  export type Encode<
    S extends string,
    Tmp extends string[] = []
  > = S extends `${infer H}${infer T}`
    ? Tmp["length"] extends 0
      ? Encode<T, [H]>
      : Tmp[0] extends H
      ? Encode<T, [...Tmp, H]>
      : `${Compress<Tmp>}${Encode<T, [H]>}`
    : Compress<Tmp>;

  type Repeat<
    C extends string,
    T extends string,
    Arr extends any[] = [any]
  > = `${Arr["length"]}` extends `${T}`
    ? C
    : `${C}${Repeat<C, T, [...Arr, any]>}`;
  
  export type Decode<S extends string, N extends string = ""> = S extends ""
    ? ""
    : S extends `${infer H}${infer T}`
    ? H extends `${number}`
      ? Decode<T, `${N}${H}`>
      : `${Repeat<H, N extends "" ? "1" : N>}${Decode<T, "">}`
    : Repeat<S, N extends "" ? "1" : N>;
}

Solution by bedis-elacheche #21120

type ArrayToString<
  T extends string[],
  L extends number = T['length']
> = L extends 0 ? '' : L extends 1 ? T[0] : `${L}${T[0]}`;
type NumberToString<
  N extends string,
  S extends string,
  L extends unknown[] = [],
  R extends string = ''
> = N extends ''
  ? S
  : `${L['length']}` extends N
  ? R
  : NumberToString<N, S, [...L, 1], `${R}${S}`>;
namespace RLE {
  export type Encode<
    S extends string,
    L extends string[] = []
  > = S extends `${infer A}${infer Rest}`
    ? A extends L[0]
      ? Encode<Rest, [...L, A]>
      : `${ArrayToString<L>}${Encode<Rest, [A]>}`
    : `${ArrayToString<L>}`;

  export type Decode<
    S extends string,
    N extends string = ''
  > = S extends `${infer A}${infer Rest}`
    ? A extends `${number}`
      ? Decode<Rest, `${N}${A}`>
      : `${NumberToString<N, A>}${Decode<Rest>}`
    : '';
}

Solution by bigcreate #20919

namespace RLE {
  export type Encode<S extends string, _Last extends string = '', _Length extends 0[] = [0], _Result extends string = ''> =
    S extends `${ infer F }${ infer Rest }`
      ? _Last extends ''
        ? RLE.Encode<S, F>
        : F extends _Last
          ? RLE.Encode<Rest, _Last, [ ..._Length, 0 ], `${ _Length['length'] extends 1 ? '' : _Length['length'] }${ F }`>
          : `${ _Result }${ RLE.Encode<S> }`
      : _Result

  export type Decode<S extends string, _CountHelper extends 0[] = [], _Result extends string = ''> =
    S extends `${ infer Length extends number }${ infer Character }${ infer Rest }`
      ? _CountHelper['length'] extends Length
        ? `${ _Result }${ Decode<Rest, []> }`
        : Decode<S, [ ..._CountHelper, 0 ], `${ _Result }${ Character }`>
      : S extends `${ infer SingleCharacter }${ infer Rest }`
        ? Decode<Rest, [], `${ _Result }${ SingleCharacter }`>
        : _Result
}

Solution by lvjiaxuan #20832

type Length<T extends any[], L = T['length']> = L extends number ? L : 0;

type ArrayFromLength<T extends number, A extends any[] = []> =
  A['length'] extends T
    ? A
    : ArrayFromLength<T, [any, ...A]>

type Repeat<V extends string, T extends string, Result extends string = '', U extends any[] = []> =
  `${ U['length'] }` extends T
    ? Result
    : Repeat<V, T, `${ Result }${ V }`, [any, ...U]>

type Increase<T extends number> = Length<[...ArrayFromLength<T>, any]>

type IsNumberString<T extends string> = T extends `${ infer V extends number }` ? true : false;

namespace RLE {
  export type Encode<S extends string, PreChar extends string = '', Num extends number = 0, Result extends string = ''> =
    S extends `${ infer F }${ infer R }`
      ? F extends PreChar
        ? Encode<R, PreChar, Increase<Num>, Result>
        : Encode<R, F, 1, `${ Result }${ Num extends 0 | 1 ? '' : Num }${ PreChar }`>
      : `${ Result }${ Num extends 0 | 1 ? '' : Num }${ PreChar }`;

  export type Decode<S extends string, Num extends string = '', Result extends string = ''> = S extends `${ infer L }${ infer R }`
    ? IsNumberString<L> extends true
      ? Decode<R, `${ Num }${ L }`, Result>
      : Decode<R, '', `${ Result }${ Repeat<L, Num extends '' ? '1' : Num> }`>
    : Result;
}

Solution by xiexuan-star #20137

namespace RLE {
  type TenTimesArray<T extends unknown[]> = [
    ...T,
    ...T,
    ...T,
    ...T,
    ...T,
    ...T,
    ...T,
    ...T,
    ...T,
    ...T
  ]

  type ArrayWithinTen<
    T extends string | number,
    C extends string,
    R extends unknown[] = []
  > = `${R['length']}` extends `${T}` ? R : ArrayWithinTen<T, C, [C, ...R]>

  type ArrayWithLength<
    T extends string | number,
    C extends string,
    R extends unknown[] = []
  > = `${T}` extends `${infer A}${infer B}`
    ? ArrayWithLength<B, C, [...TenTimesArray<R>, ...ArrayWithinTen<A, C>]>
    : R

  type ArrayToString<T extends unknown[]> = T extends [infer A, ...infer B]
    ? A extends string
      ? `${A}${ArrayToString<B>}`
      : ArrayToString<B>
    : ''

  type RepeatChar<T extends string, R extends string | number> = ArrayToString<
    ArrayWithLength<R, T>
  >

  export type Encode<
    S extends string,
    C extends string[] = []
  > = S extends `${infer A}${infer B}`
    ? C['length'] extends 0
      ? Encode<B, [A]>
      : C[0] extends A
      ? Encode<B, [...C, A]>
      : `${C['length'] extends 1 ? '' : C['length']}${C[0]}${Encode<S, []>}`
    : `${C['length'] extends 1 ? '' : C['length']}${C[0]}`

  export type Decode<
    S extends string,
    C extends string = ''
  > = S extends `${infer A}${infer B}`
    ? A extends `${number}`
      ? Decode<B, `${C}${A}`>
      : `${C extends '' ? A : RepeatChar<A, C>}${Decode<B>}`
    : S
}

Solution by theoolee #19809

// your answers
namespace RLE {

  export type Encode<S extends string, C extends unknown[] = [], R extends string = '', C1 extends unknown[] = [...C, unknown]> = S extends `${infer Head extends string}${infer Tail extends string}`
    ? Tail extends `${Head}${string}`
      ? Encode<Tail, C1, R>
      : C extends []
        ? Encode<Tail, [], `${R}${Head}`>
        : Encode<Tail, [], `${R}${C1['length']}${Head}`>
    : R
  ;      
  
  // append N number of C to R
  // NC<'A', 3, 'RR'> = 'RRAAA'
  type NC<C extends string, N extends number, R extends string , A extends unknown[] = []> = N extends A['length'] ? R
    : NC<C, N, `${R}${C}`, [...A, unknown]>
  ;
  export type Decode<S extends string, R extends string = ''> = S extends `${infer Head extends string}${infer Char extends string}${infer Tail extends string}`
    ? Head extends `${infer Head extends number}`
      ? Decode<Tail, NC<Char, Head, R>>
      : Decode<`${Char}${Tail}`, `${R}${Head}`> 
    : `${R}${S}`
}

Solution by alexfung888 #18083

// your answers
type Num = '1' | '2' | '3' | '4' | '5' | '6' | '7' | '8' | '9' | '0';

type TransToArr<N extends Num, Result extends unknown[] = []> = `${Result['length']}` extends N ? Result : TransToArr<N, [...Result, unknown]>;

type Repeat<N extends unknown[], S extends string, Result extends string = ''> = N extends [infer _R, ...infer U]
                                                                                    ? Repeat<U, S, `${Result}${S}`>
                                                                                    : Result

type Trans<T extends string, S extends string = '', Cache extends unknown[] = []> = T extends `${infer R}${infer U}`
                                                                                        ? Trans<U, R, [...Cache, unknown]>
                                                                                        : `${Cache['length'] extends 1 ? '' : Cache['length']}${S}`;

type isSame<S extends string, R extends string> = R extends '' ? true : R extends `${infer J}${infer _U}` 
                                                    ? J extends S ? true : false
                                                    : R extends S ? true : false
namespace RLE {
  export type Encode<S extends string, Pre extends string = '', Result extends string = ''> = S extends `${infer R}${infer U}${infer K}`
                                                                                                ? Pre extends '' 
                                                                                                        ? RLE.Encode<`${U}${K}`, R, Result>
                                                                                                        : isSame<R, Pre> extends true
                                                                                                                    ? RLE.Encode<`${U}${K}`, `${Pre}${R}`, Result>
                                                                                                                    : RLE.Encode<`${U}${K}`, R, `${Result}${Trans<Pre>}`>
                                                                                                : isSame<S, Pre> extends true ? `${Result}${Trans<`${Pre}${S}`>}`
                                                                                                                                  : `${Result}${Trans<`${Pre}`>}${S}` 
  export type Decode<S extends string, PreNum extends Num | '' = '', Result extends string = ''> = S extends `${infer R}${infer K}`
                                                                                                    ? R extends Num
                                                                                                        ? Decode<K, R, Result>
                                                                                                        : PreNum extends ''
                                                                                                                    ? Decode<K, '', `${Result}${R}`>
                                                                                                                    : PreNum extends Num
                                                                                                                                ? Decode<K, '', `${Result}${Repeat<TransToArr<PreNum>, R>}`>
                                                                                                                                : never
                                                                                                    : Result
}

Solution by jiaaoMario #18057

type LastLetter<T extends any[][]> = T extends [...infer Q, infer S] ? S extends any[] ? S['length'] extends 0 ? unknown : S[0] : unknown : unknown; type RunToString<T extends any[][] = [], R extends string = ''> = T extends [infer E, ...infer F] ? E extends any[] ? F extends any[] ? E['length'] extends 1 ? RunToString<F, ${R}${E[0]}> : RunToString<F, ${R}${E['length']}${E[0]}> : never : never : R;

type RunLengthEncoder<T extends string, R extends any[][] = []> = T extends ${infer E}${infer F} ? LastLetter extends E ? R extends [...infer U, infer S] ? U extends any[] ? S extends any[] ? RunLengthEncoder<F, [...U, [...S, S[0]]]> : never : never : never : RunLengthEncoder<F, [...R, [E]]> : RunToString;

type RunNumber = '0' | '1' | '2' | '3' | '4' | '5' | '6' | '7' | '8' | '9'; type RepeatLetter<T extends string, L extends string, P extends 0[] = [], R extends string = ''> = L extends '' ? T : ${P['length']} extends L ? R : RepeatLetter<T, L, [...P, 0], ${R}${T}>;

type RunLengthDecoder<T extends string, R extends string = '', L extends string = ''> = T extends ${infer E}${infer F} ? E extends RunNumber ? RunLengthDecoder<F, R, ${L}${E}> : RunLengthDecoder<F, ${R}${RepeatLetter<E, L>}> : R;

Solution by my5201314zwl #17183

namespace RLE {
  type RepeatChar<N, S extends string, C extends any[] = [any], R = S> =
    N extends "" ? S : `${C['length']}` extends N ? R : RepeatChar<N, S, [...C, any], `${R & string}${S}`>;
  type MakeEncodedStr<Res, C extends any[], D> = `${Res & string}${C['length'] extends 1 ? "" : C['length']}${D & string}`;
  export type Encode<S extends string, D = '', Res = "", C extends any[] = [any]> =
    S extends `${infer F}${infer R}`
      ? F extends D
        ? Encode<R, F, Res, [...C, any]>
        : Encode<R, F, MakeEncodedStr<Res, C, D>>
      : MakeEncodedStr<Res, C, D>;
  export type Decode<S extends string, N = ''> =
    S extends `${infer F extends number}${infer R}`
      ? Decode<R, `${N & string}${F}`>
      : S extends `${infer F}${infer R}`
        ? `${RepeatChar<N, F>}${Decode<R>}`
        : '';
}

Solution by BulatDashiev #16978

type Make10<S extends string> = `${S}${S}${S}${S}${S}${S}${S}${S}${S}${S}`

type Repeat<T extends string,N extends string,R extends string = ''> = 
    N extends `${infer F}${infer L}`?
      F extends '1'?
        Repeat<T,L,`${Make10<R>}${T}`>:
        F extends '2'?
          Repeat<T,L,`${Make10<R>}${T}${T}`>:
            F extends '3'?
              Repeat<T,L,`${Make10<R>}${T}${T}${T}`>:
                F extends '4'?
                  Repeat<T,L,`${Make10<R>}${T}${T}${T}${T}`>:
                    F extends '5'?
                      Repeat<T,L,`${Make10<R>}${T}${T}${T}${T}${T}`>:
                        F extends '6'?
                          Repeat<T,L,`${Make10<R>}${T}${T}${T}${T}${T}${T}`>:
                            F extends '7'?
                              Repeat<T,L,`${Make10<R>}${T}${T}${T}${T}${T}${T}${T}`>:
                                F extends '8'?
                                  Repeat<T,L,`${Make10<R>}${T}${T}${T}${T}${T}${T}${T}${T}`>:
                                    F extends '9'?
                                      Repeat<T,L,`${Make10<R>}${T}${T}${T}${T}${T}${T}${T}${T}${T}`>:
                                        Repeat<T,L,Make10<R>>

      :R

namespace RLE {
  type Length<T extends number> = T extends 1?'':`${T}`


  export type Encode<S extends string,R extends string = '',Q extends string[] = []> = 
    S extends `${infer F}${infer L}`?
      Q['length'] extends 0?
        Encode<L,R,[F]>
        :F extends Q[0]?
          Encode<L,R,[...Q,F]>
          :Encode<L,`${R}${Length<Q['length']>}${Q[0]}`,[F]>

      :Q['length'] extends 0?
        R:`${R}${Length<Q['length']>}${Q[0]}`


  
  type Num = '0' | '1' | '2' | '3' | '4' | '5' | '6' | '7' | '8' | '9'
  export type Decode<S extends string,N extends string = '',R extends string = ''> = 
    S extends `${infer F}${infer L}`?
      F extends Num?
        Decode<L,`${N}${F}`,R>
        :Decode<L,'',`${R}${Repeat<F,N extends ''?'1':N>}`>
      :R
}

Solution by jiangshanmeta #16799

// your answers

/**
 * ParseInt<'A'> // never
 * ParseInt<'1'> // 1
 */
type ParseInt<T extends string> = T extends `${infer R extends number}`
  ? R
  : never

/**
 * FillString<'A', 0> // ''
 * FillString<'A', 1> // 'A'
 * FillString<'A', 3> // 'AAA'
 */
type FillString<T extends string, L extends number, R extends T[] = [], To extends string = ''> = R['length'] extends L
  ? To
  : FillString<T, L, [T, ...R], `${To}${T}`>
namespace RLE {
  export type Encode<
    S extends string,
    Cache extends string[] = [],
    Result extends string = ''
  > = S extends `${infer F}${infer R}`
    ? Cache extends []
      ? Encode<R, [...Cache, F], Result>
      : Cache[0] extends F
        ? Encode<R, [...Cache, F], Result>
        : Encode<R, [F], `${Result}${Cache['length'] extends 1 ? '' : Cache['length']}${Cache[0]}`>
    : `${Result}${Cache[0]}`

  export type Decode<
    S extends string,
    N extends number = never,
    Result extends string = ''
  > = S extends `${infer F}${infer R}`
    ? [ParseInt<F>] extends [never]
      ? [N] extends [never]
        ? Decode<R, never, `${Result}${F}`>
        : Decode<R, never, `${Result}${FillString<F, N>}`>
      : Decode<R, ParseInt<F>, Result>
    : Result
}

Solution by humandetail #16559

namespace RLE {
  /*
Adds one to a given number by creating an array and adding random numbers onto it until it's size is the given number. Then add another number and return the length. 
Input(Number: 5)
Output: 6
*/
  type NumberPlusOne<T extends number, Acc extends number[] = []>= Acc['length'] extends T ? [...Acc, 1]['length']: NumberPlusOne<T, [...Acc, 1]>

 /*
 Temp is needed to check if we are still getting the same string from the array (e.g. A)
 TempCount is needed to count how many times a Char occurs
*/
  export type Encode<S extends string, Temp extends string = "", TempCount extends number = 0, Result extends string = ""> = S extends `${infer H}${infer Tail}` 
  ? H extends Temp 
    /*  If we still get the same char, just add one to the count */
     ? Encode<Tail, Temp, NumberPlusOne<TempCount>, Result>
      /*  If the count is one and we are not getting the same char again, just reset everything and add the char to the result (e.g for the B) */
     : TempCount extends 1
       ? Encode<Tail, H, 1, `${Result}${Temp}`>
       /* As tempCount can be 0 for the `B` in the string, we don't add the number to the result. */
     : Encode<Tail, H, 1, `${Result}${TempCount extends 0 ? "" : TempCount}${Temp}`>
  : `${Result}${Temp}`;

/*
Duplicates the given string n-times 
Input(Char: "AB", Number: 3)
Output: "ABABAB"
*/
type MultiplyChar<C extends string, N extends number, Acc extends number[] = [], Result extends string = ""> = Acc['length'] extends N ? Result: MultiplyChar<C, N, [...Acc,1], `${Result}${C}`>



 /*
1. Iterate the given string and look for the pattern of number and string together, e.g. 3A, 2C, 6X (`${infer H extends number}${infer Char}${infer Tail}`)
2. If there is a match (e.g 3A), call the function again and only return the tail of the String and add the Char (A) multiple times (3) to the result-string
3. If there is no match, look if we are currently at a normal char, e.g (B). If so, infer it and add it to the result
Note: Read more about the part `${infer H extends number}` here => https://devblogs.microsoft.com/typescript/announcing-typescript-4-8-beta/#infer-types-template-strings
*/
export type Decode<S extends string, Result extends string = ""> = S extends `${infer H extends number}${infer Char}${infer Tail}` ? Decode<Tail, `${Result}${MultiplyChar<Char, H>}`> : S extends `${infer H}${infer Tail}` ? Decode<Tail, `${Result}${H}`>: Result

}

Solution by JohannesSchwegler #16351

// your answerstype Letter =
    'A'|'B'|'C'|'D'|'E'|'F'|'G'|'H'|'I'|'J'|'K'|'L'|'M'|'N'|'O'|'P'|'Q'|'R'|'S'|'T'|'U'|'V'|'W'|'X'|'Y'|'Z'|' '|'' ;

type Digit =
    '0'|'1'|'2'|'3'|'4'|'5'|'6'|'7'|'8'|'9' ;

type Dictionary<
    L extends string >=
{
  '0':``,
  '1':`${L}`,
  '2':`${L}${L}`,
  '3':`${L}${L}${L}`,
  '4':`${L}${L}${L}${L}`,
  '5':`${L}${L}${L}${L}${L}`,
  '6':`${L}${L}${L}${L}${L}${L}`,
  '7':`${L}${L}${L}${L}${L}${L}${L}`,
  '8':`${L}${L}${L}${L}${L}${L}${L}${L}`,
  '9':`${L}${L}${L}${L}${L}${L}${L}${L}${L}`,
} ;

type _10<
    L extends string> =
    `${L}${L}${L}${L}${L}${L}${L}${L}${L}${L}`  ;

type Multyply<
    A extends string,
    B extends string> =
    A extends `${infer R}${infer U}`
    ? `${B}${Multyply<U,B>}`
    : ''  ;

type ReverseString<
    S extends string> =
    S extends `${infer R extends string}${infer U extends string}`
    ? `${ReverseString<U>}${R}`
    : ''  ;

type ReversedNumberToStringSequence<
    ReverseStringifiedNumber extends string,
    L extends string> =
    ReverseStringifiedNumber extends `${infer R extends keyof Dictionary<L>}${infer U extends string}`
    ? `${Dictionary<L>[R]}${Multyply<_10<L>,ReversedNumberToStringSequence<U,L>>}`
    : ''  ;

namespace RLE {
  export type Encode<
      S extends string,
      CurrentLetter extends Letter = '',
      CurrentLetterRTuple extends Letter[] =[],
      EncodeResult extends string ='',      
      CurrentSize extends string = 
      CurrentLetterRTuple['length'] extends 0|1 
      ? '' 
      : `${CurrentLetterRTuple['length']}` > = 
      S extends `${infer R extends Letter}${infer U extends string}`
      ? R extends CurrentLetter
      ? Encode<U,CurrentLetter,[...CurrentLetterRTuple,R],EncodeResult>
      : Encode<U,R,[R],`${EncodeResult}${CurrentSize}${CurrentLetter}`>
      : `${EncodeResult}${CurrentSize}${CurrentLetter}` ;

  export type Decode<
      S extends string,
      CurrentLetter extends Letter = '',
      CurrentSize extends string = '' ,
      DecodeResult extends string = '' > = 
      S extends `${infer R extends Digit}${infer U extends string}`
      ? Decode<U,CurrentLetter,`${CurrentSize}${R}`,DecodeResult>
      : S extends `${infer R extends Letter}${infer U extends string}`
      ? Decode<
          U,
          R,
          '',
          `${DecodeResult}${ReversedNumberToStringSequence<ReverseString<CurrentSize extends '' ? '1' : CurrentSize>,R>}`>
      : `${DecodeResult}` ;
} ;

Solution by justBadProgrammer #16087