Newer
Older
# imports
# standard
import random
# local, external
# local, internal
import src.topupopt.problems.esipp.signal as signal
# ******************************************************************************
# ******************************************************************************
# **************************************************************************
# **************************************************************************
# trigger errors that can only happen by messing with private/interval vars
# test amplitude constrained non-negative real signals
# **************************************************************************
# **************************************************************************
# ******************************************************************************
# ******************************************************************************
def example_amplitude_constrained_nnr_signals():
# number of time intervals
# **************************************************************************
number_samples=number_intervals,
max_pos_amp_limit=10,
min_pos_amp_limit=None,
)
assert not sig.has_max_neg_amp_limit
assert not sig.has_min_pos_amp_limit
assert sig.is_signal_bounded()
assert not sig.is_signal_fixed()
number_samples=number_intervals,
max_pos_amp_limit=None,
min_pos_amp_limit=3,
)
assert not sig.has_max_neg_amp_limit
assert sig.has_min_pos_amp_limit
assert sig.is_signal_bounded()
assert not sig.is_signal_fixed()
number_samples=number_intervals,
max_pos_amp_limit=10,
min_pos_amp_limit=3,
)
assert not sig.has_max_neg_amp_limit
assert sig.has_min_pos_amp_limit
assert sig.is_signal_bounded()
assert not sig.is_signal_fixed()
# **************************************************************************
# by providing a non-numeric nr. of samples without specific lower bounds
error_was_triggered = False
try:
sig = signal.AmplitudeConstrainedNNRSignal(
number_samples=(number_intervals,), max_pos_amp_limit=10
)
except TypeError:
error_was_triggered = True
assert error_was_triggered
error_was_triggered = False
try:
sig = signal.AmplitudeConstrainedNNRSignal(
number_samples=number_intervals,
max_pos_amp_limit=10,
lower_bounds=[-1 for i in range(number_intervals)],
)
except ValueError:
error_was_triggered = True
assert error_was_triggered
# ******************************************************************************
# ******************************************************************************
def example_amplitude_constrained_signals():
# number of time intervals
# **************************************************************************
number_samples=number_intervals,
max_pos_amp_limit=10,
min_pos_amp_limit=None,
max_neg_amp_limit=None,
min_neg_amp_limit=None,
)
assert not sig.has_max_neg_amp_limit
assert not sig.has_min_pos_amp_limit
assert not sig.is_signal_bounded()
assert not sig.is_signal_fixed()
sig.set_positive_amplitude(positive_amplitude=5)
sig.validate_positive_amplitude()
# use the tolerances and validate an otherwise invalid amplitude
sig.set_positive_amplitude(positive_amplitude=12)
sig.validate_positive_amplitude(tolerance=2)
number_samples=number_intervals,
max_pos_amp_limit=None,
min_pos_amp_limit=3,
max_neg_amp_limit=None,
min_neg_amp_limit=None,
)
assert not sig.has_max_neg_amp_limit
assert sig.has_min_pos_amp_limit
assert not sig.is_signal_bounded()
assert not sig.is_signal_fixed()
sig.set_positive_amplitude(positive_amplitude=5)
sig.validate_positive_amplitude()
# use the tolerances and validate an otherwise invalid amplitude
sig.set_positive_amplitude(positive_amplitude=1)
sig.validate_positive_amplitude(tolerance=2)
number_samples=number_intervals,
max_pos_amp_limit=None,
min_pos_amp_limit=None,
max_neg_amp_limit=10,
min_neg_amp_limit=None,
)
assert sig.has_max_neg_amp_limit
assert not sig.has_min_pos_amp_limit
assert not sig.is_signal_bounded()
assert not sig.is_signal_fixed()
sig.set_negative_amplitude(negative_amplitude=5)
sig.validate_negative_amplitude()
# use the tolerances and validate an otherwise invalid amplitude
sig.set_negative_amplitude(negative_amplitude=12)
sig.validate_negative_amplitude(tolerance=2)
number_samples=number_intervals,
max_pos_amp_limit=None,
min_pos_amp_limit=None,
max_neg_amp_limit=None,
min_neg_amp_limit=3,
)
assert not sig.has_max_neg_amp_limit
assert not sig.has_min_pos_amp_limit
assert not sig.is_signal_bounded()
assert not sig.is_signal_fixed()
sig.set_negative_amplitude(negative_amplitude=5)
sig.validate_negative_amplitude()
# use the tolerances and validate an otherwise invalid amplitude
sig.set_negative_amplitude(negative_amplitude=1)
sig.validate_negative_amplitude(tolerance=2)
number_samples=number_intervals,
max_pos_amp_limit=10,
min_pos_amp_limit=3,
max_neg_amp_limit=None,
min_neg_amp_limit=None,
)
assert not sig.has_max_neg_amp_limit
assert sig.has_min_pos_amp_limit
assert not sig.is_signal_bounded()
assert not sig.is_signal_fixed()
number_samples=number_intervals,
max_pos_amp_limit=None,
min_pos_amp_limit=None,
max_neg_amp_limit=10,
min_neg_amp_limit=3,
)
assert sig.has_max_neg_amp_limit
assert not sig.has_min_pos_amp_limit
assert not sig.is_signal_bounded()
assert not sig.is_signal_fixed()
# create amplitude constrained signal with all limits but without bounds
number_samples=number_intervals,
max_pos_amp_limit=10,
min_pos_amp_limit=3,
max_neg_amp_limit=11,
min_neg_amp_limit=4,
)
assert sig.has_max_neg_amp_limit
assert sig.has_min_pos_amp_limit
assert not sig.is_signal_bounded()
assert not sig.is_signal_fixed()
# create amplitude constrained signal with all limits and with bounds
number_samples=number_intervals,
max_pos_amp_limit=10,
min_pos_amp_limit=3,
max_neg_amp_limit=11,
min_neg_amp_limit=4,
lower_bounds=[-7 for i in range(number_intervals)],
upper_bounds=[15 for i in range(number_intervals)],
)
assert sig.has_max_neg_amp_limit
assert sig.has_min_pos_amp_limit
assert sig.is_signal_bounded()
assert not sig.is_signal_fixed()
# set the signal using samples that do not violate the limits nor the bounds
# set the signal using samples that violate the positive limits and bounds
sig.set_signal([25 for i in range(number_intervals)])
# set the signal using samples that violate the positive limits and bounds
sig.set_signal([-25 for i in range(number_intervals)])
# test external samples that do not violate the limits
assert not sig.violates_amplitude_limits(
samples=[0 for i in range(number_intervals)]
# test external samples that violate the positive limits
assert sig.violates_amplitude_limits(samples=[15 for i in range(number_intervals)])
# test external samples that violate the negative limits
assert sig.violates_amplitude_limits(samples=[-15 for i in range(number_intervals)])
# create amplitude constrained signal without limits or bounds
number_samples=number_intervals,
max_pos_amp_limit=None,
min_pos_amp_limit=None,
max_neg_amp_limit=None,
min_neg_amp_limit=None,
)
assert not sig.has_max_neg_amp_limit
assert not sig.has_min_pos_amp_limit
assert not sig.is_signal_bounded()
assert not sig.is_signal_fixed()
assert not sig.violates_amplitude_limits() # because it has none
# **************************************************************************
error_was_triggered = False
try:
sig = signal.AmplitudeConstrainedSignal(
number_samples=number_intervals,
max_pos_amp_limit=-10,
min_pos_amp_limit=3,
max_neg_amp_limit=None,
min_neg_amp_limit=None,
)
except ValueError:
error_was_triggered = True
assert error_was_triggered
error_was_triggered = False
try:
sig = signal.AmplitudeConstrainedSignal(
number_samples=number_intervals,
max_pos_amp_limit=10,
min_pos_amp_limit=-3,
max_neg_amp_limit=None,
min_neg_amp_limit=None,
)
except ValueError:
error_was_triggered = True
assert error_was_triggered
error_was_triggered = False
try:
sig = signal.AmplitudeConstrainedSignal(
number_samples=number_intervals,
max_pos_amp_limit=None,
min_pos_amp_limit=None,
max_neg_amp_limit=-11,
min_neg_amp_limit=4,
)
except ValueError:
error_was_triggered = True
assert error_was_triggered
error_was_triggered = False
try:
sig = signal.AmplitudeConstrainedSignal(
number_samples=number_intervals,
max_pos_amp_limit=None,
min_pos_amp_limit=None,
max_neg_amp_limit=11,
min_neg_amp_limit=-4,
)
except ValueError:
error_was_triggered = True
assert error_was_triggered
# by providing non-numeric or not None amplitude limits (e.g. tuple)
error_was_triggered = False
try:
sig = signal.AmplitudeConstrainedSignal(
number_samples=number_intervals,
max_pos_amp_limit=(10,),
min_pos_amp_limit=None,
max_neg_amp_limit=None,
min_neg_amp_limit=None,
)
except TypeError:
error_was_triggered = True
assert error_was_triggered
error_was_triggered = False
try:
sig = signal.AmplitudeConstrainedSignal(
number_samples=number_intervals,
max_pos_amp_limit=None,
min_pos_amp_limit=(3,),
max_neg_amp_limit=None,
min_neg_amp_limit=None,
)
except TypeError:
error_was_triggered = True
assert error_was_triggered
error_was_triggered = False
try:
sig = signal.AmplitudeConstrainedSignal(
number_samples=number_intervals,
max_pos_amp_limit=None,
min_pos_amp_limit=None,
max_neg_amp_limit=(10,),
min_neg_amp_limit=None,
)
except TypeError:
error_was_triggered = True
assert error_was_triggered
error_was_triggered = False
try:
sig = signal.AmplitudeConstrainedSignal(
number_samples=number_intervals,
max_pos_amp_limit=None,
min_pos_amp_limit=None,
max_neg_amp_limit=None,
min_neg_amp_limit=(3,),
)
except TypeError:
error_was_triggered = True
assert error_was_triggered
# by providing bounds incompatible with positive limits
error_was_triggered = False
try:
sig = signal.AmplitudeConstrainedSignal(
number_samples=number_intervals,
max_pos_amp_limit=9,
min_pos_amp_limit=None,
max_neg_amp_limit=None,
lower_bounds=[10 for i in range(number_intervals)],
)
except ValueError:
error_was_triggered = True
assert error_was_triggered
# by providing bounds incompatible with negative limits
error_was_triggered = False
try:
sig = signal.AmplitudeConstrainedSignal(
number_samples=number_intervals,
max_pos_amp_limit=None,
min_pos_amp_limit=None,
max_neg_amp_limit=6,
min_neg_amp_limit=None,
upper_bounds=[-10 for i in range(number_intervals)],
except ValueError:
error_was_triggered = True
assert error_was_triggered
# by providing incompatible maximum and minimum positive limits
error_was_triggered = False
try:
sig = signal.AmplitudeConstrainedSignal(
number_samples=number_intervals,
max_pos_amp_limit=5,
min_pos_amp_limit=10,
max_neg_amp_limit=None,
min_neg_amp_limit=None,
)
except ValueError:
error_was_triggered = True
assert error_was_triggered
# by providing incompatible maximum and minimum negative limits
error_was_triggered = False
try:
sig = signal.AmplitudeConstrainedSignal(
number_samples=number_intervals,
max_pos_amp_limit=None,
min_pos_amp_limit=None,
max_neg_amp_limit=6,
min_neg_amp_limit=11,
)
except ValueError:
error_was_triggered = True
assert error_was_triggered
# by providing non-numeric or not None amplitude limits (e.g. tuple)
error_was_triggered = False
try:
sig = signal.AmplitudeConstrainedSignal(
number_samples=number_intervals,
max_pos_amp_limit=10,
min_pos_amp_limit=3,
max_neg_amp_limit=None,
min_neg_amp_limit=None,
)
sig.set_positive_amplitude(positive_amplitude=(5,))
except TypeError:
error_was_triggered = True
assert error_was_triggered
# by providing non-numeric or not None amplitude limits (e.g. tuple)
error_was_triggered = False
try:
sig = signal.AmplitudeConstrainedSignal(
number_samples=number_intervals,
max_pos_amp_limit=None,
min_pos_amp_limit=None,
max_neg_amp_limit=10,
min_neg_amp_limit=3,
)
sig.set_negative_amplitude(negative_amplitude=(5,))
except TypeError:
error_was_triggered = True
assert error_was_triggered
# by checking if bounds have been violated without there being samples
error_was_triggered = False
try:
sig = signal.AmplitudeConstrainedSignal(
number_samples=number_intervals,
max_pos_amp_limit=10,
min_pos_amp_limit=3,
max_neg_amp_limit=None,
min_neg_amp_limit=None,
)
assert not sig.has_max_neg_amp_limit
assert sig.has_min_pos_amp_limit
assert not sig.is_signal_bounded()
assert not sig.is_signal_fixed() # signal is not set
assert not sig.violates_amplitude_limits() # since the sig is not set
except ValueError:
error_was_triggered = True
assert error_was_triggered
# by seeking to validate a positive amplitude when there are no positive
# amplitude limits
error_was_triggered = False
try:
sig = signal.AmplitudeConstrainedSignal(
number_samples=number_intervals,
max_pos_amp_limit=10,
min_pos_amp_limit=3,
max_neg_amp_limit=None,
min_neg_amp_limit=None,
)
sig.validate_negative_amplitude()
except ValueError:
error_was_triggered = True
assert error_was_triggered
# by seeking to validate a negative amplitude when there are no negative
# amplitude limits
error_was_triggered = False
try:
sig = signal.AmplitudeConstrainedSignal(
number_samples=number_intervals,
max_pos_amp_limit=None,
min_pos_amp_limit=None,
max_neg_amp_limit=10,
min_neg_amp_limit=3,
)
sig.validate_positive_amplitude()
except ValueError:
error_was_triggered = True
assert error_was_triggered
# by seeking to validate a positive amplitude that exceeds its tolerated
# maximum, using the internal positive amplitude
error_was_triggered = False
try:
sig = signal.AmplitudeConstrainedSignal(
number_samples=number_intervals,
max_pos_amp_limit=10,
min_pos_amp_limit=3,
max_neg_amp_limit=None,
min_neg_amp_limit=None,
)
sig.set_positive_amplitude(12)
sig.validate_positive_amplitude()
except ValueError:
error_was_triggered = True
assert error_was_triggered
# by seeking to validate a positive amplitude that exceeds its tolerated
# maximum, using an externally supplied amplitude
error_was_triggered = False
try:
sig = signal.AmplitudeConstrainedSignal(
number_samples=number_intervals,
max_pos_amp_limit=10,
min_pos_amp_limit=3,
max_neg_amp_limit=None,
min_neg_amp_limit=None,
)
sig.validate_positive_amplitude(12)
except ValueError:
error_was_triggered = True
assert error_was_triggered
# by seeking to validate a positive amplitude that is below its tolerated
# minimum, using the internal positive amplitude
error_was_triggered = False
try:
sig = signal.AmplitudeConstrainedSignal(
number_samples=number_intervals,
max_pos_amp_limit=10,
min_pos_amp_limit=3,
max_neg_amp_limit=None,
min_neg_amp_limit=None,
)
sig.set_positive_amplitude(2)
sig.validate_positive_amplitude()
except ValueError:
error_was_triggered = True
assert error_was_triggered
# by seeking to validate a positive amplitude that is below its tolerated
# minimum, using an externally supplied amplitude
error_was_triggered = False
try:
sig = signal.AmplitudeConstrainedSignal(
number_samples=number_intervals,
max_pos_amp_limit=10,
min_pos_amp_limit=3,
max_neg_amp_limit=None,
min_neg_amp_limit=None,
)
sig.validate_positive_amplitude(2)
except ValueError:
error_was_triggered = True
assert error_was_triggered
# by seeking to validate a negative amplitude that exceeds its tolerated
# maximum, using the internal negative amplitude
error_was_triggered = False
try:
sig = signal.AmplitudeConstrainedSignal(
number_samples=number_intervals,
max_pos_amp_limit=None,
min_pos_amp_limit=None,
max_neg_amp_limit=10,
min_neg_amp_limit=3,
)
sig.set_negative_amplitude(12)
sig.validate_negative_amplitude()
except ValueError:
error_was_triggered = True
assert error_was_triggered
# by seeking to validate a negative amplitude that exceeds its tolerated
# maximum, using an externally supplied amplitude
error_was_triggered = False
try:
sig = signal.AmplitudeConstrainedSignal(
number_samples=number_intervals,
max_pos_amp_limit=None,
min_pos_amp_limit=None,
max_neg_amp_limit=10,
min_neg_amp_limit=3,
)
sig.validate_negative_amplitude(12)
except ValueError:
error_was_triggered = True
assert error_was_triggered
# by seeking to validate a negative amplitude that is below its tolerated
# minimum, using the internal negative amplitude
error_was_triggered = False
try:
sig = signal.AmplitudeConstrainedSignal(
number_samples=number_intervals,
max_pos_amp_limit=None,
min_pos_amp_limit=None,
max_neg_amp_limit=10,
min_neg_amp_limit=3,
)
sig.set_negative_amplitude(2)
sig.validate_negative_amplitude()
except ValueError:
error_was_triggered = True
assert error_was_triggered
# by seeking to validate a negative amplitude that is below its tolerated
# minimum, using an externally supplied amplitude
error_was_triggered = False
try:
sig = signal.AmplitudeConstrainedSignal(
number_samples=number_intervals,
max_pos_amp_limit=None,
min_pos_amp_limit=None,
max_neg_amp_limit=10,
min_neg_amp_limit=3,
)
sig.validate_negative_amplitude(2)
except ValueError:
error_was_triggered = True
assert error_was_triggered
# ******************************************************************************
# ******************************************************************************
def example_peculiar_errors():
# number of time intervals
# **************************************************************************
# by providing samples as something other than a list, e.g. tuples
error_was_triggered = False
try:
_ = signal.Signal(
number_samples=number_intervals,
samples=(random.random() for i in range(number_intervals)),
lower_bounds=None,
upper_bounds=None,
except TypeError:
error_was_triggered = True
assert error_was_triggered
error_was_triggered = False
try:
_ = signal.Signal(
number_samples=number_intervals,
samples=[random.random() for i in range(number_intervals + 1)],
except ValueError:
error_was_triggered = True
assert error_was_triggered
# **************************************************************************
# **************************************************************************
# the tests below require messing with the internals
lower_bounds = [5 for i in range(number_intervals)]
upper_bounds = [7 for i in range(number_intervals)]
error_was_triggered = False
try:
sig = signal.Signal(
number_samples=number_intervals,
samples=None,
lower_bounds=lower_bounds,
upper_bounds=upper_bounds,
)
sig.lower_bounds = [random.random() for i in range(number_intervals + 1)]
sig.has_lower_bounds()
except ValueError:
error_was_triggered = True
assert error_was_triggered
error_was_triggered = False
try:
sig = signal.Signal(
number_samples=number_intervals,
samples=None,
lower_bounds=lower_bounds,
upper_bounds=upper_bounds,
)
sig.upper_bounds = [random.random() for i in range(number_intervals - 1)]
sig.has_upper_bounds()
except ValueError:
error_was_triggered = True
assert error_was_triggered
error_was_triggered = False
try:
sig = signal.Signal(
number_samples=number_intervals,
samples=[random.random() for i in range(number_intervals)],
lower_bounds=None,
upper_bounds=None,
)
sig.samples = [random.random() for i in range(number_intervals - 1)]
sig.is_signal_fixed()
except ValueError:
error_was_triggered = True
assert error_was_triggered
# by deleting the lower bounds after creating the object
sig = signal.NonNegativeRealSignal(number_samples=number_intervals)
sig.lower_bounds = None
sig.is_lower_bounded = False
if not sig.are_bounds_nnr():
raise ValueError()
except ValueError:
error_was_triggered = True
# by providing negative upper bounds (requires even lower lower bounds)
sig = signal.NonNegativeRealSignal(number_samples=number_intervals)
sig.is_upper_bounded = True
sig.upper_bounds = [-1 for i in range(number_intervals)]
if not sig.are_bounds_nnr():
raise ValueError()
except ValueError:
error_was_triggered = True
assert error_was_triggered
# ******************************************************************************
# ******************************************************************************
def example_binary_signals():
# number of time intervals
# **************************************************************************
# create a binary signal and insert non-binary integer numbers in it
sig = signal.BinarySignal(number_samples=number_intervals)
assert sig.is_signal_bounded() == True # it has upper and lower bounds
assert sig.violates_bounds() == False # because it is not fixed
assert sig.is_nnr() == False # because it is not fixed
assert sig.are_bounds_nnr() == True # because it is within the range [0,1]
sig.set_signal(samples=[3 for _ in range(number_intervals)])
assert sig.is_signal_binary_only(integrality_tolerance=0.0) == False
assert sig.is_signal_integer_only(integrality_tolerance=0.0) == True
assert sig.is_signal_binary_only(integrality_tolerance=None) == False
# create a binary signal and insert a noisy binary numbers in it
sig = signal.BinarySignal(number_samples=number_intervals)
deviation = [amplitude * (random.random() - 0.5) for _ in range(number_intervals)]
samples = [random.randint(0, 1) + deviation[i] for i in range(number_intervals)]
955
956
957
958
959
960
961
962
963
964
965
966
967
968
969
970
971
972
973
974
975
976
977
978
979
980
981
982
983
984
985
986
assert sig.is_signal_bounded() == True # it has upper and lower bounds
assert sig.violates_bounds(tolerance=amplitude) == False # it should not
assert sig.is_nnr(tolerance=amplitude) == True # it should be
assert sig.are_bounds_nnr() == True # because it is within the range [0,1]
assert (
sig.is_signal_binary_only(integrality_tolerance=amplitude) == True
) # since the tol. is the ampli.
assert (
sig.is_signal_integer_only(integrality_tolerance=amplitude) == True
) # since the tol. is the ampli.
assert (
sig.is_signal_binary_only(
integrality_tolerance=max([abs(max(deviation)), abs(min(deviation))])
* (1 - 0.1)
)
== False
) # because the tolerance was set below the maximum deviation
assert (
sig.is_signal_integer_only(
integrality_tolerance=max([abs(max(deviation)), abs(min(deviation))])
* (1 - 0.1)
)
== False
) # because the tolerance was set below the maximum deviation
assert sig.is_signal_binary_only(integrality_tolerance=None) == True
sig = signal.BinarySignal(number_samples=number_intervals)
assert sig.is_signal_binary_only() == False # because it is not fixed yet
assert sig.is_signal_integer_only() == False # because it is not fixed yet
assert sig.is_signal_bounded() == True # it has upper and lower bounds