Multiply
提出詳細
type Elem = "I" type Formattable = string | number | bigint | boolean | null | undefined type NumToArr<N extends number, Acc extends readonly unknown[]=[]> = Acc["length"] extends N ? Acc : NumToArr<N, [...Acc, Elem]> type TupleToString<T extends readonly unknown[], Acc extends string=""> = T extends [infer T1 extends Formattable, ...infer T2] ? TupleToString<T2, `${Acc}${T1}`> : Acc type Repeat<T, N extends number, Acc extends readonly unknown[]=[]> = Acc["length"] extends N ? Acc : Repeat<T, N, [...Acc, T]> type RepeatString<S extends string, N extends number> = TupleToString<Repeat<S,N>> type Reverse<S extends string> = S extends `${infer S1}${infer S2}` ? `${Reverse<S2>}${S1}` : "" type StringLength<S extends string, Count extends readonly unknown[]=[]> = S extends `${infer S1}${infer S2}` ? StringLength<S2,[...Count,Elem]> : Count["length"] type PadZero<S extends string, N extends number> = NumToArr<N> extends [...NumToArr<StringLength<S>>, ...infer Rest] ? `${RepeatString<"0",Rest["length"]>}${S}` : S type Padded<S extends string, T extends string> = [ `0${PadZero<PadZero<S,StringLength<S>>,StringLength<T>>}`, `0${PadZero<PadZero<T,StringLength<S>>,StringLength<T>>}`] type TrimLeadingZeros<S extends string> = S extends "0" ? S : S extends `0${infer S2}` ? TrimLeadingZeros<S2> : S type CarryOut<Arr extends readonly unknown[]> = Arr extends [...Repeat<Elem,10>, ...infer Rest] ? [1, Rest["length"]] : [0, Arr["length"]] type SumOneDigit<N extends number, M extends number, CarryIn extends 0|1=0> = CarryIn extends 1 ? CarryOut<[...NumToArr<N>, ...NumToArr<M>, Elem]> : CarryOut<[...NumToArr<N>, ...NumToArr<M>]> type SumReverse<NS extends string, MS extends string, CarryIn extends 0|1=0, Acc extends string=""> = NS extends `${infer X extends number}${infer NRest}` ? MS extends `${infer Y extends number}${infer MRest}` ? SumOneDigit<X,Y,CarryIn> extends [infer CarryOut extends 0|1, infer Result extends number] ? SumReverse<NRest, MRest, CarryOut, `${Acc}${Result}`> : never : never : `${Acc}` type Sum<A extends string | number | bigint, B extends string | number | bigint> = Padded<`${A}`,`${B}`> extends [infer A2 extends string, infer B2 extends string] ? TrimLeadingZeros<Reverse<SumReverse<Reverse<A2>, Reverse<B2>>>> : never type MulOneDigit< N extends number, M extends number, Count extends readonly unknown[]=[], Acc extends readonly unknown[]=[]> = Count["length"] extends M ? Acc["length"] : MulOneDigit<N, M, [...Count, Elem], [...Acc, ...NumToArr<N>]> type Mul10<S extends string> = `${S}0` type MulByOneDigit<NS extends string, M extends number, Acc extends string="0"> = NS extends `${infer X extends number}${infer NRest}` ? MulOneDigit<X,M> extends infer Result extends number ? MulByOneDigit<NRest, M, Sum<Mul10<Acc>, Result>> : never : Acc type MulImpl<NS extends string, MS extends string, Acc extends string="0"> = MS extends `${infer Y extends number}${infer MRest}` ? MulImpl<NS, MRest, Sum<Mul10<Acc>, MulByOneDigit<NS,Y>>> : Acc type Multiply<A extends string | number | bigint, B extends string | number | bigint> = TrimLeadingZeros<MulImpl<`${A}`,`${B}`>>
提出日時 | 2023-09-20 01:22:14 |
---|---|
問題 | Multiply |
ユーザー | sankantsu |
ステータス | Accepted |
import type { Equal, Expect } from '@type-challenges/utils' type cases = [ Expect<Equal<Multiply<2, 3>, '6'>>, Expect<Equal<Multiply<3, '5'>, '15'>>, Expect<Equal<Multiply<'4', 10>, '40'>>, Expect<Equal<Multiply<0, 16>, '0'>>, Expect<Equal<Multiply<'13', '21'>, '273'>>, Expect<Equal<Multiply<'43423', 321543n>, '13962361689'>>, Expect<Equal<Multiply<9999, 1>, '9999'>>, Expect<Equal<Multiply<4325234, '39532'>, '170985150488'>>, Expect<Equal<Multiply<100_000n, '1'>, '100000'>>, Expect<Equal<Multiply<259, 9125385>, '2363474715'>>, Expect<Equal<Multiply<9, 99>, '891'>>, Expect<Equal<Multiply<315, '100'>, '31500'>>, Expect<Equal<Multiply<11n, 13n>, '143'>>, Expect<Equal<Multiply<728, 0>, '0'>>, Expect<Equal<Multiply<'0', 213>, '0'>>, Expect<Equal<Multiply<0, '0'>, '0'>>, ]