In `TypeScript`

, we have the way to create `compose`

function with overloaded something like this:

```
type UnaryFunc<T, R> = (arg: T) => R;
export function compose<T1, T2, R>(
fn2: UnaryFunc<T2, R>,
fn1: UnaryFunc<T1, T2>
): UnaryFunc<T1, R>;
export function compose<T1, T2, T3, R>(
fn3: UnaryFunc<T3, R>,
fn2: UnaryFunc<T2, T3>,
fn1: UnaryFunc<T1, T2>
): UnaryFunc<T1, R>;
export function compose<T1, T2, T3, T4, R>(
fn4: UnaryFunc<T4, R>,
fn3: UnaryFunc<T3, T4>,
fn2: UnaryFunc<T2, T3>,
fn1: UnaryFunc<T1, T2>
): UnaryFunc<T1, R>;
export function compose<T1, T2, T3, T4, T5, R>(
fn5: UnaryFunc<T5, R>,
fn4: UnaryFunc<T4, T5>,
fn3: UnaryFunc<T3, T4>,
fn2: UnaryFunc<T2, T3>,
fn1: UnaryFunc<T1, T2>
): UnaryFunc<T1, R>;
export function compose<T1, T2, T3, T4, T5, T6, R>(
fn6: UnaryFunc<T6, R>,
fn5: UnaryFunc<T5, T6>,
fn4: UnaryFunc<T4, T5>,
fn3: UnaryFunc<T3, T4>,
fn2: UnaryFunc<T2, T3>,
fn1: UnaryFunc<T1, T2>
): UnaryFunc<T1, R>;
export function compose<T1, T2, T3, T4, T5, T6, T7, R>(
fn7: UnaryFunc<T7, R>,
fn6: UnaryFunc<T6, T7>,
fn5: UnaryFunc<T5, T6>,
fn4: UnaryFunc<T4, T5>,
fn3: UnaryFunc<T3, T4>,
fn2: UnaryFunc<T2, T3>,
fn1: UnaryFunc<T1, T2>
): UnaryFunc<T1, R>;
export function compose<T = any, R = any>(
...fns: UnaryFunc<any, any>[]
): UnaryFunc<T, R> {
return function (arg: T): R {
return fns.reduceRight((acc, fn) => fn(acc), arg);
};
}
// Example usage
function addOne(x: number): number {
return x + 1;
}
function twoTimes(x: number): number {
return x * 2;
}
function displayResult(x: number): string {
return `The result is ${x}.`;
}
const resultAfterCalculated = compose(displayResult, twoTimes, addOne);
console.log(resultAfterCalculated(3)) // "The result is 8."
```

In this way above, it makes the `compose`

function’s type inference display a type hint accurately

I wanna do something equivalent to the above in Python like this:

```
from typing import TypeVar, Callable, Any
T1 = TypeVar('T1')
T2 = TypeVar('T2')
T3 = TypeVar('T3')
T4 = TypeVar('T4')
T5 = TypeVar('T5')
T6 = TypeVar('T6')
T7 = TypeVar('T7')
R = TypeVar('R')
def compose(fn1: Callable[[T1], T2], fn2: Callable[[T2], R]) -> Callable[[T1], R],
def compose(
fn1: Callable[[T1], T2],
fn2: Callable[[T2], T3],
fn3: Callable[[T3], R]) -> Callable[[T1], R],
def compose(fn1: Callable[[T1], T2], fn2: Callable[[T2], T3], fn3: Callable[[T3], T4],
fn4: Callable[[T4], R],) -> Callable[[T1], R],
def compose(
fn1: Callable[[T1], T2],
fn2: Callable[[T2], T3],
fn3: Callable[[T3], T4],
fn4: Callable[[T4], T5],
fn5: Callable[[T5], R],
) -> Callable[[T1], R],
def compose(
fn1: Callable[[T1], T2],
fn2: Callable[[T2], T3],
fn3: Callable[[T3], T4],
fn4: Callable[[T4], T5],
fn5: Callable[[T5], T6],
fn6: Callable[[T6], R],
) -> Callable[[T1], R],
def compose(
fn1: Callable[[T1], T2],
fn2: Callable[[T2], T3],
fn3: Callable[[T3], T4],
fn4: Callable[[T4], T5],
fn5: Callable[[T5], T6],
fn6: Callable[[T6], T7],
fn7: Callable[[T7], R],
) -> Callable[[T1], R],
def compose(*funcs: Callable[[Any], Any]) -> Callable[[Any], Any]:
def composed(arg: Any) -> Any:
for func in reversed(funcs):
arg = func(arg)
return arg
return composed
# Example usage
add_one: Callable[[int], int] = lambda x: x + 1
two_times: Callable[[int], int] = lambda x: x * 2
display_result = lambda x: f"The result is {x}."
result_after_calculated = compose(display_result, two_times, add_one)
print(result_after_calculated) # "The result is 8."
```

If it can be, will it possible to make this support Python version lower than v.3.12?