1 /* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */ 2 /* */ 3 /* This file is part of the program and library */ 4 /* SCIP --- Solving Constraint Integer Programs */ 5 /* */ 6 /* Copyright (c) 2002-2023 Zuse Institute Berlin (ZIB) */ 7 /* */ 8 /* Licensed under the Apache License, Version 2.0 (the "License"); */ 9 /* you may not use this file except in compliance with the License. */ 10 /* You may obtain a copy of the License at */ 11 /* */ 12 /* http://www.apache.org/licenses/LICENSE-2.0 */ 13 /* */ 14 /* Unless required by applicable law or agreed to in writing, software */ 15 /* distributed under the License is distributed on an "AS IS" BASIS, */ 16 /* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. */ 17 /* See the License for the specific language governing permissions and */ 18 /* limitations under the License. */ 19 /* */ 20 /* You should have received a copy of the Apache-2.0 license */ 21 /* along with SCIP; see the file LICENSE. If not visit scipopt.org. */ 22 /* */ 23 /* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */ 24 25 /**@file objpresol.cpp 26 * @brief C++ wrapper for presolvers 27 * @author Tobias Achterberg 28 */ 29 30 /*---+----1----+----2----+----3----+----4----+----5----+----6----+----7----+----8----+----9----+----0----+----1----+----2*/ 31 32 #include <cassert> 33 34 #include "objpresol.h" 35 36 37 38 39 /* 40 * Data structures 41 */ 42 43 /** presolver data */ 44 struct SCIP_PresolData 45 { 46 scip::ObjPresol* objpresol; /**< presolver object */ 47 SCIP_Bool deleteobject; /**< should the presolver object be deleted when presolver is freed? */ 48 }; 49 50 51 52 53 /* 54 * Callback methods of presolver 55 */ 56 57 extern "C" 58 { 59 60 /** copy method for presolver plugins (called when SCIP copies plugins) */ 61 static 62 SCIP_DECL_PRESOLCOPY(presolCopyObj) 63 { /*lint --e{715}*/ 64 SCIP_PRESOLDATA* presoldata; 65 66 assert(scip != NULL); 67 68 presoldata = SCIPpresolGetData(presol); 69 assert(presoldata != NULL); 70 assert(presoldata->objpresol != NULL); 71 assert(presoldata->objpresol->scip_ != scip); 72 73 if( presoldata->objpresol->iscloneable() ) 74 { 75 scip::ObjPresol* newobjpresol; 76 newobjpresol = dynamic_cast<scip::ObjPresol*> (presoldata->objpresol->clone(scip)); 77 78 /* call include method of presolver object */ 79 SCIP_CALL( SCIPincludeObjPresol(scip, newobjpresol, TRUE) ); 80 } 81 82 return SCIP_OKAY; 83 } 84 85 /** destructor of presolver to free user data (called when SCIP is exiting) */ 86 static 87 SCIP_DECL_PRESOLFREE(presolFreeObj) 88 { /*lint --e{715}*/ 89 SCIP_PRESOLDATA* presoldata; 90 91 presoldata = SCIPpresolGetData(presol); 92 assert(presoldata != NULL); 93 assert(presoldata->objpresol != NULL); 94 assert(presoldata->objpresol->scip_ == scip); 95 96 /* call virtual method of presol object */ 97 SCIP_CALL( presoldata->objpresol->scip_free(scip, presol) ); 98 99 /* free presol object */ 100 if( presoldata->deleteobject ) 101 delete presoldata->objpresol; 102 103 /* free presol data */ 104 delete presoldata; 105 SCIPpresolSetData(presol, NULL); /*lint !e64*/ 106 107 return SCIP_OKAY; 108 } 109 110 111 /** initialization method of presolver (called after problem was transformed) */ 112 static 113 SCIP_DECL_PRESOLINIT(presolInitObj) 114 { /*lint --e{715}*/ 115 SCIP_PRESOLDATA* presoldata; 116 117 presoldata = SCIPpresolGetData(presol); 118 assert(presoldata != NULL); 119 assert(presoldata->objpresol != NULL); 120 assert(presoldata->objpresol->scip_ == scip); 121 122 /* call virtual method of presol object */ 123 SCIP_CALL( presoldata->objpresol->scip_init(scip, presol) ); 124 125 return SCIP_OKAY; 126 } 127 128 129 /** deinitialization method of presolver (called before transformed problem is freed) */ 130 static 131 SCIP_DECL_PRESOLEXIT(presolExitObj) 132 { /*lint --e{715}*/ 133 SCIP_PRESOLDATA* presoldata; 134 135 presoldata = SCIPpresolGetData(presol); 136 assert(presoldata != NULL); 137 assert(presoldata->objpresol != NULL); 138 139 /* call virtual method of presol object */ 140 SCIP_CALL( presoldata->objpresol->scip_exit(scip, presol) ); 141 142 return SCIP_OKAY; 143 } 144 145 146 /** presolving initialization method of presolver (called when presolving is about to begin) */ 147 static 148 SCIP_DECL_PRESOLINITPRE(presolInitpreObj) 149 { /*lint --e{715}*/ 150 SCIP_PRESOLDATA* presoldata; 151 152 presoldata = SCIPpresolGetData(presol); 153 assert(presoldata != NULL); 154 assert(presoldata->objpresol != NULL); 155 156 /* call virtual method of presol object */ 157 SCIP_CALL( presoldata->objpresol->scip_initpre(scip, presol) ); 158 159 return SCIP_OKAY; 160 } 161 162 163 /** presolving deinitialization method of presolver (called after presolving has been finished) */ 164 static 165 SCIP_DECL_PRESOLEXITPRE(presolExitpreObj) 166 { /*lint --e{715}*/ 167 SCIP_PRESOLDATA* presoldata; 168 169 presoldata = SCIPpresolGetData(presol); 170 assert(presoldata != NULL); 171 assert(presoldata->objpresol != NULL); 172 173 /* call virtual method of presol object */ 174 SCIP_CALL( presoldata->objpresol->scip_exitpre(scip, presol) ); 175 176 return SCIP_OKAY; 177 } 178 179 180 /** execution method of presolver */ 181 static 182 SCIP_DECL_PRESOLEXEC(presolExecObj) 183 { /*lint --e{715}*/ 184 SCIP_PRESOLDATA* presoldata; 185 186 presoldata = SCIPpresolGetData(presol); 187 assert(presoldata != NULL); 188 assert(presoldata->objpresol != NULL); 189 190 /* call virtual method of presol object */ 191 SCIP_CALL( presoldata->objpresol->scip_exec(scip, presol, nrounds, presoltiming, 192 nnewfixedvars, nnewaggrvars, nnewchgvartypes, nnewchgbds, nnewholes, 193 nnewdelconss, nnewaddconss, nnewupgdconss, nnewchgcoefs, nnewchgsides, 194 nfixedvars, naggrvars, nchgvartypes, nchgbds, naddholes, 195 ndelconss, naddconss, nupgdconss, nchgcoefs, nchgsides, result) ); 196 197 return SCIP_OKAY; 198 } 199 } 200 201 202 203 /* 204 * presolver specific interface methods 205 */ 206 207 /** creates the presolver for the given presolver object and includes it in SCIP */ 208 SCIP_RETCODE SCIPincludeObjPresol( 209 SCIP* scip, /**< SCIP data structure */ 210 scip::ObjPresol* objpresol, /**< presolver object */ 211 SCIP_Bool deleteobject /**< should the presolver object be deleted when presolver is freed? */ 212 ) 213 { 214 SCIP_PRESOLDATA* presoldata; 215 216 assert(scip != NULL); 217 assert(objpresol != NULL); 218 219 /* create presolver data */ 220 presoldata = new SCIP_PRESOLDATA; 221 presoldata->objpresol = objpresol; 222 presoldata->deleteobject = deleteobject; 223 224 /* include presolver */ 225 SCIP_CALL( SCIPincludePresol(scip, objpresol->scip_name_, objpresol->scip_desc_, 226 objpresol->scip_priority_, objpresol->scip_maxrounds_, objpresol->scip_timing_, 227 presolCopyObj, presolFreeObj, presolInitObj, presolExitObj, 228 presolInitpreObj, presolExitpreObj, presolExecObj, 229 presoldata) ); /*lint !e429*/ 230 231 return SCIP_OKAY; /*lint !e429*/ 232 } 233 234 /** returns the presol object of the given name, or 0 if not existing */ 235 scip::ObjPresol* SCIPfindObjPresol( 236 SCIP* scip, /**< SCIP data structure */ 237 const char* name /**< name of presolver */ 238 ) 239 { 240 SCIP_PRESOL* presol; 241 SCIP_PRESOLDATA* presoldata; 242 243 presol = SCIPfindPresol(scip, name); 244 if( presol == NULL ) 245 return 0; 246 247 presoldata = SCIPpresolGetData(presol); 248 assert(presoldata != NULL); 249 250 return presoldata->objpresol; 251 } 252 253 /** returns the presol object for the given presolver */ 254 scip::ObjPresol* SCIPgetObjPresol( 255 SCIP* scip, /**< SCIP data structure */ 256 SCIP_PRESOL* presol /**< presolver */ 257 ) 258 { 259 SCIP_PRESOLDATA* presoldata; 260 261 assert(scip != NULL); 262 presoldata = SCIPpresolGetData(presol); 263 assert(presoldata != NULL); 264 265 return presoldata->objpresol; 266 } 267