Packages
fixpoint
0.9.3
0.22.1
0.21.5
0.21.4
0.21.3
0.21.2
0.21.1
0.21.0
0.20.6
0.20.5
0.20.4
0.20.3
0.20.2
0.20.1
0.19.5
0.19.4
0.19.3
0.19.2
0.19.1
0.18.2
0.18.1
0.17.6
0.17.5
0.17.4
0.17.3
0.17.2
0.17.1
0.16.5
0.16.4
0.16.3
0.16.2
0.16.1
0.16.0
0.15.6
0.15.5
0.15.4
0.15.3
0.15.2
0.15.1
0.15.0
0.14.9
0.14.8
0.14.7
0.14.6
0.14.5
0.14.4
0.14.3
0.14.2
0.14.1
0.13.5
0.13.4
0.13.2
0.13.1
0.12.9
0.12.8
0.12.7
0.12.6
0.12.5
0.12.4
0.12.2
0.12.1
0.11.8
0.11.7
0.11.6
0.11.5
0.11.4
0.11.3
0.11.2
0.11.1
0.10.7
0.10.6
0.10.5
0.10.4
0.10.3
0.10.2
0.10.1
0.9.12
0.9.11
0.9.10
0.9.9
0.9.8
0.9.7
0.9.6
0.9.5
0.9.4
0.9.3
0.9.2
0.9.1
0.9.0
0.8.52
0.8.51
0.8.50
0.8.49
0.8.48
0.8.46
0.8.44
0.8.43
0.8.42
0.8.41
0.8.40
0.8.39
0.8.38
0.8.37
0.8.36
0.8.35
0.8.34
0.8.33
0.8.32
0.8.31
0.8.30
0.8.29
0.8.28
0.8.27
0.8.26
0.8.25
0.8.24
0.8.23
0.8.22
0.8.21
0.8.20
0.8.19
0.8.18
0.8.17
0.8.16
0.8.15
0.8.14
0.8.13
0.8.12
0.8.11
0.8.10
0.8.9
0.8.8
0.8.7
0.8.6
0.8.5
0.8.4
0.8.3
0.8.2
0.8.1
0.8.0
0.7.10
0.7.9
0.7.8
0.7.7
0.7.6
0.7.5
0.7.4
0.7.3
0.7.2
0.7.1
0.7.0
0.6.5
0.6.4
0.6.3
0.6.2
0.6.1
0.6.0
0.5.12
0.5.11
0.5.10
0.5.9
0.5.8
0.5.7
0.5.6
0.5.5
0.5.4
0.5.3
0.5.2
0.5.1
0.5.0
0.4.3
0.4.2
0.4.1
0.4.0
0.3.6
0.3.5
0.3.4
0.3.3
0.3.2
0.3.1
0.3.0
0.2.3
0.2.2
0.2.1
0.1.3
0.1.2
0.1.1
0.1.0
Constraint Programming Solver
Current section
Files
Jump to
Current section
Files
lib/solver/constraints/propagators/modulo.ex
defmodule CPSolver.Propagator.Modulo do
use CPSolver.Propagator
@x_y_fixed [false, true, true]
@m_x_fixed [true, true, false]
@m_y_fixed [true, false, true]
@all_fixed [true, true, true]
def new(m, x, y) do
new([m, x, y])
end
@impl true
def variables(args) do
args
|> Propagator.default_variables_impl()
|> Enum.map(fn var -> set_propagate_on(var, :bound_change) end)
end
@impl true
def filter(args, nil, changes) do
filter(args, initial_state(args), changes)
end
def filter(args, %{fixed_flags: fixed_flags}, changes) do
updated_fixed = update_fixed(args, fixed_flags, changes)
if filter_impl(args, updated_fixed) do
:passive
else
{:state, %{fixed_flags: updated_fixed}}
end
end
## This (no changes) will happen when the propagator doesn't receive changes
## (either because it was first to run or there were no changes)
# when map_size(changes) == 0
defp update_fixed(args, fixed_flags, _changes) do
for idx <- 0..2 do
Enum.at(fixed_flags, idx) || fixed?(Enum.at(args, idx))
end
end
# defp update_fixed(_args, fixed_flags, changes) do
# Enum.reduce(changes, fixed_flags, fn
# {idx, :fixed}, flags_acc ->
# List.replace_at(flags_acc, idx, true)
# {_idx, _bound_change}, flags_acc ->
# flags_acc
# end)
# end
def filter_impl([m, x, y] = _args, @x_y_fixed) do
fix(m, rem(min(x), min(y)))
end
def filter_impl([m, x, y], @m_x_fixed) do
m_value = min(m)
x_value = min(x)
domain(y)
|> Domain.to_list()
|> Enum.each(fn y_value ->
rem(x_value, y_value) != m_value &&
remove(y, y_value)
end)
fixed?(y)
end
def filter_impl([m, x, y], @m_y_fixed) do
m_value = min(m)
y_value = min(y)
domain(x)
|> Domain.to_list()
|> Enum.each(fn x_value ->
rem(x_value, y_value) != m_value &&
remove(x, x_value)
end)
fixed?(x)
end
def filter_impl(_args, @all_fixed) do
true
end
def filter_impl(_args, [true | _x_y_flags]) do
false
end
def filter_impl([m, _x, _y] = args, [false | x_y_flags]) do
update_bounds(args)
fixed?(m) && filter_impl(args, [true | x_y_flags])
end
defp update_bounds([m, x, y] = _args) do
max_x = max(x)
min_x = min(x)
max_y = max(y)
min_y = min(y)
{m_lower_bound, m_upper_bound} =
mod_bounds(min_x, max_x, min_y, max_y)
removeAbove(m, m_upper_bound)
removeBelow(m, m_lower_bound)
end
defp initial_state([_m, _x, y] = args) do
remove(y, 0)
%{fixed_flags: Enum.map(args, fn arg -> fixed?(arg) end)}
end
defp mod_bounds(min_x, max_x, min_y, max_y) do
cond do
min_x >= 0 ->
{0, (max(abs(min_y), abs(max_y)) - 1) |> min(max_x)}
max_x < 0 ->
{(-max(abs(min_y), abs(max_y)) + 1) |> max(min_x), 0}
true ->
{
(min(min(min_y, -min_y), min(max_y, -max_y)) + 1) |> max(min_x),
(max(max(min_y, -min_y), max(max_y, -max_y)) - 1) |> min(max_x)
}
end
end
def mod_bounds(x, y) do
mod_bounds(min(x), max(x), min(y), max(y))
end
end