# Support dynamic overload

**URL:** <https://discuss.python.org/t/support-dynamic-overload/105174>\
**Category:** Ideas\
**Tags:** typing\
**Created:** [December 3, 2025, 6:12am UTC](https://discuss.python.org/t/support-dynamic-overload/105174 "2025-12-03T06:12:46Z")\
**Posts on this page:** 4\
**Page:** 1

<div class="post-metadata">

**Author:** ![STofone](https://sea2.discourse-cdn.com/flex002/user_avatar/discuss.python.org/stofone/32/24741_2.png) [@STofone](https://discuss.python.org/u/STofone)\
**Post date:** [December 3, 2025, 6:12am UTC](https://discuss.python.org/t/support-dynamic-overload/105174/1 "2025-12-03T06:12:46Z")

</div>

in typing.py

```python
NoType = object()

def cast_overload(func, overload_func, type=NoType):
    """If tpye is NoType, type = Type[overload_func]"""
    f = getattr(func, " __func__", func)
    of = getattr(overload_func, " __func__", overload_func)
    try:
        _overload_registry[f. __module__][f. __qualname__][
            of. __code__.co_firstlineno
        ] = overload_func
    except AttributeError:
        # Not a normal function; ignore.
        pass
    return overload_func

```

Usage

```python
from typing import Callable, Concatenate, LiteralString, cast_overload

factory_dict = dict[str, Callable]()

def factory(key, *args, **kwargs):
    return factory_dict[key](*args, **kwargs)

def register[K: LiteralString](key: K):
    def decorator[**P, T](func: Callable[P, T]):
        factory_dict[key] = func
        return cast_overload(factory, func, Callable[Concatenate[K, P], T])

    return decorator

@register("function1")
def func1(x, y, z):
    pass

@register("function2")
def func2(a, b, c):
    pass

```

This can support type hint for `Interface` & `implementation`

---

<div class="post-metadata">

**Author:** ![Nineteendo](https://sea2.discourse-cdn.com/flex002/user_avatar/discuss.python.org/nineteendo/32/19122_2.png) [@Nineteendo](https://discuss.python.org/u/Nineteendo)\
**Post date:** [December 3, 2025, 6:45am UTC](https://discuss.python.org/t/support-dynamic-overload/105174/2 "2025-12-03T06:45:15Z")

</div>

There’s `functools.singledispatch()`

---

<div class="post-metadata">

**Author:** ![STofone](https://sea2.discourse-cdn.com/flex002/user_avatar/discuss.python.org/stofone/32/24741_2.png) [@STofone](https://discuss.python.org/u/STofone)\
**Post date:** [December 4, 2025, 6:52am UTC](https://discuss.python.org/t/support-dynamic-overload/105174/3 "2025-12-04T06:52:09Z")

</div>

`singledispatch` fixes the first argument as the dispatch type, and dispatch by itself.

I want to dispatch by myself and the first argument of implementation is not type for dispatch.

What i want is more like overload for pre-defined function

---

<div class="post-metadata">

**Author:** ![bswck](https://sea2.discourse-cdn.com/flex002/user_avatar/discuss.python.org/bswck/32/34363_2.png) [@bswck](https://discuss.python.org/u/bswck)\
**Post date:** [September 6, 2026, 10:22pm UTC](https://discuss.python.org/t/support-dynamic-overload/105174/4 "2026-09-06T22:22:24Z")

</div>

> [@STofone](#):
>
> `singledispatch` fixes the first argument as the dispatch type, and dispatch by itself.
> 
> I want to dispatch by myself and the first argument of implementation is not type for dispatch.

You can dispatch by yourself using the `.dispatch()` API:

```py
from functools import singledispatch

@singledispatch
def visit(x: object) -> None:
    print("visisted object")

@visit.register
def visit_int(x: int) -> None:
    print("visisted int")

@visit.register
def visit_str(x: str) -> None:
    print("visisted str")

str_visitor = visit.dispatch(str)
assert str_visitor is visit_str
str_visitor(object())
# visited str

```
