source: trunk/Cbc/src/CbcLinked.hpp @ 1899

Last change on this file since 1899 was 1899, checked in by stefan, 5 years ago

fixup svn properties

  • Property svn:eol-style set to native
  • Property svn:keywords set to Author Date Id Revision
File size: 41.0 KB
Line 
1/* $Id: CbcLinked.hpp 1899 2013-04-09 18:12:08Z stefan $ */
2// Copyright (C) 2006, International Business Machines
3// Corporation and others.  All Rights Reserved.
4// This code is licensed under the terms of the Eclipse Public License (EPL).
5
6#ifndef CglLinked_H
7#define CglLinked_H
8/* THIS CONTAINS STUFF THAT SHOULD BE IN
9   OsiSolverLink
10   OsiBranchLink
11   CglTemporary
12*/
13#include "CoinModel.hpp"
14#include "OsiClpSolverInterface.hpp"
15#include "OsiChooseVariable.hpp"
16#include "CbcFathom.hpp"
17class CbcModel;
18class CoinPackedMatrix;
19class OsiLinkedBound;
20class OsiObject;
21class CglStored;
22class CglTemporary;
23/**
24
25This is to allow the user to replace initialSolve and resolve
26This version changes coefficients
27*/
28
29class OsiSolverLink : public CbcOsiSolver {
30
31public:
32    //---------------------------------------------------------------------------
33    /**@name Solve methods */
34    //@{
35    /// Solve initial LP relaxation
36    virtual void initialSolve();
37
38    /// Resolve an LP relaxation after problem modification
39    virtual void resolve();
40
41    /**
42       Problem specific
43       Returns -1 if node fathomed and no solution
44                0 if did nothing
45            1 if node fathomed and solution
46       allFixed is true if all LinkedBound variables are fixed
47    */
48    virtual int fathom(bool allFixed) ;
49    /** Solves nonlinear problem from CoinModel using SLP - may be used as crash
50        for other algorithms when number of iterations small.
51        Also exits if all problematical variables are changing
52        less than deltaTolerance
53        Returns solution array
54    */
55    double * nonlinearSLP(int numberPasses, double deltaTolerance);
56    /** Solve linearized quadratic objective branch and bound.
57        Return cutoff and OA cut
58    */
59    double linearizedBAB(CglStored * cut) ;
60    /** Solves nonlinear problem from CoinModel using SLP - and then tries to get
61        heuristic solution
62        Returns solution array
63        mode -
64        0 just get continuous
65        1 round and try normal bab
66        2 use defaultBound_ to bound integer variables near current solution
67    */
68    double * heuristicSolution(int numberPasses, double deltaTolerance, int mode);
69
70    /// Do OA cuts
71    int doAOCuts(CglTemporary * cutGen, const double * solution, const double * solution2);
72    //@}
73
74
75    /**@name Constructors and destructors */
76    //@{
77    /// Default Constructor
78    OsiSolverLink ();
79
80    /** This creates from a coinModel object
81
82        if errors.then number of sets is -1
83
84        This creates linked ordered sets information.  It assumes -
85
86        for product terms syntax is yy*f(zz)
87        also just f(zz) is allowed
88        and even a constant
89
90        modelObject not const as may be changed as part of process.
91    */
92    OsiSolverLink(  CoinModel & modelObject);
93    // Other way with existing object
94    void load(  CoinModel & modelObject, bool tightenBounds = false, int logLevel = 1);
95    /// Clone
96    virtual OsiSolverInterface * clone(bool copyData = true) const;
97
98    /// Copy constructor
99    OsiSolverLink (const OsiSolverLink &);
100
101    /// Assignment operator
102    OsiSolverLink & operator=(const OsiSolverLink& rhs);
103
104    /// Destructor
105    virtual ~OsiSolverLink ();
106
107    //@}
108
109
110    /**@name Sets and Gets */
111    //@{
112    /// Add a bound modifier
113    void addBoundModifier(bool upperBoundAffected, bool useUpperBound, int whichVariable, int whichVariableAffected,
114                          double multiplier = 1.0);
115    /// Update coefficients - returns number updated if in updating mode
116    int updateCoefficients(ClpSimplex * solver, CoinPackedMatrix * matrix);
117    /// Analyze constraints to see which are convex (quadratic)
118    void analyzeObjects();
119    /// Add reformulated bilinear constraints
120    void addTighterConstraints();
121    /// Objective value of best solution found internally
122    inline double bestObjectiveValue() const {
123        return bestObjectiveValue_;
124    }
125    /// Set objective value of best solution found internally
126    inline void setBestObjectiveValue(double value) {
127        bestObjectiveValue_ = value;
128    }
129    /// Best solution found internally
130    inline const double * bestSolution() const {
131        return bestSolution_;
132    }
133    /// Set best solution found internally
134    void setBestSolution(const double * solution, int numberColumns);
135    /// Set special options
136    inline void setSpecialOptions2(int value) {
137        specialOptions2_ = value;
138    }
139    /// Say convex (should work it out) - if convex false then strictly concave
140    void sayConvex(bool convex);
141    /// Get special options
142    inline int specialOptions2() const {
143        return specialOptions2_;
144    }
145    /** Clean copy of matrix
146        So we can add rows
147    */
148    CoinPackedMatrix * cleanMatrix() const {
149        return matrix_;
150    }
151    /** Row copy of matrix
152        Just genuine columns and rows
153        Linear part
154    */
155    CoinPackedMatrix * originalRowCopy() const {
156        return originalRowCopy_;
157    }
158    /// Copy of quadratic model if one
159    ClpSimplex * quadraticModel() const {
160        return quadraticModel_;
161    }
162    /// Gets correct form for a quadratic row - user to delete
163    CoinPackedMatrix * quadraticRow(int rowNumber, double * linear) const;
164    /// Default meshSize
165    inline double defaultMeshSize() const {
166        return defaultMeshSize_;
167    }
168    inline void setDefaultMeshSize(double value) {
169        defaultMeshSize_ = value;
170    }
171    /// Default maximumbound
172    inline double defaultBound() const {
173        return defaultBound_;
174    }
175    inline void setDefaultBound(double value) {
176        defaultBound_ = value;
177    }
178    /// Set integer priority
179    inline void setIntegerPriority(int value) {
180        integerPriority_ = value;
181    }
182    /// Get integer priority
183    inline int integerPriority() const {
184        return integerPriority_;
185    }
186    /// Objective transfer variable if one
187    inline int objectiveVariable() const {
188        return objectiveVariable_;
189    }
190    /// Set biLinear priority
191    inline void setBiLinearPriority(int value) {
192        biLinearPriority_ = value;
193    }
194    /// Get biLinear priority
195    inline int biLinearPriority() const {
196        return biLinearPriority_;
197    }
198    /// Return CoinModel
199    inline const CoinModel * coinModel() const {
200        return &coinModel_;
201    }
202    /// Set all biLinear priorities on x-x variables
203    void setBiLinearPriorities(int value, double meshSize = 1.0);
204    /** Set options and priority on all or some biLinear variables
205        1 - on I-I
206        2 - on I-x
207        4 - on x-x
208        or combinations.
209        -1 means leave (for priority value and strategy value)
210    */
211    void setBranchingStrategyOnVariables(int strategyValue, int priorityValue = -1,
212                                         int mode = 7);
213    /// Set all mesh sizes on x-x variables
214    void setMeshSizes(double value);
215    /** Two tier integer problem where when set of variables with priority
216        less than this are fixed the problem becomes an easier integer problem
217    */
218    void setFixedPriority(int priorityValue);
219    //@}
220
221    //---------------------------------------------------------------------------
222
223protected:
224
225
226    /**@name functions */
227    //@{
228    /// Do real work of initialize
229    //void initialize(ClpSimplex * & solver, OsiObject ** & object) const;
230    /// Do real work of delete
231    void gutsOfDestructor(bool justNullify = false);
232    /// Do real work of copy
233    void gutsOfCopy(const OsiSolverLink & rhs) ;
234    //@}
235
236    /**@name Private member data */
237    //@{
238    /** Clean copy of matrix
239        Marked coefficients will be multiplied by L or U
240    */
241    CoinPackedMatrix * matrix_;
242    /** Row copy of matrix
243        Just genuine columns and rows
244    */
245    CoinPackedMatrix * originalRowCopy_;
246    /// Copy of quadratic model if one
247    ClpSimplex * quadraticModel_;
248    /// Number of rows with nonLinearities
249    int numberNonLinearRows_;
250    /// Starts of lists
251    int * startNonLinear_;
252    /// Row number for a list
253    int * rowNonLinear_;
254    /** Indicator whether is convex, concave or neither
255        -1 concave, 0 neither, +1 convex
256    */
257    int * convex_;
258    /// Indices in a list/row
259    int * whichNonLinear_;
260    /// Model in CoinModel format
261    CoinModel coinModel_;
262    /// Number of variables in tightening phase
263    int numberVariables_;
264    /// Information
265    OsiLinkedBound * info_;
266    /**
267       0 bit (1) - call fathom (may do mini B&B)
268       1 bit (2) - quadratic only in objective (add OA cuts)
269       2 bit (4) - convex
270       3 bit (8) - try adding OA cuts
271       4 bit (16) - add linearized constraints
272    */
273    int specialOptions2_;
274    /// Objective transfer row if one
275    int objectiveRow_;
276    /// Objective transfer variable if one
277    int objectiveVariable_;
278    /// Objective value of best solution found internally
279    double bestObjectiveValue_;
280    /// Default mesh
281    double defaultMeshSize_;
282    /// Default maximum bound
283    double defaultBound_;
284    /// Best solution found internally
285    double * bestSolution_;
286    /// Priority for integers
287    int integerPriority_;
288    /// Priority for bilinear
289    int biLinearPriority_;
290    /// Number of variables which when fixed help
291    int numberFix_;
292    /// list of fixed variables
293    int * fixVariables_;
294    //@}
295};
296/**
297   List of bounds which depend on other bounds
298*/
299
300class OsiLinkedBound {
301
302public:
303    //---------------------------------------------------------------------------
304    /**@name Action methods */
305    //@{
306    /// Update other bounds
307    void updateBounds(ClpSimplex * solver);
308    //@}
309
310
311    /**@name Constructors and destructors */
312    //@{
313    /// Default Constructor
314    OsiLinkedBound ();
315    /// Useful Constructor
316    OsiLinkedBound(OsiSolverInterface * model, int variable,
317                   int numberAffected, const int * positionL,
318                   const int * positionU, const double * multiplier);
319
320    /// Copy constructor
321    OsiLinkedBound (const OsiLinkedBound &);
322
323    /// Assignment operator
324    OsiLinkedBound & operator=(const OsiLinkedBound& rhs);
325
326    /// Destructor
327    ~OsiLinkedBound ();
328
329    //@}
330
331    /**@name Sets and Gets */
332    //@{
333    /// Get variable
334    inline int variable() const {
335        return variable_;
336    }
337    /// Add a bound modifier
338    void addBoundModifier(bool upperBoundAffected, bool useUpperBound, int whichVariable,
339                          double multiplier = 1.0);
340    //@}
341
342private:
343    typedef struct {
344        double multiplier; // to use in computation
345        int affected; // variable or element affected
346        /*
347          0 - LB of variable affected
348          1 - UB of variable affected
349          2 - element in position (affected) affected
350        */
351        unsigned char affect;
352        unsigned char ubUsed; // nonzero if UB of this variable is used
353        /*
354           0 - use x*multiplier
355           1 - use multiplier/x
356           2 - if UB use min of current upper and x*multiplier, if LB use max of current lower and x*multiplier
357        */
358        unsigned char type; // type of computation
359    } boundElementAction;
360
361    /**@name Private member data */
362    //@{
363    /// Pointer back to model
364    OsiSolverInterface * model_;
365    /// Variable
366    int variable_;
367    /// Number of variables/elements affected
368    int numberAffected_;
369    /// Maximum number of variables/elements affected
370    int maximumAffected_;
371    /// Actions
372    boundElementAction * affected_;
373    //@}
374};
375#include "CbcHeuristic.hpp"
376/** heuristic - just picks up any good solution
377 */
378
379class CbcHeuristicDynamic3 : public CbcHeuristic {
380public:
381
382    // Default Constructor
383    CbcHeuristicDynamic3 ();
384
385    /* Constructor with model
386     */
387    CbcHeuristicDynamic3 (CbcModel & model);
388
389    // Copy constructor
390    CbcHeuristicDynamic3 ( const CbcHeuristicDynamic3 &);
391
392    // Destructor
393    ~CbcHeuristicDynamic3 ();
394
395    /// Clone
396    virtual CbcHeuristic * clone() const;
397
398    /// update model
399    virtual void setModel(CbcModel * model);
400
401    using CbcHeuristic::solution ;
402    /** returns 0 if no solution, 1 if valid solution.
403        Sets solution values if good, sets objective value (only if good)
404        We leave all variables which are at one at this node of the
405        tree to that value and will
406        initially set all others to zero.  We then sort all variables in order of their cost
407        divided by the number of entries in rows which are not yet covered.  We randomize that
408        value a bit so that ties will be broken in different ways on different runs of the heuristic.
409        We then choose the best one and set it to one and repeat the exercise.
410
411    */
412    virtual int solution(double & objectiveValue,
413                         double * newSolution);
414    /// Resets stuff if model changes
415    virtual void resetModel(CbcModel * model);
416    /// Returns true if can deal with "odd" problems e.g. sos type 2
417    virtual bool canDealWithOdd() const {
418        return true;
419    }
420
421protected:
422private:
423    /// Illegal Assignment operator
424    CbcHeuristicDynamic3 & operator=(const CbcHeuristicDynamic3& rhs);
425};
426
427#include "OsiBranchingObject.hpp"
428
429/** Define Special Linked Ordered Sets.
430
431*/
432class CoinWarmStartBasis;
433
434class OsiOldLink : public OsiSOS {
435
436public:
437
438    // Default Constructor
439    OsiOldLink ();
440
441    /** Useful constructor - A valid solution is if all variables are zero
442        apart from k*numberLink to (k+1)*numberLink-1 where k is 0 through
443        numberInSet-1.  The length of weights array is numberInSet.
444        For this constructor the variables in matrix are the numberInSet*numberLink
445        starting at first. If weights null then 0,1,2..
446    */
447    OsiOldLink (const OsiSolverInterface * solver, int numberMembers,
448                int numberLinks, int first,
449                const double * weights, int setNumber);
450    /** Useful constructor - A valid solution is if all variables are zero
451        apart from k*numberLink to (k+1)*numberLink-1 where k is 0 through
452        numberInSet-1.  The length of weights array is numberInSet.
453        For this constructor the variables are given by list - grouped.
454        If weights null then 0,1,2..
455    */
456    OsiOldLink (const OsiSolverInterface * solver, int numberMembers,
457                int numberLinks, int typeSOS, const int * which,
458                const double * weights, int setNumber);
459
460    // Copy constructor
461    OsiOldLink ( const OsiOldLink &);
462
463    /// Clone
464    virtual OsiObject * clone() const;
465
466    // Assignment operator
467    OsiOldLink & operator=( const OsiOldLink& rhs);
468
469    // Destructor
470    virtual ~OsiOldLink ();
471
472    using OsiObject::infeasibility ;
473    /// Infeasibility - large is 0.5
474    virtual double infeasibility(const OsiBranchingInformation * info, int & whichWay) const;
475
476    using OsiObject::feasibleRegion ;
477    /** Set bounds to fix the variable at the current (integer) value.
478
479      Given an integer value, set the lower and upper bounds to fix the
480      variable. Returns amount it had to move variable.
481    */
482    virtual double feasibleRegion(OsiSolverInterface * solver, const OsiBranchingInformation * info) const;
483
484    /** Creates a branching object
485
486      The preferred direction is set by \p way, 0 for down, 1 for up.
487    */
488    virtual OsiBranchingObject * createBranch(OsiSolverInterface * solver, const OsiBranchingInformation * info, int way) const;
489
490    /// Redoes data when sequence numbers change
491    virtual void resetSequenceEtc(int numberColumns, const int * originalColumns);
492
493    /// Number of links for each member
494    inline int numberLinks() const {
495        return numberLinks_;
496    }
497
498    /** \brief Return true if object can take part in normal heuristics
499    */
500    virtual bool canDoHeuristics() const {
501        return false;
502    }
503    /** \brief Return true if branch should only bound variables
504    */
505    virtual bool boundBranch() const {
506        return false;
507    }
508
509private:
510    /// data
511
512    /// Number of links
513    int numberLinks_;
514};
515/** Branching object for Linked ordered sets
516
517 */
518class OsiOldLinkBranchingObject : public OsiSOSBranchingObject {
519
520public:
521
522    // Default Constructor
523    OsiOldLinkBranchingObject ();
524
525    // Useful constructor
526    OsiOldLinkBranchingObject (OsiSolverInterface * solver,  const OsiOldLink * originalObject,
527                               int way,
528                               double separator);
529
530    // Copy constructor
531    OsiOldLinkBranchingObject ( const OsiOldLinkBranchingObject &);
532
533    // Assignment operator
534    OsiOldLinkBranchingObject & operator=( const OsiOldLinkBranchingObject& rhs);
535
536    /// Clone
537    virtual OsiBranchingObject * clone() const;
538
539    // Destructor
540    virtual ~OsiOldLinkBranchingObject ();
541
542    using OsiBranchingObject::branch ;
543    /// Does next branch and updates state
544    virtual double branch(OsiSolverInterface * solver);
545
546    using OsiBranchingObject::print ;
547    /** \brief Print something about branch - only if log level high
548    */
549    virtual void print(const OsiSolverInterface * solver = NULL);
550private:
551    /// data
552};
553/** Define data for one link
554
555*/
556
557
558class OsiOneLink {
559
560public:
561
562    // Default Constructor
563    OsiOneLink ();
564
565    /** Useful constructor -
566
567    */
568    OsiOneLink (const OsiSolverInterface * solver, int xRow, int xColumn, int xyRow,
569                const char * functionString);
570
571    // Copy constructor
572    OsiOneLink ( const OsiOneLink &);
573
574    // Assignment operator
575    OsiOneLink & operator=( const OsiOneLink& rhs);
576
577    // Destructor
578    virtual ~OsiOneLink ();
579
580    /// data
581
582    /// Row which defines x (if -1 then no x)
583    int xRow_;
584    /// Column which defines x
585    int xColumn_;
586    /// Output row
587    int xyRow;
588    /// Function
589    std::string function_;
590};
591/** Define Special Linked Ordered Sets. New style
592
593    members and weights may be stored in SOS object
594
595    This is for y and x*f(y) and z*g(y) etc
596
597*/
598
599
600class OsiLink : public OsiSOS {
601
602public:
603
604    // Default Constructor
605    OsiLink ();
606
607    /** Useful constructor -
608
609    */
610    OsiLink (const OsiSolverInterface * solver, int yRow,
611             int yColumn, double meshSize);
612
613    // Copy constructor
614    OsiLink ( const OsiLink &);
615
616    /// Clone
617    virtual OsiObject * clone() const;
618
619    // Assignment operator
620    OsiLink & operator=( const OsiLink& rhs);
621
622    // Destructor
623    virtual ~OsiLink ();
624
625    using OsiObject::infeasibility ;
626    /// Infeasibility - large is 0.5
627    virtual double infeasibility(const OsiBranchingInformation * info, int & whichWay) const;
628
629    using OsiObject::feasibleRegion ;
630    /** Set bounds to fix the variable at the current (integer) value.
631
632      Given an integer value, set the lower and upper bounds to fix the
633      variable. Returns amount it had to move variable.
634    */
635    virtual double feasibleRegion(OsiSolverInterface * solver, const OsiBranchingInformation * info) const;
636
637    /** Creates a branching object
638
639      The preferred direction is set by \p way, 0 for down, 1 for up.
640    */
641    virtual OsiBranchingObject * createBranch(OsiSolverInterface * solver, const OsiBranchingInformation * info, int way) const;
642
643    /// Redoes data when sequence numbers change
644    virtual void resetSequenceEtc(int numberColumns, const int * originalColumns);
645
646    /// Number of links for each member
647    inline int numberLinks() const {
648        return numberLinks_;
649    }
650
651    /** \brief Return true if object can take part in normal heuristics
652    */
653    virtual bool canDoHeuristics() const {
654        return false;
655    }
656    /** \brief Return true if branch should only bound variables
657    */
658    virtual bool boundBranch() const {
659        return false;
660    }
661
662private:
663    /// data
664    /// Current increment for y points
665    double meshSize_;
666    /// Links
667    OsiOneLink * data_;
668    /// Number of links
669    int numberLinks_;
670    /// Row which defines y
671    int yRow_;
672    /// Column which defines y
673    int yColumn_;
674};
675/** Branching object for Linked ordered sets
676
677 */
678class OsiLinkBranchingObject : public OsiTwoWayBranchingObject {
679
680public:
681
682    // Default Constructor
683    OsiLinkBranchingObject ();
684
685    // Useful constructor
686    OsiLinkBranchingObject (OsiSolverInterface * solver,  const OsiLink * originalObject,
687                            int way,
688                            double separator);
689
690    // Copy constructor
691    OsiLinkBranchingObject ( const OsiLinkBranchingObject &);
692
693    // Assignment operator
694    OsiLinkBranchingObject & operator=( const OsiLinkBranchingObject& rhs);
695
696    /// Clone
697    virtual OsiBranchingObject * clone() const;
698
699    // Destructor
700    virtual ~OsiLinkBranchingObject ();
701
702    using OsiBranchingObject::branch ;
703    /// Does next branch and updates state
704    virtual double branch(OsiSolverInterface * solver);
705
706    using OsiBranchingObject::print ;
707    /** \brief Print something about branch - only if log level high
708    */
709    virtual void print(const OsiSolverInterface * solver = NULL);
710private:
711    /// data
712};
713/** Define BiLinear objects
714
715    This models x*y where one or both are integer
716
717*/
718
719
720class OsiBiLinear : public OsiObject2 {
721
722public:
723
724    // Default Constructor
725    OsiBiLinear ();
726
727    /** Useful constructor -
728        This Adds in rows and variables to construct valid Linked Ordered Set
729        Adds extra constraints to match other x/y
730        So note not const solver
731    */
732    OsiBiLinear (OsiSolverInterface * solver, int xColumn,
733                 int yColumn, int xyRow, double coefficient,
734                 double xMesh, double yMesh,
735                 int numberExistingObjects = 0, const OsiObject ** objects = NULL );
736
737    /** Useful constructor -
738        This Adds in rows and variables to construct valid Linked Ordered Set
739        Adds extra constraints to match other x/y
740        So note not const model
741    */
742    OsiBiLinear (CoinModel * coinModel, int xColumn,
743                 int yColumn, int xyRow, double coefficient,
744                 double xMesh, double yMesh,
745                 int numberExistingObjects = 0, const OsiObject ** objects = NULL );
746
747    // Copy constructor
748    OsiBiLinear ( const OsiBiLinear &);
749
750    /// Clone
751    virtual OsiObject * clone() const;
752
753    // Assignment operator
754    OsiBiLinear & operator=( const OsiBiLinear& rhs);
755
756    // Destructor
757    virtual ~OsiBiLinear ();
758
759    using OsiObject::infeasibility ;
760    /// Infeasibility - large is 0.5
761    virtual double infeasibility(const OsiBranchingInformation * info, int & whichWay) const;
762
763    using OsiObject::feasibleRegion ;
764    /** Set bounds to fix the variable at the current (integer) value.
765
766      Given an integer value, set the lower and upper bounds to fix the
767      variable. Returns amount it had to move variable.
768    */
769    virtual double feasibleRegion(OsiSolverInterface * solver, const OsiBranchingInformation * info) const;
770
771    /** Creates a branching object
772
773      The preferred direction is set by \p way, 0 for down, 1 for up.
774    */
775    virtual OsiBranchingObject * createBranch(OsiSolverInterface * solver, const OsiBranchingInformation * info, int way) const;
776
777    /// Redoes data when sequence numbers change
778    virtual void resetSequenceEtc(int numberColumns, const int * originalColumns);
779
780    // This does NOT set mutable stuff
781    virtual double checkInfeasibility(const OsiBranchingInformation * info) const;
782
783    /** \brief Return true if object can take part in normal heuristics
784    */
785    virtual bool canDoHeuristics() const {
786        return false;
787    }
788    /** \brief Return true if branch should only bound variables
789    */
790    virtual bool boundBranch() const {
791        return (branchingStrategy_&4) != 0;
792    }
793    /// X column
794    inline int xColumn() const {
795        return xColumn_;
796    }
797    /// Y column
798    inline int yColumn() const {
799        return yColumn_;
800    }
801    /// X row
802    inline int xRow() const {
803        return xRow_;
804    }
805    /// Y row
806    inline int yRow() const {
807        return yRow_;
808    }
809    /// XY row
810    inline int xyRow() const {
811        return xyRow_;
812    }
813    /// Coefficient
814    inline double coefficient() const {
815        return coefficient_;
816    }
817    /// Set coefficient
818    inline void setCoefficient(double value) {
819        coefficient_ = value;
820    }
821    /// First lambda (of 4)
822    inline int firstLambda() const {
823        return firstLambda_;
824    }
825    /// X satisfied if less than this away from mesh
826    inline double xSatisfied() const {
827        return xSatisfied_;
828    }
829    inline void setXSatisfied(double value) {
830        xSatisfied_ = value;
831    }
832    /// Y satisfied if less than this away from mesh
833    inline double ySatisfied() const {
834        return ySatisfied_;
835    }
836    inline void setYSatisfied(double value) {
837        ySatisfied_ = value;
838    }
839    /// X other satisfied if less than this away from mesh
840    inline double xOtherSatisfied() const {
841        return xOtherSatisfied_;
842    }
843    inline void setXOtherSatisfied(double value) {
844        xOtherSatisfied_ = value;
845    }
846    /// Y other satisfied if less than this away from mesh
847    inline double yOtherSatisfied() const {
848        return yOtherSatisfied_;
849    }
850    inline void setYOtherSatisfied(double value) {
851        yOtherSatisfied_ = value;
852    }
853    /// X meshSize
854    inline double xMeshSize() const {
855        return xMeshSize_;
856    }
857    inline void setXMeshSize(double value) {
858        xMeshSize_ = value;
859    }
860    /// Y meshSize
861    inline double yMeshSize() const {
862        return yMeshSize_;
863    }
864    inline void setYMeshSize(double value) {
865        yMeshSize_ = value;
866    }
867    /// XY satisfied if two version differ by less than this
868    inline double xySatisfied() const {
869        return xySatisfied_;
870    }
871    inline void setXYSatisfied(double value) {
872        xySatisfied_ = value;
873    }
874    /// Set sizes and other stuff
875    void setMeshSizes(const OsiSolverInterface * solver, double x, double y);
876    /** branching strategy etc
877        bottom 2 bits
878        0 branch on either, 1 branch on x, 2 branch on y
879        next bit
880        4 set to say don't update coefficients
881        next bit
882        8 set to say don't use in feasible region
883        next bit
884        16 set to say - Always satisfied !!
885    */
886    inline int branchingStrategy() const {
887        return branchingStrategy_;
888    }
889    inline void setBranchingStrategy(int value) {
890        branchingStrategy_ = value;
891    }
892    /** Simple quadratic bound marker.
893        0 no
894        1 L if coefficient pos, G if negative i.e. value is ub on xy
895        2 G if coefficient pos, L if negative i.e. value is lb on xy
896        3 E
897        If bound then real coefficient is 1.0 and coefficient_ is bound
898    */
899    inline int boundType() const {
900        return boundType_;
901    }
902    inline void setBoundType(int value) {
903        boundType_ = value;
904    }
905    /// Does work of branching
906    void newBounds(OsiSolverInterface * solver, int way, short xOrY, double separator) const;
907    /// Updates coefficients - returns number updated
908    int updateCoefficients(const double * lower, const double * upper, double * objective,
909                           CoinPackedMatrix * matrix, CoinWarmStartBasis * basis) const;
910    /// Returns true value of single xyRow coefficient
911    double xyCoefficient(const double * solution) const;
912    /// Get LU coefficients from matrix
913    void getCoefficients(const OsiSolverInterface * solver, double xB[2], double yB[2], double xybar[4]) const;
914    /// Compute lambdas (third entry in each .B is current value) (nonzero if bad)
915    double computeLambdas(const double xB[3], const double yB[3], const double xybar[4], double lambda[4]) const;
916    /// Adds in data for extra row with variable coefficients
917    void addExtraRow(int row, double multiplier);
918    /// Sets infeasibility and other when pseudo shadow prices
919    void getPseudoShadow(const OsiBranchingInformation * info);
920    /// Gets sum of movements to correct value
921    double getMovement(const OsiBranchingInformation * info);
922
923protected:
924    /// Compute lambdas if coefficients not changing
925    void computeLambdas(const OsiSolverInterface * solver, double lambda[4]) const;
926    /// data
927
928    /// Coefficient
929    double coefficient_;
930    /// x mesh
931    double xMeshSize_;
932    /// y mesh
933    double yMeshSize_;
934    /// x satisfied if less than this away from mesh
935    double xSatisfied_;
936    /// y satisfied if less than this away from mesh
937    double ySatisfied_;
938    /// X other satisfied if less than this away from mesh
939    double xOtherSatisfied_;
940    /// Y other satisfied if less than this away from mesh
941    double yOtherSatisfied_;
942    /// xy satisfied if less than this away from true
943    double xySatisfied_;
944    /// value of x or y to branch about
945    mutable double xyBranchValue_;
946    /// x column
947    int xColumn_;
948    /// y column
949    int yColumn_;
950    /// First lambda (of 4)
951    int firstLambda_;
952    /** branching strategy etc
953        bottom 2 bits
954        0 branch on either, 1 branch on x, 2 branch on y
955        next bit
956        4 set to say don't update coefficients
957        next bit
958        8 set to say don't use in feasible region
959        next bit
960        16 set to say - Always satisfied !!
961    */
962    int branchingStrategy_;
963    /** Simple quadratic bound marker.
964        0 no
965        1 L if coefficient pos, G if negative i.e. value is ub on xy
966        2 G if coefficient pos, L if negative i.e. value is lb on xy
967        3 E
968        If bound then real coefficient is 1.0 and coefficient_ is bound
969    */
970    int boundType_;
971    /// x row
972    int xRow_;
973    /// y row (-1 if x*x)
974    int yRow_;
975    /// Output row
976    int xyRow_;
977    /// Convexity row
978    int convexity_;
979    /// Number of extra rows (coefficients to be modified)
980    int numberExtraRows_;
981    /// Multiplier for coefficient on row
982    double * multiplier_;
983    /// Row number
984    int * extraRow_;
985    /// Which chosen -1 none, 0 x, 1 y
986    mutable short chosen_;
987};
988/** Branching object for BiLinear objects
989
990 */
991class OsiBiLinearBranchingObject : public OsiTwoWayBranchingObject {
992
993public:
994
995    // Default Constructor
996    OsiBiLinearBranchingObject ();
997
998    // Useful constructor
999    OsiBiLinearBranchingObject (OsiSolverInterface * solver,  const OsiBiLinear * originalObject,
1000                                int way,
1001                                double separator, int chosen);
1002
1003    // Copy constructor
1004    OsiBiLinearBranchingObject ( const OsiBiLinearBranchingObject &);
1005
1006    // Assignment operator
1007    OsiBiLinearBranchingObject & operator=( const OsiBiLinearBranchingObject& rhs);
1008
1009    /// Clone
1010    virtual OsiBranchingObject * clone() const;
1011
1012    // Destructor
1013    virtual ~OsiBiLinearBranchingObject ();
1014
1015    using OsiBranchingObject::branch ;
1016    /// Does next branch and updates state
1017    virtual double branch(OsiSolverInterface * solver);
1018
1019    using OsiBranchingObject::print ;
1020    /** \brief Print something about branch - only if log level high
1021    */
1022    virtual void print(const OsiSolverInterface * solver = NULL);
1023    /** \brief Return true if branch should only bound variables
1024    */
1025    virtual bool boundBranch() const;
1026private:
1027    /// data
1028    /// 1 means branch on x, 2 branch on y
1029    short chosen_;
1030};
1031/** Define Continuous BiLinear objects for an == bound
1032
1033    This models x*y = b where both are continuous
1034
1035*/
1036
1037
1038class OsiBiLinearEquality : public OsiBiLinear {
1039
1040public:
1041
1042    // Default Constructor
1043    OsiBiLinearEquality ();
1044
1045    /** Useful constructor -
1046        This Adds in rows and variables to construct Ordered Set
1047        for x*y = b
1048        So note not const solver
1049    */
1050    OsiBiLinearEquality (OsiSolverInterface * solver, int xColumn,
1051                         int yColumn, int xyRow, double rhs,
1052                         double xMesh);
1053
1054    // Copy constructor
1055    OsiBiLinearEquality ( const OsiBiLinearEquality &);
1056
1057    /// Clone
1058    virtual OsiObject * clone() const;
1059
1060    // Assignment operator
1061    OsiBiLinearEquality & operator=( const OsiBiLinearEquality& rhs);
1062
1063    // Destructor
1064    virtual ~OsiBiLinearEquality ();
1065
1066    /// Possible improvement
1067    virtual double improvement(const OsiSolverInterface * solver) const;
1068    /** change grid
1069        if type 0 then use solution and make finer
1070        if 1 then back to original
1071        returns mesh size
1072    */
1073    double newGrid(OsiSolverInterface * solver, int type) const;
1074    /// Number of points
1075    inline int numberPoints() const {
1076        return numberPoints_;
1077    }
1078    inline void setNumberPoints(int value) {
1079        numberPoints_ = value;
1080    }
1081
1082private:
1083    /// Number of points
1084    int numberPoints_;
1085};
1086/// Define a single integer class - but one where you keep branching until fixed even if satisfied
1087
1088
1089class OsiSimpleFixedInteger : public OsiSimpleInteger {
1090
1091public:
1092
1093    /// Default Constructor
1094    OsiSimpleFixedInteger ();
1095
1096    /// Useful constructor - passed solver index
1097    OsiSimpleFixedInteger (const OsiSolverInterface * solver, int iColumn);
1098
1099    /// Useful constructor - passed solver index and original bounds
1100    OsiSimpleFixedInteger (int iColumn, double lower, double upper);
1101
1102    /// Useful constructor - passed simple integer
1103    OsiSimpleFixedInteger (const OsiSimpleInteger &);
1104
1105    /// Copy constructor
1106    OsiSimpleFixedInteger ( const OsiSimpleFixedInteger &);
1107
1108    /// Clone
1109    virtual OsiObject * clone() const;
1110
1111    /// Assignment operator
1112    OsiSimpleFixedInteger & operator=( const OsiSimpleFixedInteger& rhs);
1113
1114    /// Destructor
1115    virtual ~OsiSimpleFixedInteger ();
1116
1117    using OsiObject::infeasibility ;
1118    /// Infeasibility - large is 0.5
1119    virtual double infeasibility(const OsiBranchingInformation * info, int & whichWay) const;
1120
1121    /** Creates a branching object
1122
1123      The preferred direction is set by \p way, 0 for down, 1 for up.
1124    */
1125    virtual OsiBranchingObject * createBranch(OsiSolverInterface * solver, const OsiBranchingInformation * info, int way) const;
1126protected:
1127    /// data
1128
1129};
1130/** Define a single variable class which is involved with OsiBiLinear objects.
1131    This is used so can make better decision on where to branch as it can look at
1132    all objects.
1133
1134    This version sees if it can re-use code from OsiSimpleInteger
1135    even if not an integer variable.  If not then need to duplicate code.
1136*/
1137
1138
1139class OsiUsesBiLinear : public OsiSimpleInteger {
1140
1141public:
1142
1143    /// Default Constructor
1144    OsiUsesBiLinear ();
1145
1146    /// Useful constructor - passed solver index
1147    OsiUsesBiLinear (const OsiSolverInterface * solver, int iColumn, int type);
1148
1149    /// Useful constructor - passed solver index and original bounds
1150    OsiUsesBiLinear (int iColumn, double lower, double upper, int type);
1151
1152    /// Useful constructor - passed simple integer
1153    OsiUsesBiLinear (const OsiSimpleInteger & rhs, int type);
1154
1155    /// Copy constructor
1156    OsiUsesBiLinear ( const OsiUsesBiLinear & rhs);
1157
1158    /// Clone
1159    virtual OsiObject * clone() const;
1160
1161    /// Assignment operator
1162    OsiUsesBiLinear & operator=( const OsiUsesBiLinear& rhs);
1163
1164    /// Destructor
1165    virtual ~OsiUsesBiLinear ();
1166
1167    using OsiObject::infeasibility ;
1168    /// Infeasibility - large is 0.5
1169    virtual double infeasibility(const OsiBranchingInformation * info, int & whichWay) const;
1170
1171    /** Creates a branching object
1172
1173      The preferred direction is set by \p way, 0 for down, 1 for up.
1174    */
1175    virtual OsiBranchingObject * createBranch(OsiSolverInterface * solver, const OsiBranchingInformation * info, int way) const;
1176
1177    using OsiObject::feasibleRegion ;
1178    /** Set bounds to fix the variable at the current value.
1179
1180      Given an current value, set the lower and upper bounds to fix the
1181      variable. Returns amount it had to move variable.
1182    */
1183    virtual double feasibleRegion(OsiSolverInterface * solver, const OsiBranchingInformation * info) const;
1184
1185    /// Add all bi-linear objects
1186    void addBiLinearObjects(OsiSolverLink * solver);
1187protected:
1188    /// data
1189    /// Number of bilinear objects (maybe could be more general)
1190    int numberBiLinear_;
1191    /// Type of variable - 0 continuous, 1 integer
1192    int type_;
1193    /// Objects
1194    OsiObject ** objects_;
1195};
1196/** This class chooses a variable to branch on
1197
1198    This is just as OsiChooseStrong but it fakes it so only
1199    first so many are looked at in this phase
1200
1201*/
1202
1203class OsiChooseStrongSubset  : public OsiChooseStrong {
1204
1205public:
1206
1207    /// Default Constructor
1208    OsiChooseStrongSubset ();
1209
1210    /// Constructor from solver (so we can set up arrays etc)
1211    OsiChooseStrongSubset (const OsiSolverInterface * solver);
1212
1213    /// Copy constructor
1214    OsiChooseStrongSubset (const OsiChooseStrongSubset &);
1215
1216    /// Assignment operator
1217    OsiChooseStrongSubset & operator= (const OsiChooseStrongSubset& rhs);
1218
1219    /// Clone
1220    virtual OsiChooseVariable * clone() const;
1221
1222    /// Destructor
1223    virtual ~OsiChooseStrongSubset ();
1224
1225    /** Sets up strong list and clears all if initialize is true.
1226        Returns number of infeasibilities.
1227        If returns -1 then has worked out node is infeasible!
1228    */
1229    virtual int setupList ( OsiBranchingInformation *info, bool initialize);
1230    /** Choose a variable
1231        Returns -
1232       -1 Node is infeasible
1233       0  Normal termination - we have a candidate
1234       1  All looks satisfied - no candidate
1235       2  We can change the bound on a variable - but we also have a strong branching candidate
1236       3  We can change the bound on a variable - but we have a non-strong branching candidate
1237       4  We can change the bound on a variable - no other candidates
1238       We can pick up branch from bestObjectIndex() and bestWhichWay()
1239       We can pick up a forced branch (can change bound) from firstForcedObjectIndex() and firstForcedWhichWay()
1240       If we have a solution then we can pick up from goodObjectiveValue() and goodSolution()
1241       If fixVariables is true then 2,3,4 are all really same as problem changed
1242    */
1243    virtual int chooseVariable( OsiSolverInterface * solver, OsiBranchingInformation *info, bool fixVariables);
1244
1245    /// Number of objects to use
1246    inline int numberObjectsToUse() const {
1247        return numberObjectsToUse_;
1248    }
1249    /// Set number of objects to use
1250    inline void setNumberObjectsToUse(int value) {
1251        numberObjectsToUse_ = value;
1252    }
1253
1254protected:
1255    // Data
1256    /// Number of objects to be used (and set in solver)
1257    int numberObjectsToUse_;
1258};
1259
1260#include <string>
1261
1262#include "CglStored.hpp"
1263
1264class CoinWarmStartBasis;
1265/** Stored Temporary Cut Generator Class - destroyed after first use */
1266class CglTemporary : public CglStored {
1267
1268public:
1269
1270
1271    /**@name Generate Cuts */
1272    //@{
1273    /** Generate Mixed Integer Stored cuts for the model of the
1274        solver interface, si.
1275
1276        Insert the generated cuts into OsiCut, cs.
1277
1278        This generator just looks at previously stored cuts
1279        and inserts any that are violated by enough
1280    */
1281    virtual void generateCuts( const OsiSolverInterface & si, OsiCuts & cs,
1282                               const CglTreeInfo info = CglTreeInfo());
1283    //@}
1284
1285    /**@name Constructors and destructors */
1286    //@{
1287    /// Default constructor
1288    CglTemporary ();
1289
1290    /// Copy constructor
1291    CglTemporary (const CglTemporary & rhs);
1292
1293    /// Clone
1294    virtual CglCutGenerator * clone() const;
1295
1296    /// Assignment operator
1297    CglTemporary &
1298    operator=(const CglTemporary& rhs);
1299
1300    /// Destructor
1301    virtual
1302    ~CglTemporary ();
1303    //@}
1304
1305private:
1306
1307// Private member methods
1308
1309    // Private member data
1310};
1311//#############################################################################
1312
1313/**
1314
1315This is to allow the user to replace initialSolve and resolve
1316*/
1317
1318class OsiSolverLinearizedQuadratic : public OsiClpSolverInterface {
1319
1320public:
1321    //---------------------------------------------------------------------------
1322    /**@name Solve methods */
1323    //@{
1324    /// Solve initial LP relaxation
1325    virtual void initialSolve();
1326    //@}
1327
1328
1329    /**@name Constructors and destructors */
1330    //@{
1331    /// Default Constructor
1332    OsiSolverLinearizedQuadratic ();
1333    /// Useful constructor (solution should be good)
1334    OsiSolverLinearizedQuadratic(  ClpSimplex * quadraticModel);
1335    /// Clone
1336    virtual OsiSolverInterface * clone(bool copyData = true) const;
1337
1338    /// Copy constructor
1339    OsiSolverLinearizedQuadratic (const OsiSolverLinearizedQuadratic &);
1340
1341    /// Assignment operator
1342    OsiSolverLinearizedQuadratic & operator=(const OsiSolverLinearizedQuadratic& rhs);
1343
1344    /// Destructor
1345    virtual ~OsiSolverLinearizedQuadratic ();
1346
1347    //@}
1348
1349
1350    /**@name Sets and Gets */
1351    //@{
1352    /// Objective value of best solution found internally
1353    inline double bestObjectiveValue() const {
1354        return bestObjectiveValue_;
1355    }
1356    /// Best solution found internally
1357    const double * bestSolution() const {
1358        return bestSolution_;
1359    }
1360    /// Set special options
1361    inline void setSpecialOptions3(int value) {
1362        specialOptions3_ = value;
1363    }
1364    /// Get special options
1365    inline int specialOptions3() const {
1366        return specialOptions3_;
1367    }
1368    /// Copy of quadratic model if one
1369    ClpSimplex * quadraticModel() const {
1370        return quadraticModel_;
1371    }
1372    //@}
1373
1374    //---------------------------------------------------------------------------
1375
1376protected:
1377
1378
1379    /**@name functions */
1380    //@{
1381
1382    /**@name Private member data */
1383    //@{
1384    /// Objective value of best solution found internally
1385    double bestObjectiveValue_;
1386    /// Copy of quadratic model if one
1387    ClpSimplex * quadraticModel_;
1388    /// Best solution found internally
1389    double * bestSolution_;
1390    /**
1391       0 bit (1) - don't do mini B&B
1392       1 bit (2) - quadratic only in objective
1393    */
1394    int specialOptions3_;
1395    //@}
1396};
1397class ClpSimplex;
1398/** Return an approximate solution to a CoinModel.
1399    Lots of bounds may be odd to force a solution.
1400    mode = 0 just tries to get a continuous solution
1401*/
1402ClpSimplex * approximateSolution(CoinModel & coinModel,
1403                                 int numberPasses, double deltaTolerance,
1404                                 int mode = 0);
1405#endif
1406
Note: See TracBrowser for help on using the repository browser.