Google OR-Tools v9.15
a fast and portable software suite for combinatorial optimization
Loading...
Searching...
No Matches
2d_mandatory_overlap_propagator.cc
Go to the documentation of this file.
1// Copyright 2010-2025 Google LLC
2// Licensed under the Apache License, Version 2.0 (the "License");
3// you may not use this file except in compliance with the License.
4// You may obtain a copy of the License at
5//
6// http://www.apache.org/licenses/LICENSE-2.0
7//
8// Unless required by applicable law or agreed to in writing, software
9// distributed under the License is distributed on an "AS IS" BASIS,
10// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
11// See the License for the specific language governing permissions and
12// limitations under the License.
13
15
16#include <cstdint>
17#include <optional>
18#include <string>
19#include <utility>
20#include <vector>
21
22#include "absl/log/log.h"
23#include "absl/log/vlog_is_on.h"
24#include "absl/types/span.h"
26#include "ortools/sat/integer.h"
28#include "ortools/sat/model.h"
31
32namespace operations_research {
33namespace sat {
34
36 const int id = watcher->Register(this);
37 helper_.WatchAllBoxes(id);
38 return id;
39}
40
42 if (!VLOG_IS_ON(1)) return;
43 std::vector<std::pair<std::string, int64_t>> stats;
44 stats.push_back({"MandatoryOverlapPropagator/called_with_zero_area",
45 num_calls_zero_area_});
46 stats.push_back({"MandatoryOverlapPropagator/called_without_zero_area",
47 num_calls_nonzero_area_});
48 stats.push_back({"MandatoryOverlapPropagator/conflicts", num_conflicts_});
49
50 shared_stats_->AddStats(stats);
51}
52
54 if (!helper_.IsEnforced()) return true;
55 if (!helper_.SynchronizeAndSetDirection()) return false;
56
57 mandatory_regions_.clear();
58 mandatory_regions_index_.clear();
59 bool has_zero_area_boxes = false;
60 absl::Span<const TaskTime> tasks =
61 helper_.x_helper().TaskByIncreasingNegatedStartMax();
62 for (int i = tasks.size(); --i >= 0;) {
63 const int b = tasks[i].task_index;
64 if (!helper_.IsPresent(b)) continue;
65
66 const IntegerValue x_start_max = helper_.x_helper().StartMax(b);
67 const IntegerValue x_end_min = helper_.x_helper().EndMin(b);
68 if (x_start_max > x_end_min) continue;
69
70 const IntegerValue y_start_max = helper_.y_helper().StartMax(b);
71 const IntegerValue y_end_min = helper_.y_helper().EndMin(b);
72 if (y_start_max > y_end_min) continue;
73
74 mandatory_regions_.push_back({.x_min = x_start_max,
75 .x_max = x_end_min,
76 .y_min = y_start_max,
77 .y_max = y_end_min});
78 mandatory_regions_index_.push_back(b);
79
80 if (mandatory_regions_.back().SizeX() == 0 ||
81 mandatory_regions_.back().SizeY() == 0) {
82 has_zero_area_boxes = true;
83 }
84 }
85 std::optional<std::pair<int, int>> conflict;
86 if (has_zero_area_boxes) {
87 num_calls_zero_area_++;
88 conflict = FindOneIntersectionIfPresentWithZeroArea(mandatory_regions_);
89 } else {
90 num_calls_nonzero_area_++;
91 conflict = FindOneIntersectionIfPresent(mandatory_regions_);
92 }
93
94 if (conflict.has_value()) {
95 num_conflicts_++;
96 return helper_.ReportConflictFromTwoBoxes(
97 mandatory_regions_index_[conflict->first],
98 mandatory_regions_index_[conflict->second]);
99 }
100 return true;
101}
102
104 NoOverlap2DConstraintHelper* helper, Model* model,
105 GenericLiteralWatcher* watcher, int priority) {
106 MandatoryOverlapPropagator* propagator =
107 new MandatoryOverlapPropagator(helper, model);
108 watcher->SetPropagatorPriority(propagator->RegisterWith(watcher), priority);
109 model->TakeOwnership(propagator);
110}
111
112} // namespace sat
113} // namespace operations_research
void SetPropagatorPriority(int id, int priority)
Definition integer.cc:2700
int Register(PropagatorInterface *propagator)
Definition integer.cc:2674
std::optional< std::pair< int, int > > FindOneIntersectionIfPresent(absl::Span< const Rectangle > rectangles)
void CreateAndRegisterMandatoryOverlapPropagator(NoOverlap2DConstraintHelper *helper, Model *model, GenericLiteralWatcher *watcher, int priority)
std::optional< std::pair< int, int > > FindOneIntersectionIfPresentWithZeroArea(absl::Span< const Rectangle > rectangles)
OR-Tools root namespace.