Skip to content

Commit 8be5126

Browse files
committed
Assed applied to HighsUserScaleData
1 parent 64a4243 commit 8be5126

File tree

8 files changed

+60
-25
lines changed

8 files changed

+60
-25
lines changed

check/TestUserScale.cpp

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -79,7 +79,15 @@ TEST_CASE("user-small-cost-scale", "[highs_user_scale]") {
7979
lp.a_matrix_.start_ = {0, 2, 4};
8080
lp.a_matrix_.index_ = {0, 1, 0, 1};
8181
lp.a_matrix_.value_ = {1, 1, 2, 4};
82+
83+
HighsInt suggested_cost_scale;
84+
HighsInt suggested_bound_scale;
85+
highs.getCostBoundScaling(suggested_cost_scale, suggested_bound_scale);
86+
8287
highs.passModel(lp);
88+
89+
highs.getCostBoundScaling(suggested_cost_scale, suggested_bound_scale);
90+
8391
highs.run();
8492
REQUIRE(solution.col_value[0] == 40);
8593
REQUIRE(solution.col_value[1] == 20);

highs/Highs.h

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -575,6 +575,12 @@ class Highs {
575575
const HighsInt method = 0,
576576
const double ill_conditioning_bound = 1e-4);
577577

578+
/**
579+
* @brief Get the suggested cost and bound scaling for the incumbent model
580+
*/
581+
HighsStatus getCostBoundScaling(HighsInt& suggested_cost_scale,
582+
HighsInt& suggested_bound_scale);
583+
578584
/**
579585
* @brief Get (any) irreducible infeasible subsystem (IIS)
580586
* information for the incumbent model

highs/lp_data/HConst.h

Lines changed: 9 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -34,10 +34,16 @@ const std::string kHighsOnString = "on";
3434
const HighsInt kHighsMaxStringLength = 512;
3535
const HighsInt kSimplexConcurrencyLimit = 8;
3636
const double kRunningAverageMultiplier = 0.05;
37-
const double kExcessivelyLargeBoundValue = 1e10;
38-
const double kExcessivelyLargeCostValue = 1e10;
39-
const double kExcessivelySmallBoundValue = 1e-4;
37+
4038
const double kExcessivelySmallCostValue = 1e-4;
39+
const double kExcessivelySmallBoundValue = 1e-4;
40+
const double kExcessivelyLargeCostValue = 1e10;
41+
const double kExcessivelyLargeBoundValue = 1e10;
42+
43+
const double kOkSmallCostValue = 0.5;
44+
const double kOkSmallBoundValue = 0.5;
45+
const double kOkLargeCostValue = 2.0;
46+
const double kOkLargeBoundValue = 2.0;
4147

4248
const HighsInt kNoThreadInstance = -1;
4349
const bool kAllowDeveloperAssert = false;

highs/lp_data/HStruct.h

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -198,6 +198,7 @@ struct HighsUserScaleData {
198198
HighsInt num_large_matrix_values;
199199
HighsInt suggested_user_cost_scale;
200200
HighsInt suggested_user_bound_scale;
201+
bool applied;
201202
void initialise(const HighsInt& user_cost_scale_,
202203
const HighsInt& user_bound_scale_,
203204
const double& infinite_cost_, const double& infinite_bound_,

highs/lp_data/Highs.cpp

Lines changed: 20 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -951,17 +951,16 @@ HighsStatus Highs::run() {
951951
if (this->userScaleModel(user_scale_data) == HighsStatus::kError)
952952
return HighsStatus::kError;
953953
this->userScaleSolution(user_scale_data);
954+
// Indicate that the scaling has been applied
955+
user_scale_data.applied = true;
954956
// Zero the user scale values to prevent further scaling
955957
this->options_.user_cost_scale = 0;
956958
this->options_.user_bound_scale = 0;
957959
}
958960

959961
// Assess whether to warn the user about excessive bounds and costs
960-
assessCostBoundScaling(this->options_.log_options, this->model_,
961-
kExcessivelySmallCostValue,
962-
kExcessivelyLargeCostValue,
963-
kExcessivelySmallBoundValue,
964-
kExcessivelyLargeBoundValue,
962+
assessCostBoundScaling(this->options_.log_options,
963+
this->model_,
965964
user_scale_data);
966965

967966
HighsStatus status;
@@ -1002,6 +1001,8 @@ HighsStatus Highs::run() {
10021001
// negated to undo user scaling
10031002
this->options_.user_cost_scale = -user_scale_data.user_cost_scale;
10041003
this->options_.user_bound_scale = -user_scale_data.user_bound_scale;
1004+
// Indicate that the scaling has not been applied
1005+
user_scale_data.applied = false;
10051006
highsLogUser(this->options_.log_options, HighsLogType::kInfo,
10061007
"After solving the user-scaled model, the unscaled solution "
10071008
"has objective value %.12g\n",
@@ -2009,6 +2010,20 @@ HighsStatus Highs::getIllConditioning(HighsIllConditioning& ill_conditioning,
20092010
ill_conditioning_bound);
20102011
}
20112012

2013+
HighsStatus Highs::getCostBoundScaling(HighsInt& suggested_cost_scale,
2014+
HighsInt& suggested_bound_scale) {
2015+
this->logHeader();
2016+
HighsUserScaleData data;
2017+
initialiseUserScaleData(this->options_, data);
2018+
assessCostBoundScaling(this->options_.log_options, this->model_,
2019+
data, false);
2020+
suggested_cost_scale = data.suggested_user_cost_scale;
2021+
suggested_bound_scale = data.suggested_user_bound_scale;
2022+
printf("Highs::getCostBoundScaling suggested cost / bound scale values of %d / %d\n",
2023+
int(suggested_cost_scale), int(suggested_bound_scale));
2024+
return HighsStatus::kOk;
2025+
}
2026+
20122027
HighsStatus Highs::getIis(HighsIis& iis) {
20132028
HighsStatus return_status = this->getIisInterface();
20142029
if (return_status != HighsStatus::kError) iis = this->iis_;

highs/lp_data/HighsLpUtils.cpp

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -3686,6 +3686,7 @@ void HighsUserScaleData::initialise(const HighsInt& user_cost_scale_,
36863686
this->num_large_matrix_values = 0;
36873687
this->suggested_user_cost_scale = 0;
36883688
this->suggested_user_bound_scale = 0;
3689+
this->applied = false;
36893690
}
36903691

36913692
bool HighsUserScaleData::scaleError(std::string& message) const {

highs/lp_data/HighsSolve.cpp

Lines changed: 13 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -349,12 +349,13 @@ HighsStatus solveUnconstrainedLp(const HighsOptions& options, const HighsLp& lp,
349349
// recommendations
350350
void assessCostBoundScaling(const HighsLogOptions log_options,
351351
const HighsModel& model,
352-
const double small_cost,
353-
const double large_cost,
354-
const double small_bound,
355-
const double large_bound,
356-
HighsUserScaleData& user_scale_data) {
352+
HighsUserScaleData& user_scale_data,
353+
const bool excessive) {
357354
const bool user_cost_or_bound_scale = user_scale_data.user_cost_scale || user_scale_data.user_bound_scale;
355+
const double small_cost = excessive ? kExcessivelySmallCostValue : kOkSmallCostValue;
356+
const double large_cost = excessive ? kExcessivelyLargeCostValue : kOkLargeCostValue;
357+
const double small_bound = excessive ? kExcessivelySmallBoundValue : kOkSmallBoundValue;
358+
const double large_bound = excessive ? kExcessivelyLargeBoundValue : kOkLargeBoundValue;
358359
std::stringstream message;
359360
if (user_cost_or_bound_scale) {
360361
if (user_scale_data.user_cost_scale)
@@ -502,7 +503,7 @@ void assessCostBoundScaling(const HighsLogOptions log_options,
502503
// All scalable values are excessively large, so obviously suggest
503504
// scaling them down
504505
ratio = 1.0 / min_value;
505-
assert(0 == 11);
506+
//assert(0 == 11);
506507
} else if (0 < max_value && max_value < small_value) {
507508
// All scalable values are excessively small, so obviously suggest
508509
// scaling them up
@@ -516,12 +517,12 @@ void assessCostBoundScaling(const HighsLogOptions log_options,
516517
ratio = 1.0 / max_value;
517518
if (ratio * min_value < small_value) {
518519
ratio = std::sqrt(1.0 / (max_value * min_value));
519-
assert(0 == 325);
520+
//assert(0 == 325);
520521
}
521-
assert(0 == 33);
522+
//assert(0 == 33);
522523
} else {
523524
ratio = 1.0 / max_value;
524-
assert(0 == 44);
525+
//assert(0 == 44);
525526
}
526527
} else if (0 < min_value && min_value < small_value) {
527528
// Min value is excessively small, so look to scale it up,
@@ -531,12 +532,12 @@ void assessCostBoundScaling(const HighsLogOptions log_options,
531532
ratio = 1.0 / min_value;
532533
if (ratio * max_value > large_value) {
533534
ratio = std::sqrt(1.0 / (max_value * min_value));
534-
assert(0 == 545);
535+
//assert(0 == 545);
535536
}
536-
assert(0 == 55);
537+
//assert(0 == 55);
537538
} else {
538539
ratio = 1.0 / min_value;
539-
assert(0 == 66);
540+
//assert(0 == 66);
540541
}
541542
}
542543
}

highs/lp_data/HighsSolve.h

Lines changed: 2 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -20,9 +20,6 @@ HighsStatus solveUnconstrainedLp(const HighsOptions& options, const HighsLp& lp,
2020
HighsBasis& basis);
2121
void assessCostBoundScaling(const HighsLogOptions log_options,
2222
const HighsModel& model,
23-
const double small_cost,
24-
const double large_cost,
25-
const double small_bound,
26-
const double large_bound,
27-
HighsUserScaleData& user_scale_data);
23+
HighsUserScaleData& user_scale_data,
24+
const bool excesive = true);
2825
#endif // LP_DATA_HIGHSSOLVE_H_

0 commit comments

Comments
 (0)