import zfit
import zfit.z.numpy as znp
from ..util import ztyping as ztyping
from ..util.cache import GraphCachable as GraphCachable
from ..util.container import convert_to_container as convert_to_container
from ..util.deprecation import deprecated as deprecated, deprecated_norm_range as deprecated_norm_range
from ..util.exception import AlreadyExtendedPDFError as AlreadyExtendedPDFError, BasePDFSubclassingError as BasePDFSubclassingError, BreakingAPIChangeError as BreakingAPIChangeError, MultipleLimitsNotImplemented as MultipleLimitsNotImplemented, NormNotImplemented as NormNotImplemented, NotExtendedPDFError as NotExtendedPDFError, SpaceIncompatibleError as SpaceIncompatibleError, SpecificFunctionNotImplemented as SpecificFunctionNotImplemented, WorkInProgressError as WorkInProgressError
from ..util.plotter import PDFPlotter as PDFPlotter
from .baseobject import BaseNumeric as BaseNumeric, extract_filter_params as extract_filter_params
from .binning import unbinned_to_binindex as unbinned_to_binindex
from .data import Data as Data
from .dimension import BaseDimensional as BaseDimensional
from .parameter import convert_to_parameter as convert_to_parameter
from .space import convert_to_space as convert_to_space, supports as supports
from .tensorlike import OverloadableMixinValues as OverloadableMixinValues
from collections.abc import Callable as Callable, Iterable
from zfit import z as z
from zfit._data.binneddatav1 import BinnedData as BinnedData, BinnedSamplerData as BinnedSamplerData, move_axis_obs as move_axis_obs
from zfit._interfaces import ZfitBinnedData as ZfitBinnedData, ZfitBinnedPDF as ZfitBinnedPDF, ZfitBinning as ZfitBinning, ZfitPDF as ZfitPDF, ZfitParameter as ZfitParameter, ZfitSpace as ZfitSpace, ZfitUnbinnedData as ZfitUnbinnedData

class BaseBinnedPDF(BaseNumeric, GraphCachable, BaseDimensional, OverloadableMixinValues, ZfitBinnedPDF):
    def __init__(self, obs: ztyping.ObsTypeInput, extended: ztyping.ExtendedInputType = None, norm: ztyping.NormInputType = None, name: str | None = None, label: str | None = None, **kwargs) -> None: ...
    @property
    def label(self): ...
    @property
    def axes(self): ...
    def to_binneddata(self, **kwargs) -> zfit.data.BinnedData: ...
    def to_hist(self, **kwargs): ...
    @property
    def space(self): ...
    @deprecated_norm_range
    def pdf(self, x: ztyping.XType, norm: ztyping.LimitsType = None, *, params: ztyping.ParamTypeInput = None) -> ztyping.XType: ...
    @deprecated_norm_range
    def ext_pdf(self, x: ztyping.XType, norm: ztyping.LimitsType = None, *, params: ztyping.ParamTypeInput = None) -> ztyping.XType: ...
    def log_pdf(self, x: ztyping.XType, norm: ztyping.LimitsType = None, *, params: ztyping.ParamTypeInput = None) -> ztyping.XType: ...
    def ext_log_pdf(self, x: ztyping.XType, norm: ztyping.LimitsType = None, *, params: ztyping.ParamTypeInput = None) -> ztyping.XType: ...
    def log_normalization(self, norm, *, params=None, options=None, limits=None) -> ztyping.NumericalTypeReturn: ...
    def normalization(self, norm=None, *, params=None, options=None, limits=None) -> ztyping.NumericalTypeReturn: ...
    def integrate(self, limits: ztyping.LimitsType, norm: ztyping.LimitsType = None, *, options=None, params: ztyping.ParamTypeInput = None) -> ztyping.XType: ...
    @deprecated_norm_range
    def ext_integrate(self, limits: ztyping.LimitsType, norm: ztyping.LimitsType = None, *, options=None, params: ztyping.ParamTypeInput = None) -> ztyping.XType: ...
    def create_sampler(self, n: ztyping.nSamplingTypeIn = None, limits: ztyping.LimitsType = None, *, params: ztyping.ParamTypeInput = None, fixed_params: bool | list[ZfitParameter] | tuple[ZfitParameter] = True) -> BinnedSamplerData: ...
    def sample(self, n: int | None = None, limits: ztyping.LimitsType = None, *, params: ztyping.ParamTypeInput = None) -> ZfitBinnedData: ...
    def values(self, *, var=None, params=None): ...
    def update_integration_options(self, *_, **__) -> None: ...
    def as_func(self, norm: ztyping.LimitsType = False): ...
    @property
    def is_extended(self) -> bool: ...
    def set_norm(self, norm) -> None: ...
    def create_extended(self, yield_: ztyping.ParamTypeInput) -> ZfitPDF: ...
    def get_yield(self) -> ZfitParameter | None: ...
    @classmethod
    def register_analytic_integral(cls, func: Callable, limits: ztyping.LimitsType = None, priority: int = 50, *, supports_norm: bool = False, supports_multiple_limits: bool = False): ...
    @deprecated_norm_range
    def partial_integrate(self, x: ztyping.XType, limits: ztyping.LimitsType, *, norm=None, options=None) -> ztyping.XType: ...
    @classmethod
    def register_inverse_analytic_integral(cls, func: Callable): ...
    @property
    def norm(self): ...
    @property
    def norm_range(self): ...
    def counts(self, x: ztyping.BinnedDataInputType = None, norm: ztyping.NormInputType = None, *, params: ztyping.ParamTypeInput = None) -> ZfitBinnedData: ...
    def ext_normalization(self, norm: ztyping.NormInputType, *, options=None, params: ztyping.ParamTypeInput = None) -> ztyping.NumericalTypeReturn: ...
    def rel_counts(self, x: ztyping.BinnedDataInputType = None, *, norm: ztyping.NormInputType = None, params: ztyping.ParamTypeInput = None) -> ZfitBinnedData: ...
    def set_norm_range(self) -> None: ...
    def to_binned(self, space, *, extended=None, norm=None): ...
    def to_unbinned(self): ...
BaseBinnedPDFV1 = BaseBinnedPDF

def binned_rect_integration(*, limits: ZfitSpace, edges: Iterable[znp.array] | znp.array, counts: znp.array | None = None, density: znp.array | None = None, axis: Iterable[int] | int | None = None) -> znp.array: ...
def cut_edges_and_bins(edges: Iterable[znp.array], limits: ZfitSpace, axis=None, unscaled=None) -> tuple[list[znp.array], tuple[znp.array, znp.array], list | None]: ...
