OR-Tools  8.0
lp_data_utils.cc
Go to the documentation of this file.
1 // Copyright 2010-2018 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 namespace operations_research {
17 namespace glop {
18 
19 void ComputeSlackVariablesValues(const LinearProgram& linear_program,
20  DenseRow* values) {
21  DCHECK(values);
22  DCHECK_EQ(linear_program.num_variables(), values->size());
23 
24  // If there are no slack variable, we can give up.
25  if (linear_program.GetFirstSlackVariable() == kInvalidCol) return;
26 
27  const auto& transposed_matrix = linear_program.GetTransposeSparseMatrix();
28  for (RowIndex row(0); row < linear_program.num_constraints(); row++) {
29  const ColIndex slack_variable = linear_program.GetSlackVariable(row);
30 
31  if (slack_variable == kInvalidCol) continue;
32 
33  DCHECK_EQ(0.0, linear_program.constraint_lower_bounds()[row]);
34  DCHECK_EQ(0.0, linear_program.constraint_upper_bounds()[row]);
35 
36  const RowIndex transposed_slack = ColToRowIndex(slack_variable);
37  Fractional activation = 0.0;
38  // Row in the initial matrix (column in the transposed).
39  const SparseColumn& sparse_row =
40  transposed_matrix.column(RowToColIndex(row));
41  for (const auto& entry : sparse_row) {
42  if (transposed_slack == entry.index()) continue;
43  activation +=
44  (*values)[RowToColIndex(entry.index())] * entry.coefficient();
45  }
46  (*values)[slack_variable] = -activation;
47  }
48 }
49 
50 // This is separated from the LinearProgram class because of a cyclic dependency
51 // when scaling as an LP.
53  // Create GlopParameters proto to get default scaling algorithm.
54  GlopParameters params;
55  Scale(lp, scaler, params.scaling_method());
56 }
57 
58 // This is separated from LinearProgram class because of a cyclic dependency
59 // when scaling as an LP.
61  GlopParameters::ScalingAlgorithm scaling_method) {
62  scaler->Init(&lp->matrix_);
63  scaler->Scale(
64  scaling_method); // Compute R and C, and replace the matrix A by R.A.C
65  scaler->ScaleRowVector(false,
66  &lp->objective_coefficients_); // oc = oc.C
67  scaler->ScaleRowVector(true,
68  &lp->variable_upper_bounds_); // cl = cl.C^-1
69  scaler->ScaleRowVector(true,
70  &lp->variable_lower_bounds_); // cu = cu.C^-1
71  scaler->ScaleColumnVector(false, &lp->constraint_upper_bounds_); // rl = R.rl
72  scaler->ScaleColumnVector(false, &lp->constraint_lower_bounds_); // ru = R.ru
73  lp->transpose_matrix_is_consistent_ = false;
74 }
75 
77  scaler_.Clear();
79  lp, &scaler_, operations_research::glop::GlopParameters::DEFAULT);
80  bound_scaling_factor_ = 1.0 / lp->ScaleBounds();
81  objective_scaling_factor_ = 1.0 / lp->ScaleObjective();
82 }
83 
85  scaler_.Clear();
86  bound_scaling_factor_ = 1.0;
87  objective_scaling_factor_ = 1.0;
88 }
89 
91  // During scaling a col was multiplied by ColScalingFactor() and the variable
92  // bounds divided by it.
93  return scaler_.ColUnscalingFactor(col) * bound_scaling_factor_;
94 }
95 
97  Fractional value) const {
98  // Just the opposite of ScaleVariableValue().
99  return value / (scaler_.ColUnscalingFactor(col) * bound_scaling_factor_);
100 }
101 
103  Fractional value) const {
104  // The reduced cost move like the objective and the col scale.
105  return value * scaler_.ColUnscalingFactor(col) / objective_scaling_factor_;
106 }
107 
109  Fractional value) const {
110  // The dual value move like the objective and the inverse of the row scale.
111  return value / (scaler_.RowUnscalingFactor(row) * objective_scaling_factor_);
112 }
113 
115  Fractional value) const {
116  // The activity move with the row_scale and the bound_scaling_factor.
117  return value * scaler_.RowUnscalingFactor(row) / bound_scaling_factor_;
118 }
119 
121  ColIndex basis_col, ScatteredRow* left_inverse) const {
122  const Fractional global_factor = scaler_.ColUnscalingFactor(basis_col);
123 
124  // We have left_inverse * [RowScale * B * ColScale] = unit_row.
125  if (left_inverse->non_zeros.empty()) {
126  const ColIndex num_rows = left_inverse->values.size();
127  for (ColIndex col(0); col < num_rows; ++col) {
128  left_inverse->values[col] /=
129  scaler_.RowUnscalingFactor(ColToRowIndex(col)) * global_factor;
130  }
131  } else {
132  for (const ColIndex col : left_inverse->non_zeros) {
133  left_inverse->values[col] /=
134  scaler_.RowUnscalingFactor(ColToRowIndex(col)) * global_factor;
135  }
136  }
137 }
138 
140  const RowToColMapping& basis, ColIndex col,
141  ScatteredColumn* right_inverse) const {
142  const Fractional global_factor = scaler_.ColScalingFactor(col);
143 
144  // [RowScale * B * BColScale] * inverse = RowScale * column * ColScale.
145  // That is B * (BColScale * inverse) = columm * ColScale[col].
146  if (right_inverse->non_zeros.empty()) {
147  const RowIndex num_rows = right_inverse->values.size();
148  for (RowIndex row(0); row < num_rows; ++row) {
149  right_inverse->values[row] /=
150  scaler_.ColUnscalingFactor(basis[row]) * global_factor;
151  }
152  } else {
153  for (const RowIndex row : right_inverse->non_zeros) {
154  right_inverse->values[row] /=
155  scaler_.ColUnscalingFactor(basis[row]) * global_factor;
156  }
157  }
158 }
159 
160 } // namespace glop
161 } // namespace operations_research
operations_research::glop::LinearProgram::ScaleObjective
Fractional ScaleObjective()
Definition: lp_data.cc:1134
operations_research::glop::LinearProgram::num_constraints
RowIndex num_constraints() const
Definition: lp_data.h:208
operations_research::glop::Scale
void Scale(LinearProgram *lp, SparseMatrixScaler *scaler)
Definition: lp_data_utils.cc:52
operations_research::glop::LpScalingHelper::UnscaleUnitRowLeftSolve
void UnscaleUnitRowLeftSolve(ColIndex basis_col, ScatteredRow *left_inverse) const
Definition: lp_data_utils.cc:120
operations_research::glop::kInvalidCol
const ColIndex kInvalidCol(-1)
operations_research::glop::LpScalingHelper::Scale
void Scale(LinearProgram *lp)
Definition: lp_data_utils.cc:76
operations_research::glop::LpScalingHelper::UnscaleConstraintActivity
Fractional UnscaleConstraintActivity(RowIndex row, Fractional value) const
Definition: lp_data_utils.cc:114
operations_research::glop::Scale
void Scale(LinearProgram *lp, SparseMatrixScaler *scaler, GlopParameters::ScalingAlgorithm scaling_method)
Definition: lp_data_utils.cc:60
operations_research::glop::SparseMatrixScaler::ColUnscalingFactor
Fractional ColUnscalingFactor(ColIndex col) const
Definition: matrix_scaler.cc:51
operations_research::glop::SparseMatrixScaler::ScaleColumnVector
void ScaleColumnVector(bool up, DenseColumn *column_vector) const
Definition: matrix_scaler.cc:175
operations_research::glop::LinearProgram::GetFirstSlackVariable
ColIndex GetFirstSlackVariable() const
Definition: lp_data.cc:720
operations_research::glop::SparseMatrixScaler::ScaleRowVector
void ScaleRowVector(bool up, DenseRow *row_vector) const
Definition: matrix_scaler.cc:170
operations_research::glop::ScatteredVector::non_zeros
std::vector< Index > non_zeros
Definition: scattered_vector.h:63
value
int64 value
Definition: demon_profiler.cc:43
operations_research::glop::StrictITIVector::size
IntType size() const
Definition: lp_types.h:276
operations_research
The vehicle routing library lets one model and solve generic vehicle routing problems ranging from th...
Definition: dense_doubly_linked_list.h:21
operations_research::glop::LinearProgram::GetTransposeSparseMatrix
const SparseMatrix & GetTransposeSparseMatrix() const
Definition: lp_data.cc:374
operations_research::glop::SparseColumn
Definition: sparse_column.h:44
operations_research::glop::LpScalingHelper::Clear
void Clear()
Definition: lp_data_utils.cc:84
operations_research::glop::LpScalingHelper::UnscaleDualValue
Fractional UnscaleDualValue(RowIndex row, Fractional value) const
Definition: lp_data_utils.cc:108
operations_research::glop::Fractional
double Fractional
Definition: lp_types.h:77
operations_research::glop::ComputeSlackVariablesValues
void ComputeSlackVariablesValues(const LinearProgram &linear_program, DenseRow *values)
Definition: lp_data_utils.cc:19
operations_research::glop::LinearProgram::constraint_lower_bounds
const DenseColumn & constraint_lower_bounds() const
Definition: lp_data.h:215
operations_research::glop::RowToColIndex
ColIndex RowToColIndex(RowIndex row)
Definition: lp_types.h:48
operations_research::glop::LpScalingHelper::UnscaleColumnRightSolve
void UnscaleColumnRightSolve(const RowToColMapping &basis, ColIndex col, ScatteredColumn *right_inverse) const
Definition: lp_data_utils.cc:139
lp_data_utils.h
operations_research::glop::SparseMatrixScaler::RowUnscalingFactor
Fractional RowUnscalingFactor(RowIndex row) const
Definition: matrix_scaler.cc:46
operations_research::glop::SparseMatrixScaler::Scale
void Scale(GlopParameters::ScalingAlgorithm method)
Definition: matrix_scaler.cc:89
operations_research::glop::StrictITIVector< ColIndex, Fractional >
operations_research::glop::LpScalingHelper::UnscaleReducedCost
Fractional UnscaleReducedCost(ColIndex col, Fractional value) const
Definition: lp_data_utils.cc:102
operations_research::glop::ScatteredRow
Definition: scattered_vector.h:193
operations_research::glop::SparseMatrixScaler
Definition: matrix_scaler.h:79
operations_research::glop::LinearProgram::ScaleBounds
Fractional ScaleBounds()
Definition: lp_data.cc:1155
operations_research::glop::SparseMatrixScaler::Init
void Init(SparseMatrix *matrix)
Definition: matrix_scaler.cc:33
operations_research::glop::SparseMatrixScaler::ColScalingFactor
Fractional ColScalingFactor(ColIndex col) const
Definition: matrix_scaler.cc:60
operations_research::glop::LpScalingHelper::UnscaleVariableValue
Fractional UnscaleVariableValue(ColIndex col, Fractional value) const
Definition: lp_data_utils.cc:96
operations_research::glop::LpScalingHelper::VariableScalingFactor
Fractional VariableScalingFactor(ColIndex col) const
Definition: lp_data_utils.cc:90
operations_research::glop::SparseMatrixScaler::Clear
void Clear()
Definition: matrix_scaler.cc:40
col
ColIndex col
Definition: markowitz.cc:176
row
RowIndex row
Definition: markowitz.cc:175
operations_research::glop::LinearProgram
Definition: lp_data.h:55
operations_research::glop::ScatteredColumn
Definition: scattered_vector.h:192
operations_research::glop::LinearProgram::num_variables
ColIndex num_variables() const
Definition: lp_data.h:205
operations_research::glop::LinearProgram::GetSlackVariable
ColIndex GetSlackVariable(RowIndex row) const
Definition: lp_data.cc:724
operations_research::glop::ColToRowIndex
RowIndex ColToRowIndex(ColIndex col)
Definition: lp_types.h:51
operations_research::glop::ScatteredVector::values
StrictITIVector< Index, Fractional > values
Definition: scattered_vector.h:58
operations_research::glop::LinearProgram::constraint_upper_bounds
const DenseColumn & constraint_upper_bounds() const
Definition: lp_data.h:218