From cb864f33b140f2ddf15727972d40ed3875e39568 Mon Sep 17 00:00:00 2001 From: Vitor Sessak Date: Tue, 28 Jan 2025 07:58:29 +0000 Subject: [PATCH] Make the comparator CmpExpIdx respect the std::strict_weak_ordering requirements. With the current code, if there are two id Expressions: `id1` and `id2` and one non-id expression `expr`, we could have `id1 < id2` and `id2 < expr < id1`. This CL makes ids to be ordered before non-ids. Also remove call to Expression::equal(), which also made a checker complain the ordering was not strict, probably because it is not transitive. --- include/minizinc/flatten_internal.hh | 17 +++++++++++------ 1 file changed, 11 insertions(+), 6 deletions(-) diff --git a/include/minizinc/flatten_internal.hh b/include/minizinc/flatten_internal.hh index 65e262c14..cbc6a9792 100644 --- a/include/minizinc/flatten_internal.hh +++ b/include/minizinc/flatten_internal.hh @@ -590,12 +590,17 @@ public: std::vector& x; CmpExpIdx(std::vector& x0) : x(x0) {} bool operator()(int i, int j) const { - if (Expression::equal(x[i](), x[j]())) { - return false; - } - if (Expression::isa(x[i]()) && Expression::isa(x[j]()) && - Expression::cast(x[i]())->idn() != -1 && Expression::cast(x[j]())->idn() != -1) { - return Expression::cast(x[i]())->idn() < Expression::cast(x[j]())->idn(); + const long long int i_idn = + Expression::isa(x[i]()) ? Expression::cast(x[i]())->idn() : -1; + const long long int j_idn = + Expression::isa(x[j]()) ? Expression::cast(x[j]())->idn() : -1; + const bool i_is_valid_id = i_idn != -1; + const bool j_is_valid_id = j_idn != -1; + if (i_is_valid_id != j_is_valid_id) { + return i_is_valid_id > j_is_valid_id; + } + if (i_is_valid_id && j_is_valid_id) { + return i_idn < j_idn; } return x[i]() < x[j](); }