Returns whether the value has a channel representation.

    Returns:
        If `val` has a `_has_channel_` method and its result is not
        NotImplemented, that result is returned. Otherwise, if `val` has a
        `_has_mixture_` method and its result is not NotImplemented, that
        result is returned. Otherwise if `val` has a `_has_unitary_` method
        and its results is not NotImplemented, that result is returned.
        Otherwise, if the value has a _channel_ method return if that
        has a non-default value. Returns False if none of these functions
        exists.

def has_channel(val: Any) -> bool:
    """Returns whether the value has a channel representation.

    Returns:
        If `val` has a `_has_channel_` method and its result is not
        NotImplemented, that result is returned. Otherwise, if `val` has a
        `_has_mixture_` method and its result is not NotImplemented, that
        result is returned. Otherwise if `val` has a `_has_unitary_` method
        and its results is not NotImplemented, that result is returned.
        Otherwise, if the value has a _channel_ method return if that
        has a non-default value. Returns False if none of these functions
        exists.
    """
    channel_getter = getattr(val, '_has_channel_', None)
    result = NotImplemented if channel_getter is None else channel_getter()

    if result is not NotImplemented:
        return result

    result = has_mixture_channel(val)
    if result is not NotImplemented and result:
        return result

    # No has methods, use `_channel_` or delegates instead.
    return channel(val, None) is not None