# Path: qkeras/qtools/quantized_operators/adder_impl.py
# def po2_qbits_converter(po2_quantizer: quantizer_impl.IQuantizer):
#   def implemented_as():
#   def __init__(self, quantizer_1, quantizer_2):
#   def implemented_as():
#   def __init__(self, quantizer_1, quantizer_2):
#   def implemented_as():
#   def __init__(self, quantizer_1, quantizer_2):
#   def implemented_as():
#   def __init__(self, quantizer_1, quantizer_2):
#   def implemented_as():
# class IAdderImpl(abc.ABC):
# class FixedPointAdder(IAdderImpl):
# class FloatingPointAdder(IAdderImpl):
# class Po2FixedPointAdder(IAdderImpl):
# class Po2Adder(IAdderImpl):
# 
# Path: qkeras/qtools/quantized_operators/quantizer_impl.py
# FLOATINGPOINT_BITS = 32
# def get_np_value(val):
# def get_exp(quantizer):
#   def __init__(self):
#   def __init__(self):
#   def convert_qkeras_quantizer(
#       self, quantizer: quantizers.quantized_bits):
#   def convert_to_qkeras_quantizer(
#       self, symmetric=1, alpha=None, use_stochastic_rounding=False,
#       scale_axis=None, qnoise_factor=1.0):
#   def __init__(self):
#   def convert_qkeras_quantizer(
#       self, quantizer: quantizers.quantized_tanh):
#   def convert_to_qkeras_quantizer(
#       self, symmetric=False, use_stochastic_rounding=False):
#   def __init__(self):
#   def convert_qkeras_quantizer(
#       self, quantizer: quantizers.quantized_ulaw):
#   def convert_to_qkeras_quantizer(self, symmetric=0, u=255.0):
#   def __init__(self, use_01=False):
#   def convert_qkeras_quantizer(self, quantizer: quantizers.binary):
#   def convert_to_qkeras_quantizer(self, alpha=None,
#                                   use_stochastic_rounding=False):
#   def __init__(self):
#   def convert_qkeras_quantizer(
#       self, quantizer: quantizers.stochastic_binary):
#   def convert_to_qkeras_quantizer(self, alpha=None, temperature=6.0,
#                                   use_real_sigmoid=True):
#   def __init__(self):
#   def convert_qkeras_quantizer(self, quantizer: quantizers.bernoulli):
#   def convert_to_qkeras_quantizer(self, alpha=None, temperature=6.0,
#                                   use_real_sigmoid=True):
#   def __init__(self):
#   def convert_qkeras_quantizer(
#       self, quantizer: quantizers.quantized_relu):
#   def convert_to_qkeras_quantizer(
#       self, use_sigmoid=0, negative_slope=0.0, use_stochastic_rounding=False,
#       relu_upper_bound=None, is_quantized_clip=True, qnoise_factor=1.0):
#   def __init__(self):
#   def convert_qkeras_quantizer(
#       self, quantizer: quantizers.ternary):
#   def convert_to_qkeras_quantizer(
#       self, alpha=None, threshold=None, use_stochastic_rounding=False,
#       number_of_unrolls=5):
#   def __init__(self):
#   def convert_qkeras_quantizer(
#       self, quantizer: quantizers.stochastic_ternary):
#   def convert_to_qkeras_quantizer(
#       self, alpha=None, threshold=None, temperature=8.0,
#       use_real_sigmoid=True, number_of_unrolls=5):
#   def __init__(self, bits):
#   def convert_qkeras_quantizer(self, bits):
#   def convert_to_qkeras_quantizer(self, bits):
#   def __init__(self, is_signed=True):
#   def convert_qkeras_quantizer(self, quantizer):
#   def convert_to_qkeras_quantizer(
#       self, negative_slope=0, use_stochastic_rounding=False,
#       quadratic_approximation=False):
#   def get_min_max_exp(self):
#   def quantizer_bits_calculator(self, val):
#   def update_quantizer(self, val, reset=False):
#   def update_inference_values(self, weights):
#   def __init__(self):
#   def convert_qkeras_quantizer(
#       self, quantizer: quantizers.quantized_relu_po2):
#   def convert_to_qkeras_quantizer(
#       self, negative_slope=0, use_stochastic_rounding=False,
#       quadratic_approximation=False):
# class IQuantizer(abc.ABC):
# class QuantizedBits(IQuantizer):
# class QuantizedTanh(QuantizedBits):
# class QuantizedUlaw(QuantizedBits):
# class Binary(IQuantizer):
# class StochasticBinary(Binary):
# class Bernoulli(Binary):
# class QuantizedRelu(IQuantizer):
# class Ternary(IQuantizer):
# class StochasticTernary(Ternary):
# class FloatingPoint(IQuantizer):
# class PowerOfTwo(IQuantizer):
# class ReluPowerOfTwo(PowerOfTwo):


import abc
import copy
from absl import logging
from qkeras.qtools.quantized_operators import adder_impl
from qkeras.qtools.quantized_operators import quantizer_impl
# you may not use this file except in compliance with the License.
# You may obtain a copy of the License at
#
#     http://www.apache.org/licenses/LICENSE-2.0
#
# Unless required by applicable law or agreed to in writing, software
# distributed under the License is distributed on an "AS IS" BASIS,
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
# See the License for the specific language governing permissions and
# limitations under the License.
# ==============================================================================
"""implement adder quantizer."""

from __future__ import absolute_import
from __future__ import division
from __future__ import print_function




class IAdder(abc.ABC):
  """abstract class for adder."""

  def __init__(self):
    self.adder_impl_table = [
        [
            adder_impl.FixedPointAdder,
            adder_impl.Po2FixedPointAdder,
            adder_impl.FixedPointAdder,
            adder_impl.FixedPointAdder,

# Path: qkeras/qtools/quantized_operators/adder_impl.py
# def po2_qbits_converter(po2_quantizer: quantizer_impl.IQuantizer):
#   def implemented_as():
#   def __init__(self, quantizer_1, quantizer_2):
#   def implemented_as():
#   def __init__(self, quantizer_1, quantizer_2):
#   def implemented_as():
#   def __init__(self, quantizer_1, quantizer_2):
#   def implemented_as():
#   def __init__(self, quantizer_1, quantizer_2):
#   def implemented_as():
# class IAdderImpl(abc.ABC):
# class FixedPointAdder(IAdderImpl):
# class FloatingPointAdder(IAdderImpl):
# class Po2FixedPointAdder(IAdderImpl):
# class Po2Adder(IAdderImpl):
# 
# Path: qkeras/qtools/quantized_operators/quantizer_impl.py
# FLOATINGPOINT_BITS = 32
# def get_np_value(val):
# def get_exp(quantizer):
#   def __init__(self):
#   def __init__(self):
#   def convert_qkeras_quantizer(
#       self, quantizer: quantizers.quantized_bits):
#   def convert_to_qkeras_quantizer(
#       self, symmetric=1, alpha=None, use_stochastic_rounding=False,
#       scale_axis=None, qnoise_factor=1.0):
#   def __init__(self):
#   def convert_qkeras_quantizer(
#       self, quantizer: quantizers.quantized_tanh):
#   def convert_to_qkeras_quantizer(
#       self, symmetric=False, use_stochastic_rounding=False):
#   def __init__(self):
#   def convert_qkeras_quantizer(
#       self, quantizer: quantizers.quantized_ulaw):
#   def convert_to_qkeras_quantizer(self, symmetric=0, u=255.0):
#   def __init__(self, use_01=False):
#   def convert_qkeras_quantizer(self, quantizer: quantizers.binary):
#   def convert_to_qkeras_quantizer(self, alpha=None,
#                                   use_stochastic_rounding=False):
#   def __init__(self):
#   def convert_qkeras_quantizer(
#       self, quantizer: quantizers.stochastic_binary):
#   def convert_to_qkeras_quantizer(self, alpha=None, temperature=6.0,
#                                   use_real_sigmoid=True):
#   def __init__(self):
#   def convert_qkeras_quantizer(self, quantizer: quantizers.bernoulli):
#   def convert_to_qkeras_quantizer(self, alpha=None, temperature=6.0,
#                                   use_real_sigmoid=True):
#   def __init__(self):
#   def convert_qkeras_quantizer(
#       self, quantizer: quantizers.quantized_relu):
#   def convert_to_qkeras_quantizer(
#       self, use_sigmoid=0, negative_slope=0.0, use_stochastic_rounding=False,
#       relu_upper_bound=None, is_quantized_clip=True, qnoise_factor=1.0):
#   def __init__(self):
#   def convert_qkeras_quantizer(
#       self, quantizer: quantizers.ternary):
#   def convert_to_qkeras_quantizer(
#       self, alpha=None, threshold=None, use_stochastic_rounding=False,
#       number_of_unrolls=5):
#   def __init__(self):
#   def convert_qkeras_quantizer(
#       self, quantizer: quantizers.stochastic_ternary):
#   def convert_to_qkeras_quantizer(
#       self, alpha=None, threshold=None, temperature=8.0,
#       use_real_sigmoid=True, number_of_unrolls=5):
#   def __init__(self, bits):
#   def convert_qkeras_quantizer(self, bits):
#   def convert_to_qkeras_quantizer(self, bits):
#   def __init__(self, is_signed=True):
#   def convert_qkeras_quantizer(self, quantizer):
#   def convert_to_qkeras_quantizer(
#       self, negative_slope=0, use_stochastic_rounding=False,
#       quadratic_approximation=False):
#   def get_min_max_exp(self):
#   def quantizer_bits_calculator(self, val):
#   def update_quantizer(self, val, reset=False):
#   def update_inference_values(self, weights):
#   def __init__(self):
#   def convert_qkeras_quantizer(
#       self, quantizer: quantizers.quantized_relu_po2):
#   def convert_to_qkeras_quantizer(
#       self, negative_slope=0, use_stochastic_rounding=False,
#       quadratic_approximation=False):
# class IQuantizer(abc.ABC):
# class QuantizedBits(IQuantizer):
# class QuantizedTanh(QuantizedBits):
# class QuantizedUlaw(QuantizedBits):
# class Binary(IQuantizer):
# class StochasticBinary(Binary):
# class Bernoulli(Binary):
# class QuantizedRelu(IQuantizer):
# class Ternary(IQuantizer):
# class StochasticTernary(Ternary):
# class FloatingPoint(IQuantizer):
# class PowerOfTwo(IQuantizer):
# class ReluPowerOfTwo(PowerOfTwo):


# Path: qkeras/qtools/quantized_operators/adder_factory.py
import abc
import copy
from absl import logging
from qkeras.qtools.quantized_operators import adder_impl
from qkeras.qtools.quantized_operators import quantizer_impl

# you may not use this file except in compliance with the License.
# You may obtain a copy of the License at
#
#     http://www.apache.org/licenses/LICENSE-2.0
#
# Unless required by applicable law or agreed to in writing, software
# distributed under the License is distributed on an "AS IS" BASIS,
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
# See the License for the specific language governing permissions and
# limitations under the License.
# ==============================================================================
"""implement adder quantizer."""

from __future__ import absolute_import
from __future__ import division
from __future__ import print_function




class IAdder(abc.ABC):
  """abstract class for adder."""

  def __init__(self):
    self.adder_impl_table = [
        [
            adder_impl.FixedPointAdder,
            adder_impl.Po2FixedPointAdder,
            adder_impl.FixedPointAdder,
            adder_impl.FixedPointAdder,

            adder_impl.FixedPointAdder,