From b8ec67f491da3c6ddad3e1c55d70400fdab4961b Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Stephan=20A=C3=9Fmus?= Date: Sun, 6 Dec 2009 13:14:45 +0000 Subject: [PATCH] * Simplified and optimized a lot the "ToString()" debugging facilities. * *::Index() is now const, thanks to the BList improvements. git-svn-id: file:///srv/svn/repos/haiku/haiku/trunk@34521 a95241bf-73f2-0310-859d-f6bbb57e9c96 --- headers/libs/alm/Area.h | 24 ++-- headers/libs/linprog/Constraint.h | 18 +-- headers/libs/linprog/LinearSpec.h | 58 ++++----- headers/libs/linprog/Variable.h | 8 +- src/libs/alm/Area.cpp | 196 ++++++++++++++-------------- src/libs/alm/BALMLayout.cpp | 107 ++++++++------- src/libs/linprog/Constraint.cpp | 129 +++++++++--------- src/libs/linprog/LinearSpec.cpp | 208 +++++++++++++++--------------- src/libs/linprog/Variable.cpp | 79 ++++++------ 9 files changed, 404 insertions(+), 423 deletions(-) diff --git a/headers/libs/alm/Area.h b/headers/libs/alm/Area.h index 7c6f498486..d1165dc16f 100644 --- a/headers/libs/alm/Area.h +++ b/headers/libs/alm/Area.h @@ -29,7 +29,7 @@ class BALMLayout; * Rectangular area in the GUI, defined by a tab on each side. */ class Area { - + public: XTab* Left() const; void SetLeft(XTab* left); @@ -83,32 +83,32 @@ public: bool AutoPreferredContentSize() const; void SetAutoPreferredContentSize(bool value); - BString* ToBString(); - const char* ToString(); + operator BString() const; + void GetString(BString& string) const; Constraint* HasSameWidthAs(Area* area); Constraint* HasSameHeightAs(Area* area); BList* HasSameSizeAs(Area* area); ~Area(); - + protected: Area(BALMLayout* ls, XTab* left, YTab* top, - XTab* right, YTab* bottom, - BView* content, + XTab* right, YTab* bottom, + BView* content, BSize minContentSize); - Area(BALMLayout* ls, Row* row, Column* column, + Area(BALMLayout* ls, Row* row, Column* column, BView* content, BSize minContentSize); void DoLayout(); - + private: void InitChildArea(); void UpdateHorizontal(); void UpdateVertical(); - void Init(BALMLayout* ls, XTab* left, YTab* top, - XTab* right, YTab* bottom, - BView* content, + void Init(BALMLayout* ls, XTab* left, YTab* top, + XTab* right, YTab* bottom, + BView* content, BSize minContentSize); public: @@ -152,7 +152,7 @@ private: Constraint* fTopConstraint; Constraint* fRightConstraint; Constraint* fBottomConstraint; - + public: friend class BALMLayout; diff --git a/headers/libs/linprog/Constraint.h b/headers/libs/linprog/Constraint.h index f804350c81..00ca91b410 100644 --- a/headers/libs/linprog/Constraint.h +++ b/headers/libs/linprog/Constraint.h @@ -19,28 +19,28 @@ namespace LinearProgramming { - + class LinearSpec; /** - * Hard linear constraint, i.e. one that must be satisfied. + * Hard linear constraint, i.e. one that must be satisfied. * May render a specification infeasible. */ class Constraint { - + public: - int32 Index(); + int32 Index() const; BList* LeftSide(); void SetLeftSide(BList* summands); void UpdateLeftSide(); void SetLeftSide(double coeff1, Variable* var1); - void SetLeftSide(double coeff1, Variable* var1, + void SetLeftSide(double coeff1, Variable* var1, double coeff2, Variable* var2); - void SetLeftSide(double coeff1, Variable* var1, + void SetLeftSide(double coeff1, Variable* var1, double coeff2, Variable* var2, double coeff3, Variable* var3); - void SetLeftSide(double coeff1, Variable* var1, + void SetLeftSide(double coeff1, Variable* var1, double coeff2, Variable* var2, double coeff3, Variable* var3, double coeff4, Variable* var4); @@ -68,8 +68,8 @@ public: bool IsValid(); void Invalidate(); - BString* ToBString(); - const char* ToString(); + operator BString() const; + void GetString(BString& string) const; ~Constraint(); diff --git a/headers/libs/linprog/LinearSpec.h b/headers/libs/linprog/LinearSpec.h index d21a8d1f2e..72677128b4 100644 --- a/headers/libs/linprog/LinearSpec.h +++ b/headers/libs/linprog/LinearSpec.h @@ -25,7 +25,7 @@ namespace LinearProgramming { - + class Constraint; class ObjFunctionSummand; class PenaltyFunction; @@ -35,52 +35,52 @@ class Variable; * Specification of a linear programming problem. */ class LinearSpec { - + public: LinearSpec(); virtual ~LinearSpec(); Variable* AddVariable(); - Constraint* AddConstraint(BList* summands, - OperatorType op, double rightSide); - Constraint* AddConstraint(double coeff1, Variable* var1, - OperatorType op, double rightSide); - Constraint* AddConstraint(double coeff1, Variable* var1, - double coeff2, Variable* var2, + Constraint* AddConstraint(BList* summands, OperatorType op, double rightSide); Constraint* AddConstraint(double coeff1, Variable* var1, - double coeff2, Variable* var2, - double coeff3, Variable* var3, OperatorType op, double rightSide); Constraint* AddConstraint(double coeff1, Variable* var1, - double coeff2, Variable* var2, - double coeff3, Variable* var3, - double coeff4, Variable* var4, + double coeff2, Variable* var2, + OperatorType op, double rightSide); + Constraint* AddConstraint(double coeff1, Variable* var1, + double coeff2, Variable* var2, + double coeff3, Variable* var3, + OperatorType op, double rightSide); + Constraint* AddConstraint(double coeff1, Variable* var1, + double coeff2, Variable* var2, + double coeff3, Variable* var3, + double coeff4, Variable* var4, OperatorType op, double rightSide); - Constraint* AddConstraint(BList* summands, - OperatorType op, double rightSide, + Constraint* AddConstraint(BList* summands, + OperatorType op, double rightSide, double penaltyNeg, double penaltyPos); Constraint* AddConstraint(double coeff1, Variable* var1, - OperatorType op, double rightSide, + OperatorType op, double rightSide, double penaltyNeg, double penaltyPos); Constraint* AddConstraint(double coeff1, Variable* var1, - double coeff2, Variable* var2, - OperatorType op, double rightSide, + double coeff2, Variable* var2, + OperatorType op, double rightSide, double penaltyNeg, double penaltyPos); Constraint* AddConstraint(double coeff1, Variable* var1, - double coeff2, Variable* var2, - double coeff3, Variable* var3, - OperatorType op, double rightSide, + double coeff2, Variable* var2, + double coeff3, Variable* var3, + OperatorType op, double rightSide, double penaltyNeg, double penaltyPos); Constraint* AddConstraint(double coeff1, Variable* var1, - double coeff2, Variable* var2, - double coeff3, Variable* var3, - double coeff4, Variable* var4, - OperatorType op, double rightSide, + double coeff2, Variable* var2, + double coeff3, Variable* var3, + double coeff4, Variable* var4, + OperatorType op, double rightSide, double penaltyNeg, double penaltyPos); - + PenaltyFunction* AddPenaltyFunction(Variable* var, BList* xs, BList* gs); BList* ObjFunction(); @@ -90,7 +90,7 @@ public: ResultType Presolve(); void RemovePresolved(); ResultType Solve(); - void Save(char* fname); + void Save(const char* fileName); int32 CountColumns() const; OptimizationType Optimization() const; @@ -101,8 +101,8 @@ public: double ObjectiveValue() const; double SolvingTime() const; - BString* ToBString(); - const char* ToString(); + operator BString() const; + void GetString(BString& string) const; protected: int32 fCountColumns; diff --git a/headers/libs/linprog/Variable.h b/headers/libs/linprog/Variable.h index 45cf7a28ea..d212fd6bec 100644 --- a/headers/libs/linprog/Variable.h +++ b/headers/libs/linprog/Variable.h @@ -24,7 +24,7 @@ class Summand; class Variable { public: - int32 Index(); + int32 Index() const; LinearSpec* LS() const; double Value() const; void SetValue(double value); @@ -36,9 +36,9 @@ public: const char* Label(); void SetLabel(const char* label); - - BString* ToBString(); - const char* ToString(); + + operator BString() const; + void GetString(BString& string) const; Constraint* IsEqual(Variable* var); Constraint* IsSmallerOrEqual(Variable* var); diff --git a/src/libs/alm/Area.cpp b/src/libs/alm/Area.cpp index 8a89a59a14..740d4275b0 100644 --- a/src/libs/alm/Area.cpp +++ b/src/libs/alm/Area.cpp @@ -73,12 +73,12 @@ void Area::SetLeft(XTab* left) { fLeft = left; - + fColumn = NULL; - + if (fChildArea == NULL) { fMinContentWidth->SetLeftSide(-1.0, fLeft, 1.0, fRight); - + if (fMaxContentWidth != NULL) fMaxContentWidth->SetLeftSide(-1.0, fLeft, 1.0, fRight); } else @@ -108,12 +108,12 @@ void Area::SetRight(XTab* right) { fRight = right; - + fColumn = NULL; - + if (fChildArea == NULL) { fMinContentWidth->SetLeftSide(-1.0, fLeft, 1.0, fRight); - + if (fMaxContentWidth != NULL) fMaxContentWidth->SetLeftSide(-1.0, fLeft, 1.0, fRight); } else @@ -139,12 +139,12 @@ void Area::SetTop(YTab* top) { fTop = top; - + fRow = NULL; - + if (fChildArea == NULL) { fMinContentHeight->SetLeftSide(-1.0, fTop, 1.0, fBottom); - + if (fMaxContentHeight != NULL) fMaxContentHeight->SetLeftSide(-1.0, fTop, 1.0, fBottom); } else @@ -170,12 +170,12 @@ void Area::SetBottom(YTab* bottom) { fBottom = bottom; - + fRow = NULL; - + if (fChildArea == NULL) { fMinContentHeight->SetLeftSide(-1.0, fTop, 1.0, fBottom); - + if (fMaxContentHeight != NULL) fMaxContentHeight->SetLeftSide(-1.0, fTop, 1.0, fBottom); } else @@ -315,7 +315,7 @@ Area::SetMinContentSize(BSize min) fMinContentSize = min; fMinContentWidth->SetRightSide(fMinContentSize.Width()); fMinContentHeight->SetRightSide(fMinContentSize.Height()); - } else + } else fChildArea->SetMinContentSize(min); fLS->InvalidateLayout(); } @@ -342,7 +342,7 @@ Area::SetMaxContentSize(BSize max) fMaxContentWidth = fLS->AddConstraint(-1.0, fLeft, 1.0, fRight, OperatorType(LE), fMaxContentSize.Width()); fConstraints->AddItem(fMaxContentWidth); - + fMaxContentHeight = fLS->AddConstraint(-1.0, fTop, 1.0, fBottom, OperatorType(LE), fMaxContentSize.Height()); fConstraints->AddItem(fMaxContentHeight); @@ -370,7 +370,7 @@ Area::PreferredContentSize() const /** * Sets Preferred size of the area's content. * May be different from the preferred size of the area. - * Manual changes of PreferredContentSize are ignored unless + * Manual changes of PreferredContentSize are ignored unless * autoPreferredContentSize is set to false. */ void @@ -384,7 +384,7 @@ Area::SetPreferredContentSize(BSize preferred) fPreferredContentSize.Width(), fShrinkPenalties.Width(), fGrowPenalties.Width()); fConstraints->AddItem(fPreferredContentWidth); - + fPreferredContentHeight = fLS->AddConstraint( -1.0, fTop, 1.0, fBottom, OperatorType(EQ), fPreferredContentSize.Height(), fShrinkPenalties.Height(), @@ -418,7 +418,7 @@ void Area::SetShrinkPenalties(BSize shrink) { fPreferredContentWidth->SetPenaltyNeg(shrink.Width()); fPreferredContentHeight->SetPenaltyNeg(shrink.Height()); } - } else + } else fChildArea->SetShrinkPenalties(shrink); fLS->InvalidateLayout(); } @@ -444,7 +444,7 @@ Area::SetGrowPenalties(BSize grow) fPreferredContentWidth->SetPenaltyPos(grow.Width()); fPreferredContentHeight->SetPenaltyPos(grow.Height()); } - } else + } else fChildArea->SetGrowPenalties(grow); fLS->InvalidateLayout(); } @@ -616,7 +616,7 @@ Area::SetBottomInset(int32 bottom) /** - * Sets the preferred size according to the content's PreferredSize method, + * Sets the preferred size according to the content's PreferredSize method, * and the penalties according to heuristics. */ void @@ -628,12 +628,12 @@ Area::SetDefaultBehavior() SetGrowPenalties(BSize(0, 0)); return; } - + if (PreferredContentSize() != Content()->PreferredSize()){ SetPreferredContentSize(Content()->PreferredSize()); fLS->InvalidateLayout(); } - + if (dynamic_cast(Content()) != NULL || dynamic_cast(Content()) != NULL || dynamic_cast(Content()) != NULL @@ -649,40 +649,32 @@ Area::SetDefaultBehavior() } -BString* -Area::ToBString() -{ - BString* str = new BString(); - BString* leftStr = fLeft->ToBString(); - BString* topStr = fTop->ToBString(); - BString* rightStr = fRight->ToBString(); - BString* bottomStr = fBottom->ToBString(); - *str << "Area(" << *leftStr << ", " - << *topStr << ", " - << *rightStr << ", " - << *bottomStr << ")"; - delete leftStr; - delete topStr; - delete rightStr; - delete bottomStr; - return str; -} - - -const char* -Area::ToString() -{ - BString* str = new BString(); - char* result = (char*) malloc(str->Length() + 1); - str->CopyInto(result, 0, str->Length()); - delete str; - return result; +Area::operator BString() const +{ + BString string; + GetString(string); + return string; +} + + +void +Area::GetString(BString& string) const +{ + string << "Area("; + fLeft->GetString(string); + string << ", "; + fTop->GetString(string); + string << ", "; + fRight->GetString(string); + string << ", "; + fBottom->GetString(string); + string << ")"; } /** * Sets the width of the area to be the same as the width of the given area. - * + * * @param area the area that should have the same width * @return the same-width constraint */ @@ -690,14 +682,14 @@ Constraint* Area::HasSameWidthAs(Area* area) { return fLS->AddConstraint( - -1.0, fLeft, 1.0, fRight, 1.0, area->fLeft, -1.0, area->fRight, + -1.0, fLeft, 1.0, fRight, 1.0, area->fLeft, -1.0, area->fRight, OperatorType(EQ), 0.0); } /** * Sets the height of the area to be the same as the height of the given area. - * + * * @param area the area that should have the same height * @return the same-height constraint */ @@ -705,14 +697,14 @@ Constraint* Area::HasSameHeightAs(Area* area) { return fLS->AddConstraint( - -1.0, fTop, 1.0, fBottom, 1.0, area->fTop, -1.0, area->fBottom, + -1.0, fTop, 1.0, fBottom, 1.0, area->fTop, -1.0, area->fBottom, OperatorType(EQ), 0.0); } /** * Sets the size of the area to be the same as the size of the given area. - * + * * @param area the area that should have the same size * @return a list containing a same-width and same-height constraint */ @@ -743,9 +735,9 @@ Area::~Area() * Constructor. * Uses XTabs and YTabs. */ -Area::Area(BALMLayout* ls, XTab* left, YTab* top, XTab* right, YTab* bottom, +Area::Area(BALMLayout* ls, XTab* left, YTab* top, XTab* right, YTab* bottom, BView* content, BSize minContentSize) -{ +{ Init(ls, left, top, right, bottom, content, minContentSize); } @@ -757,8 +749,8 @@ Area::Area(BALMLayout* ls, XTab* left, YTab* top, XTab* right, YTab* bottom, Area::Area(BALMLayout* ls, Row* row, Column* column, BView* content, BSize minContentSize) { - - Init(ls, column->Left(), row->Top(), column->Right(), row->Bottom(), + + Init(ls, column->Left(), row->Top(), column->Right(), row->Bottom(), content, minContentSize); fRow = row; fColumn = column; @@ -769,40 +761,40 @@ Area::Area(BALMLayout* ls, Row* row, Column* column, BView* content, * Initialize variables. */ void -Area::Init(BALMLayout* ls, XTab* left, YTab* top, XTab* right, YTab* bottom, +Area::Init(BALMLayout* ls, XTab* left, YTab* top, XTab* right, YTab* bottom, BView* content, BSize minContentSize) { - + fConstraints = new BList(2); fMaxContentSize = kMaxSize; - + fMaxContentWidth = NULL; fMaxContentHeight = NULL; - + fPreferredContentSize = kUndefinedSize; fShrinkPenalties = BSize(2, 2); fGrowPenalties = BSize(1, 1); fContentAspectRatio = 0; fContentAspectRatioC = NULL; - + fAutoPreferredContentSize = false; - + fPreferredContentWidth = NULL; fPreferredContentHeight = NULL; - + fChildArea = NULL; - + fAlignment = BAlignment(B_ALIGN_USE_FULL_WIDTH, B_ALIGN_USE_FULL_HEIGHT); fLeftInset = 0; fTopInset = 0; fRightInset = 0; fBottomInset = 0; - + fLeftConstraint = NULL; fTopConstraint = NULL; fRightConstraint = NULL; fBottomConstraint = NULL; - + fLS = ls; fLeft = left; fRight = right; @@ -810,13 +802,13 @@ Area::Init(BALMLayout* ls, XTab* left, YTab* top, XTab* right, YTab* bottom, fBottom = bottom; SetContent(content); fMinContentSize = minContentSize; - - // adds the two essential constraints of the area that make sure that the left x-tab is + + // adds the two essential constraints of the area that make sure that the left x-tab is // really to the left of the right x-tab, and the top y-tab really above the bottom y-tab fMinContentWidth = ls->AddConstraint(-1.0, left, 1.0, right, OperatorType(GE), minContentSize.Width()); fConstraints->AddItem(fMinContentWidth); - + fMinContentHeight = ls->AddConstraint(-1.0, top, 1.0, bottom, OperatorType(GE), minContentSize.Height()); fConstraints->AddItem(fMinContentHeight); @@ -828,14 +820,14 @@ Area::Init(BALMLayout* ls, XTab* left, YTab* top, XTab* right, YTab* bottom, */ void Area::DoLayout() { - if (Content() == NULL) + if (Content() == NULL) return; // empty areas need no layout - + // if there is a childArea, then it is the childArea that actually contains the content Area* area = (fChildArea != NULL) ? fChildArea : this; - + // set content location and size - area->Content()->MoveTo(floor(area->Left()->Value() + 0.5), + area->Content()->MoveTo(floor(area->Left()->Value() + 0.5), floor(area->Top()->Value() + 0.5)); int32 width = (int32)floor(area->Right()->Value() - area->Left()->Value() + 0.5); int32 height = (int32)floor(area->Bottom()->Value() - area->Top()->Value() + 0.5); @@ -844,15 +836,15 @@ void Area::DoLayout() /** - * Adds a childArea to this area, together with constraints that specify the relative location - * of the childArea within this area. It is called when such a childArea becomes necessary, + * Adds a childArea to this area, together with constraints that specify the relative location + * of the childArea within this area. It is called when such a childArea becomes necessary, * i.e. when the user requests insets or special alignment. */ void Area::InitChildArea() { // add a child area with new tabs, - // and add constraints that set its tabs to be equal to the + // and add constraints that set its tabs to be equal to the // coresponding tabs of this area (for a start) fChildArea = new Area(fLS, new XTab(fLS), new YTab(fLS), new XTab(fLS), new YTab(fLS), fContent, BSize(0, 0)); @@ -864,7 +856,7 @@ Area::InitChildArea() fConstraints->AddItem(fRightConstraint); fBottomConstraint = fBottom->IsEqual(fChildArea->Bottom()); fConstraints->AddItem(fBottomConstraint); - + // remove the minimum content size constraints from this area // and copy the minimum content size setting to the childArea fConstraints->RemoveItem(fMinContentWidth); @@ -875,33 +867,33 @@ Area::InitChildArea() fMinContentHeight = fChildArea->fMinContentHeight; fChildArea->SetMinContentSize(fMinContentSize); - // if there are maximum content size constraints on this area, - // change them so that they refer to the tabs of the childArea + // if there are maximum content size constraints on this area, + // change them so that they refer to the tabs of the childArea // and copy the minimum content size settings to the childArea if (fMaxContentWidth != NULL) { fChildArea->fMaxContentSize = fMaxContentSize; - + fChildArea->fMaxContentWidth = fMaxContentWidth; fMaxContentWidth->SetLeftSide( -1.0, fChildArea->Left(), 1.0, fChildArea->Right()); - + fChildArea->fMaxContentHeight = fMaxContentHeight; fMaxContentHeight->SetLeftSide( -1.0, fChildArea->Top(), 1.0, fChildArea->Bottom()); } - - // if there are preferred content size constraints on this area, - // change them so that they refer to the tabs of the childArea + + // if there are preferred content size constraints on this area, + // change them so that they refer to the tabs of the childArea // and copy the preferred content size settings to the childArea if (fPreferredContentHeight != NULL) { fChildArea->fPreferredContentSize = fPreferredContentSize; fChildArea->fShrinkPenalties = fShrinkPenalties; fChildArea->fGrowPenalties = fGrowPenalties; - + fChildArea->fPreferredContentWidth = fPreferredContentWidth; fPreferredContentWidth->SetLeftSide( -1.0, fChildArea->Left(), 1.0, fChildArea->Right()); - + fChildArea->fPreferredContentHeight = fPreferredContentHeight; fPreferredContentHeight->SetLeftSide( -1.0, fChildArea->Top(), 1.0, fChildArea->Bottom()); @@ -919,13 +911,13 @@ Area::UpdateHorizontal() if (fChildArea == NULL) InitChildArea(); - // change the constraints leftConstraint and rightConstraint so that the horizontal + // change the constraints leftConstraint and rightConstraint so that the horizontal // alignment and insets of the childArea within this area are as specified by the user if (fAlignment.Horizontal() == B_ALIGN_LEFT) { fLeftConstraint->SetLeftSide(-1.0, fLeft, 1.0, fChildArea->Left()); fLeftConstraint->SetOp(OperatorType(EQ)); fLeftConstraint->SetRightSide(fLeftInset); - + fRightConstraint->SetLeftSide(-1.0, fChildArea->Right(), 1.0, fRight); fRightConstraint->SetOp(OperatorType(GE)); fRightConstraint->SetRightSide(fRightInset); @@ -933,7 +925,7 @@ Area::UpdateHorizontal() fLeftConstraint->SetLeftSide(-1.0, fLeft, 1.0, fChildArea->Left()); fLeftConstraint->SetOp(OperatorType(GE)); fLeftConstraint->SetRightSide(fLeftInset); - + fRightConstraint->SetLeftSide(-1.0, fChildArea->Right(), 1.0, fRight); fRightConstraint->SetOp(OperatorType(EQ)); fRightConstraint->SetRightSide(fRightInset); @@ -941,7 +933,7 @@ Area::UpdateHorizontal() fLeftConstraint->SetLeftSide(-1.0, fLeft, 1.0, fChildArea->Left()); fLeftConstraint->SetOp(OperatorType(GE)); fLeftConstraint->SetRightSide(max(fLeftInset, fRightInset)); - + fRightConstraint->SetLeftSide(-1.0, fLeft, 1.0, fChildArea->Left(), 1.0, fChildArea->Right(), -1.0, fRight); fRightConstraint->SetOp(OperatorType(EQ)); fRightConstraint->SetRightSide(0); @@ -949,7 +941,7 @@ Area::UpdateHorizontal() fLeftConstraint->SetLeftSide(-1.0, fLeft, 1.0, fChildArea->Left()); fLeftConstraint->SetOp(OperatorType(EQ)); fLeftConstraint->SetRightSide(fLeftInset); - + fRightConstraint->SetLeftSide(-1.0, fChildArea->Right(), 1.0, fRight); fRightConstraint->SetOp(OperatorType(EQ)); fRightConstraint->SetRightSide(fRightInset); @@ -957,7 +949,7 @@ Area::UpdateHorizontal() fLeftConstraint->SetLeftSide(-1.0, fLeft, 1.0, fChildArea->Left()); fLeftConstraint->SetOp(OperatorType(GE)); fLeftConstraint->SetRightSide(fLeftInset); - + fRightConstraint->SetLeftSide(-1.0, fChildArea->Right(), 1.0, fRight); fRightConstraint->SetOp(OperatorType(GE)); fRightConstraint->SetRightSide(fRightInset); @@ -970,16 +962,16 @@ Area::UpdateHorizontal() */ void Area::UpdateVertical() { // if the area does not have a childAdrea yet, this is the time to add it - if (fChildArea == NULL) + if (fChildArea == NULL) InitChildArea(); - - // change the constraints topConstraint and bottomConstraint so that the vertical + + // change the constraints topConstraint and bottomConstraint so that the vertical // alignment and insets of the childArea within this area are as specified by the user if (fAlignment.Vertical() == B_ALIGN_TOP) { fTopConstraint->SetLeftSide(-1.0, fTop, 1.0, fChildArea->Top()); fTopConstraint->SetOp(OperatorType(EQ)); fTopConstraint->SetRightSide(fTopInset); - + fBottomConstraint->SetLeftSide(-1.0, fChildArea->Bottom(), 1.0, fBottom); fBottomConstraint->SetOp(OperatorType(GE)); fBottomConstraint->SetRightSide(fBottomInset); @@ -987,7 +979,7 @@ void Area::UpdateVertical() { fTopConstraint->SetLeftSide(-1.0, fTop, 1.0, fChildArea->Top()); fTopConstraint->SetOp(OperatorType(GE)); fTopConstraint->SetRightSide(fTopInset); - + fBottomConstraint->SetLeftSide(-1.0, fChildArea->Bottom(), 1.0, fBottom); fBottomConstraint->SetOp(OperatorType(EQ)); fBottomConstraint->SetRightSide(fBottomInset); @@ -995,7 +987,7 @@ void Area::UpdateVertical() { fTopConstraint->SetLeftSide(-1.0, fTop, 1.0, fChildArea->Top()); fTopConstraint->SetOp(OperatorType(GE)); fTopConstraint->SetRightSide(max(fTopInset, fBottomInset)); - + fBottomConstraint->SetLeftSide(-1.0, fTop, 1.0, fChildArea->Top(), 1.0, fChildArea->Bottom(), -1.0, fBottom); fBottomConstraint->SetOp(OperatorType(EQ)); fBottomConstraint->SetRightSide(0); @@ -1003,7 +995,7 @@ void Area::UpdateVertical() { fTopConstraint->SetLeftSide(-1.0, fTop, 1.0, fChildArea->Top()); fTopConstraint->SetOp(OperatorType(EQ)); fTopConstraint->SetRightSide(fTopInset); - + fBottomConstraint->SetLeftSide(-1.0, fChildArea->Bottom(), 1.0, fBottom); fBottomConstraint->SetOp(OperatorType(EQ)); fBottomConstraint->SetRightSide(fBottomInset); @@ -1011,7 +1003,7 @@ void Area::UpdateVertical() { fTopConstraint->SetLeftSide(-1.0, fTop, 1.0, fChildArea->Top()); fTopConstraint->SetOp(OperatorType(GE)); fTopConstraint->SetRightSide(fTopInset); - + fBottomConstraint->SetLeftSide(-1.0, fChildArea->Bottom(), 1.0, fBottom); fBottomConstraint->SetOp(OperatorType(GE)); fBottomConstraint->SetRightSide(fBottomInset); diff --git a/src/libs/alm/BALMLayout.cpp b/src/libs/alm/BALMLayout.cpp index 95bb1eff7e..ccbedbd207 100644 --- a/src/libs/alm/BALMLayout.cpp +++ b/src/libs/alm/BALMLayout.cpp @@ -19,29 +19,29 @@ * Constructor. * Creates new layout engine. */ -BALMLayout::BALMLayout() +BALMLayout::BALMLayout() : BLayout(), LinearSpec() { fLayoutStyle = FIT_TO_SIZE; fActivated = true; - + fAreas = new BList(1); fLeft = new XTab(this); fRight = new XTab(this); fTop = new YTab(this); fBottom = new YTab(this); - + // the Left tab is always at x-position 0, and the Top tab is always at y-position 0 fLeft->SetRange(0, 0); fTop->SetRange(0, 0); - + // cached layout values // need to be invalidated whenever the layout specification is changed fMinSize = Area::kUndefinedSize; fMaxSize = Area::kUndefinedSize; fPreferredSize = Area::kUndefinedSize; - + fPerformancePath = NULL; } @@ -61,23 +61,28 @@ BALMLayout::SolveLayout() if (currentArea->AutoPreferredContentSize()) currentArea->SetDefaultBehavior(); } - - // try to solve the layout until the result is OPTIMAL or INFEASIBLE, maximally - // 15 tries sometimes the solving algorithm encounters numerical problems - // (NUMFAILURE), and repeating the solving often helps to overcome them - BFile* file = new BFile(fPerformancePath, - B_READ_WRITE | B_CREATE_FILE | B_OPEN_AT_END); - + + // Try to solve the layout until the result is OPTIMAL or INFEASIBLE, + // maximally 15 tries sometimes the solving algorithm encounters numerical + // problems (NUMFAILURE), and repeating the solving often helps to overcome + // them. + BFile* file = NULL; + if (fPerformancePath != NULL) { + file = new BFile(fPerformancePath, + B_READ_WRITE | B_CREATE_FILE | B_OPEN_AT_END); + } + ResultType result; for (int32 tries = 0; tries < 15; tries++) { result = Solve(); if (fPerformancePath != NULL) { char buffer [100]; - file->Write(buffer, sprintf(buffer, "%d\t%fms\t#vars=%ld\t#constraints=%ld\n", - result, SolvingTime(), Variables()->CountItems(), - Constraints()->CountItems())); + file->Write(buffer, sprintf(buffer, "%d\t%fms\t#vars=%ld\t" + "#constraints=%ld\n", result, SolvingTime(), + Variables()->CountItems(), Constraints()->CountItems())); } - if (result == OPTIMAL || result == INFEASIBLE) break; + if (result == OPTIMAL || result == INFEASIBLE) + break; } delete file; } @@ -85,7 +90,7 @@ BALMLayout::SolveLayout() /** * Adds a new x-tab to the specification. - * + * * @return the new x-tab */ XTab* @@ -93,11 +98,11 @@ BALMLayout::AddXTab() { return new XTab(this); } - + /** * Adds a new y-tab to the specification. - * + * * @return the new y-tab */ YTab* @@ -109,7 +114,7 @@ BALMLayout::AddYTab() /** * Adds a new row to the specification. - * + * * @return the new row */ Row* @@ -121,7 +126,7 @@ BALMLayout::AddRow() /** * Adds a new row to the specification that is glued to the given y-tabs. - * + * * @param top * @param bottom * @return the new row @@ -130,15 +135,17 @@ Row* BALMLayout::AddRow(YTab* top, YTab* bottom) { Row* row = new Row(this); - if (top != NULL) row->Constraints()->AddItem(row->Top()->IsEqual(top)); - if (bottom != NULL) row->Constraints()->AddItem(row->Bottom()->IsEqual(bottom)); + if (top != NULL) + row->Constraints()->AddItem(row->Top()->IsEqual(top)); + if (bottom != NULL) + row->Constraints()->AddItem(row->Bottom()->IsEqual(bottom)); return row; } /** * Adds a new column to the specification. - * + * * @return the new column */ Column* @@ -150,7 +157,7 @@ BALMLayout::AddColumn() /** * Adds a new column to the specification that is glued to the given x-tabs. - * + * * @param left * @param right * @return the new column @@ -167,7 +174,7 @@ BALMLayout::AddColumn(XTab* left, XTab* right) /** * Adds a new area to the specification, setting only the necessary minimum size constraints. - * + * * @param left left border * @param top top border * @param right right border @@ -179,7 +186,7 @@ BALMLayout::AddColumn(XTab* left, XTab* right) Area* BALMLayout::AddArea(XTab* left, YTab* top, XTab* right, YTab* bottom, BView* content, BSize minContentSize) -{ +{ InvalidateLayout(); if (content != NULL) View()->AddChild(content); @@ -191,7 +198,7 @@ BALMLayout::AddArea(XTab* left, YTab* top, XTab* right, YTab* bottom, /** * Adds a new area to the specification, setting only the necessary minimum size constraints. - * + * * @param row the row that defines the top and bottom border * @param column the column that defines the left and right border * @param content the control which is the area content @@ -201,7 +208,7 @@ BALMLayout::AddArea(XTab* left, YTab* top, XTab* right, YTab* bottom, Area* BALMLayout::AddArea(Row* row, Column* column, BView* content, BSize minContentSize) -{ +{ InvalidateLayout(); if (content != NULL) View()->AddChild(content); @@ -213,7 +220,7 @@ BALMLayout::AddArea(Row* row, Column* column, BView* content, /** * Adds a new area to the specification, automatically setting preferred size constraints. - * + * * @param left left border * @param top top border * @param right right border @@ -224,7 +231,7 @@ BALMLayout::AddArea(Row* row, Column* column, BView* content, Area* BALMLayout::AddArea(XTab* left, YTab* top, XTab* right, YTab* bottom, BView* content) -{ +{ InvalidateLayout(); if (content != NULL) View()->AddChild(content); @@ -238,11 +245,11 @@ BALMLayout::AddArea(XTab* left, YTab* top, XTab* right, YTab* bottom, /** * Adds a new area to the specification, automatically setting preferred size constraints. - * + * * @param row the row that defines the top and bottom border * @param column the column that defines the left and right border * @param content the control which is the area content - * @return the new area + * @return the new area */ Area* BALMLayout::AddArea(Row* row, Column* column, BView* content) @@ -260,7 +267,7 @@ BALMLayout::AddArea(Row* row, Column* column, BView* content) /** * Finds the area that contains the given control. - * + * * @param control the control to look for * @return the area that contains the control */ @@ -270,7 +277,7 @@ BALMLayout::AreaOf(BView* control) Area* area; for (int32 i = 0; i < fAreas->CountItems(); i++) { area = (Area*)fAreas->ItemAt(i); - if (area->Content() == control) + if (area->Content() == control) return area; } return NULL; @@ -516,45 +523,45 @@ BALMLayout::LayoutView() if (!fActivated) return; fActivated = false; - + if (View() == NULL) return; - + // reverse engineer a layout specification if none was given //~ if (this == NULL) RecoverLayout(View()); - + // if the layout engine is set to fit the GUI to the given size, // then the given size is enforced by setting absolute positions for Right and Bottom if (fLayoutStyle == FIT_TO_SIZE) { Right()->SetRange(View()->Bounds().Width(), View()->Bounds().Width()); Bottom()->SetRange(View()->Bounds().Height(), View()->Bounds().Height()); } - + SolveLayout(); - + // if new layout is infasible, use previous layout if (Result() == INFEASIBLE) { fActivated = true; // now layout calculation is allowed to run again return; } - + if (Result() != OPTIMAL) { Save("failed-layout.txt"); printf("Could not solve the layout specification (%d). ", Result()); printf("Saved specification in file failed-layout.txt\n"); } - - // change the size of the GUI according to the calculated size + + // change the size of the GUI according to the calculated size // if the layout engine was configured to do so if (fLayoutStyle == ADJUST_SIZE) { View()->ResizeTo(floor(Right()->Value() - Left()->Value() + 0.5), floor(Bottom()->Value() - Top()->Value() + 0.5)); } - + // set the calculated positions and sizes for every area for (int32 i = 0; i < Areas()->CountItems(); i++) ((Area*)Areas()->ItemAt(i))->DoLayout(); - + fActivated = true; } @@ -600,14 +607,14 @@ BALMLayout::CalculateMinSize() delete (Summand*)newObjFunction->ItemAt(0); delete (Summand*)newObjFunction->ItemAt(1); delete newObjFunction; - + if (Result() == UNBOUNDED) return Area::kMinSize; if (Result() != OPTIMAL) { Save("failed-layout.txt"); printf("Could not solve the layout specification (%d). Saved specification in file failed-layout.txt", Result()); } - + return BSize(Right()->Value() - Left()->Value(), Bottom()->Value() - Top()->Value()); } @@ -629,14 +636,14 @@ BALMLayout::CalculateMaxSize() delete (Summand*)newObjFunction->ItemAt(0); delete (Summand*)newObjFunction->ItemAt(1); delete newObjFunction; - + if (Result() == UNBOUNDED) return Area::kMaxSize; if (Result() != OPTIMAL) { Save("failed-layout.txt"); printf("Could not solve the layout specification (%d). Saved specification in file failed-layout.txt", Result()); } - + return BSize(Right()->Value() - Left()->Value(), Bottom()->Value() - Top()->Value()); } @@ -652,7 +659,7 @@ BALMLayout::CalculatePreferredSize() Save("failed-layout.txt"); printf("Could not solve the layout specification (%d). Saved specification in file failed-layout.txt", Result()); } - + return BSize(Right()->Value() - Left()->Value(), Bottom()->Value() - Top()->Value()); } diff --git a/src/libs/linprog/Constraint.cpp b/src/libs/linprog/Constraint.cpp index 03e80df639..3486d2cb9b 100644 --- a/src/libs/linprog/Constraint.cpp +++ b/src/libs/linprog/Constraint.cpp @@ -23,11 +23,11 @@ /** * Gets the index of the constraint. - * + * * @return the index of the constraint */ int32 -Constraint::Index() +Constraint::Index() const { int32 i = fLS->Constraints()->IndexOf(this); if (i == -1) { @@ -40,7 +40,7 @@ Constraint::Index() /** * Gets the left side of the constraint. - * + * * @return pointer to a BList containing the summands on the left side of the constraint */ BList* @@ -53,7 +53,7 @@ Constraint::LeftSide() /** * Sets the summands on the left side of the constraint. * The old summands are NOT deleted. - * + * * @param summands a BList containing the Summand objects that make up the new left side */ void @@ -81,22 +81,22 @@ Constraint::UpdateLeftSide() coeffs[i] = s->Coeff(); varIndexes[i] = s->Var()->Index(); } - + if (fDNegObjSummand != NULL && fOp != OperatorType(LE)) { varIndexes[i] = fDNegObjSummand->Var()->Index(); coeffs[i] = 1.0; i++; } - + if (fDPosObjSummand != NULL && fOp != OperatorType(GE)) { varIndexes[i] = fDPosObjSummand->Var()->Index(); coeffs[i] = -1.0; i++; } - + if (!set_rowex(fLS->fLP, this->Index(), i, &coeffs[0], &varIndexes[0])) STRACE(("Error in set_rowex.")); - + fLS->UpdateObjFunction(); fLS->RemovePresolved(); } @@ -117,7 +117,7 @@ Constraint::SetLeftSide(double coeff1, Variable* var1) void -Constraint::SetLeftSide(double coeff1, Variable* var1, +Constraint::SetLeftSide(double coeff1, Variable* var1, double coeff2, Variable* var2) { if (!fIsValid) @@ -131,9 +131,9 @@ Constraint::SetLeftSide(double coeff1, Variable* var1, UpdateLeftSide(); } - + void -Constraint::SetLeftSide(double coeff1, Variable* var1, +Constraint::SetLeftSide(double coeff1, Variable* var1, double coeff2, Variable* var2, double coeff3, Variable* var3) { @@ -172,7 +172,7 @@ Constraint::SetLeftSide(double coeff1, Variable* var1, /** * Gets the operator used for this constraint. - * + * * @return the operator used for this constraint */ OperatorType @@ -184,7 +184,7 @@ Constraint::Op() /** * Sets the operator used for this constraint. - * + * * @param value operator */ void @@ -199,14 +199,14 @@ Constraint::SetOp(OperatorType value) : (fOp == OperatorType(GE)) ? GE : LE))) STRACE(("Error in set_constr_type.")); - + fLS->RemovePresolved(); } - + /** * Gets the constant value that is on the right side of the operator. - * + * * @return the constant value that is on the right side of the operator */ double @@ -215,10 +215,10 @@ Constraint::RightSide() const return fRightSide; } - + /** * Sets the constant value that is on the right side of the operator. - * + * * @param value constant value that is on the right side of the operator */ void @@ -230,14 +230,14 @@ Constraint::SetRightSide(double value) fRightSide = value; if (!set_rh(fLS->fLP, Index(), fRightSide)) STRACE(("Error in set_rh.")); - + fLS->RemovePresolved(); } /** * Gets the penalty coefficient for negative deviations. - * + * * @return the penalty coefficient */ double @@ -252,7 +252,7 @@ Constraint::PenaltyNeg() const /** * The penalty coefficient for negative deviations from the soft constraint's exact solution,  * i.e. if the left side is too large. - * + * * @param value coefficient of negative penalty double */ void @@ -268,7 +268,7 @@ Constraint::SetPenaltyNeg(double value) fLS->UpdateObjFunction(); return; } - + if (value == fDNegObjSummand->Coeff()) return; @@ -279,7 +279,7 @@ Constraint::SetPenaltyNeg(double value) /** * Gets the penalty coefficient for positive deviations. - * + * * @return the penalty coefficient */ double @@ -294,7 +294,7 @@ Constraint::PenaltyPos() const /** * The penalty coefficient for negative deviations from the soft constraint's exact solution, * i.e. if the left side is too small. - * + * * @param value coefficient of positive penalty double */ void @@ -339,33 +339,32 @@ Constraint::WriteXML(BFile* file) { if (file->IsWritable() && fOwner == NULL) { char buffer[200]; - + file->Write(buffer, sprintf(buffer, "\t\n")); file->Write(buffer, sprintf(buffer, "\t\t\n")); - + Summand* summand; for (int32 i = 0; i < fLeftSide->CountItems(); i++) { summand = (Summand*)fLeftSide->ItemAt(i); file->Write(buffer, sprintf(buffer, "\t\t\t\n")); - file->Write(buffer, sprintf(buffer, "\t\t\t\t%f\n", + file->Write(buffer, sprintf(buffer, "\t\t\t\t%f\n", summand->Coeff())); - BString* varStr = summand->Var()->ToBString(); - file->Write(buffer, sprintf(buffer, "\t\t\t\t%s\n", - varStr->String())); - delete varStr; + BString varStr = *(summand->Var()); + file->Write(buffer, sprintf(buffer, "\t\t\t\t%s\n", + varStr.String())); file->Write(buffer, sprintf(buffer, "\t\t\t\n")); } - + file->Write(buffer, sprintf(buffer, "\t\t\n")); - - char* op; + + const char* op = "??"; if (fOp == OperatorType(EQ)) op = "EQ"; else if (fOp == OperatorType(LE)) op = "LE"; else if (fOp == OperatorType(GE)) op = "GE"; - + file->Write(buffer, sprintf(buffer, "\t\t%s\n", op)); file->Write(buffer, sprintf(buffer, "\t\t%f\n", fRightSide)); //~ file->Write(buffer, sprintf(buffer, "\t\t%s\n", PenaltyNeg())); @@ -377,7 +376,7 @@ Constraint::WriteXML(BFile* file) /** * Gets the slack variable for the negative variations. - * + * * @return the slack variable for the negative variations */ Variable* @@ -391,7 +390,7 @@ Constraint::DNeg() const /** * Gets the slack variable for the positive variations. - * + * * @return the slack variable for the positive variations */ Variable* @@ -452,56 +451,50 @@ Constraint::Invalidate() fDPosObjSummand = NULL; } - del_constraint(fLS->fLP, this->Index()); + del_constraint(fLS->fLP, this->Index()); fLS->Constraints()->RemoveItem(this); } -BString* -Constraint::ToBString() +Constraint::operator BString() const { - BString* str = new BString(); - *str << "Constraint "; + BString string; + GetString(string); + return string; +} + + +void +Constraint::GetString(BString& string) const +{ + string << "Constraint "; if (fLabel) - *str << fLabel; - *str << "(" << (int32)this << "): "; + string << fLabel; + string << "(" << (int32)this << "): "; if (fIsValid) { for (int i = 0; i < fLeftSide->CountItems(); i++) { Summand* s = static_cast(fLeftSide->ItemAt(i)); - *str << (float)s->Coeff() << "*"; - BString* varString = s->Var()->ToBString(); - *str << *varString << " "; - delete varString; + string << (float)s->Coeff() << "*"; + s->Var()->GetString(string); + string << " "; } - *str << ((fOp == OperatorType(EQ)) ? "== " + string << ((fOp == OperatorType(EQ)) ? "== " : (fOp == OperatorType(GE)) ? ">= " : (fOp == OperatorType(LE)) ? "<= " : "?? "); - *str << (float)fRightSide; - *str << " PenaltyPos=" << (float)PenaltyPos(); - *str << " PenaltyNeg=" << (float)PenaltyNeg(); + string << (float)fRightSide; + string << " PenaltyPos=" << (float)PenaltyPos(); + string << " PenaltyNeg=" << (float)PenaltyNeg(); } else - *str << "invalid"; - return str; -} - - -const char* -Constraint::ToString() -{ - BString* str = ToBString(); - char* result = (char*) malloc(str->Length() + 1); - str->CopyInto(result, 0, str->Length()); - delete str; - return result; + string << "invalid"; } /** * Constructor. */ -Constraint::Constraint(LinearSpec* ls, BList* summands, OperatorType op, +Constraint::Constraint(LinearSpec* ls, BList* summands, OperatorType op, double rightSide, double penaltyNeg, double penaltyPos) : fLS(ls), fLeftSide(summands), @@ -519,7 +512,7 @@ Constraint::Constraint(LinearSpec* ls, BList* summands, OperatorType op, coeffs[i] = s->Coeff(); varIndexes[i] = s->Var()->Index(); } - + if (penaltyNeg != INFINITY && fOp != OperatorType(LE)) { fDNegObjSummand = new Summand(penaltyNeg, new Variable(fLS)); @@ -530,7 +523,7 @@ Constraint::Constraint(LinearSpec* ls, BList* summands, OperatorType op, } else fDNegObjSummand = NULL; - + if (penaltyPos != INFINITY && fOp != OperatorType(GE)) { fDPosObjSummand = new Summand(penaltyPos, new Variable(fLS)); diff --git a/src/libs/linprog/LinearSpec.cpp b/src/libs/linprog/LinearSpec.cpp index 0f74b8b426..164b858eb0 100644 --- a/src/libs/linprog/LinearSpec.cpp +++ b/src/libs/linprog/LinearSpec.cpp @@ -31,7 +31,7 @@ LinearSpec::LinearSpec() /** * Destructor. - * Removes the specification and deletes all constraints, + * Removes the specification and deletes all constraints, * objective function summands and variables. */ LinearSpec::~LinearSpec() @@ -49,7 +49,7 @@ LinearSpec::~LinearSpec() /** * Adds a new variable to the specification. - * + * * @return the new variable */ Variable* @@ -61,7 +61,7 @@ LinearSpec::AddVariable() /** * Adds a new hard linear constraint to the specification. - * + * * @param coeffs the constraint's coefficients * @param vars the constraint's variables * @param op the constraint's operand @@ -70,7 +70,7 @@ LinearSpec::AddVariable() */ Constraint* LinearSpec::AddConstraint(BList* summands, OperatorType op, double rightSide) -{ +{ Constraint* c = new Constraint(this, summands, op, rightSide, INFINITY, INFINITY); RemovePresolved(); @@ -80,7 +80,7 @@ LinearSpec::AddConstraint(BList* summands, OperatorType op, double rightSide) /** * Adds a new hard linear constraint to the specification with a single summand. - * + * * @param coeff1 the constraint's first coefficient * @param var1 the constraint's first variable * @param op the constraint's operand @@ -88,9 +88,9 @@ LinearSpec::AddConstraint(BList* summands, OperatorType op, double rightSide) * @return the new constraint */ Constraint* -LinearSpec::AddConstraint(double coeff1, Variable* var1, +LinearSpec::AddConstraint(double coeff1, Variable* var1, OperatorType op, double rightSide) -{ +{ BList* summands = new BList(1); summands->AddItem(new Summand(coeff1, var1)); Constraint* c = new Constraint(this, summands, op, rightSide, @@ -102,7 +102,7 @@ LinearSpec::AddConstraint(double coeff1, Variable* var1, /** * Adds a new hard linear constraint to the specification with two summands. - * + * * @param coeff1 the constraint's first coefficient * @param var1 the constraint's first variable * @param coeff2 the constraint's second coefficient @@ -112,22 +112,22 @@ LinearSpec::AddConstraint(double coeff1, Variable* var1, * @return the new constraint */ Constraint* -LinearSpec::AddConstraint(double coeff1, Variable* var1, +LinearSpec::AddConstraint(double coeff1, Variable* var1, double coeff2, Variable* var2, OperatorType op, double rightSide) -{ +{ BList* summands = new BList(2); summands->AddItem(new Summand(coeff1, var1)); summands->AddItem(new Summand(coeff2, var2)); Constraint* c = new Constraint(this, summands, op, rightSide, INFINITY, INFINITY); RemovePresolved(); - return c; + return c; } /** * Adds a new hard linear constraint to the specification with three summands. - * + * * @param coeff1 the constraint's first coefficient * @param var1 the constraint's first variable * @param coeff2 the constraint's second coefficient @@ -139,10 +139,10 @@ LinearSpec::AddConstraint(double coeff1, Variable* var1, * @return the new constraint */ Constraint* -LinearSpec::AddConstraint(double coeff1, Variable* var1, - double coeff2, Variable* var2, double coeff3, Variable* var3, +LinearSpec::AddConstraint(double coeff1, Variable* var1, + double coeff2, Variable* var2, double coeff3, Variable* var3, OperatorType op, double rightSide) -{ +{ BList* summands = new BList(3); summands->AddItem(new Summand(coeff1, var1)); summands->AddItem(new Summand(coeff2, var2)); @@ -150,13 +150,13 @@ LinearSpec::AddConstraint(double coeff1, Variable* var1, Constraint* c = new Constraint(this, summands, op, rightSide, INFINITY, INFINITY); RemovePresolved(); - return c; + return c; } /** * Adds a new hard linear constraint to the specification with four summands. - * + * * @param coeff1 the constraint's first coefficient * @param var1 the constraint's first variable * @param coeff2 the constraint's second coefficient @@ -170,10 +170,10 @@ LinearSpec::AddConstraint(double coeff1, Variable* var1, * @return the new constraint */ Constraint* -LinearSpec::AddConstraint(double coeff1, Variable* var1, - double coeff2, Variable* var2, double coeff3, Variable* var3, +LinearSpec::AddConstraint(double coeff1, Variable* var1, + double coeff2, Variable* var2, double coeff3, Variable* var3, double coeff4, Variable* var4, OperatorType op, double rightSide) -{ +{ BList* summands = new BList(3); summands->AddItem(new Summand(coeff1, var1)); summands->AddItem(new Summand(coeff2, var2)); @@ -182,14 +182,14 @@ LinearSpec::AddConstraint(double coeff1, Variable* var1, Constraint* c = new Constraint(this, summands, op, rightSide, INFINITY, INFINITY); RemovePresolved(); - return c; + return c; } /** * Adds a new soft linear constraint to the specification. * i.e. a constraint that does not always have to be satisfied. - * + * * @param coeffs the constraint's coefficients * @param vars the constraint's variables * @param op the constraint's operand @@ -198,10 +198,10 @@ LinearSpec::AddConstraint(double coeff1, Variable* var1, * @param penaltyPos the coefficient penalizing positive deviations from the exact solution */ Constraint* -LinearSpec::AddConstraint(BList* summands, OperatorType op, +LinearSpec::AddConstraint(BList* summands, OperatorType op, double rightSide, double penaltyNeg, double penaltyPos) -{ - Constraint* c = new Constraint(this, summands, op, rightSide, +{ + Constraint* c = new Constraint(this, summands, op, rightSide, penaltyNeg, penaltyPos); RemovePresolved(); return c; @@ -210,7 +210,7 @@ LinearSpec::AddConstraint(BList* summands, OperatorType op, /** * Adds a new soft linear constraint to the specification with a single summand. - * + * * @param coeff1 the constraint's first coefficient * @param var1 the constraint's first variable * @param op the constraint's operand @@ -219,9 +219,9 @@ LinearSpec::AddConstraint(BList* summands, OperatorType op, * @param penaltyPos the coefficient penalizing positive deviations from the exact solution */ Constraint* -LinearSpec::AddConstraint(double coeff1, Variable* var1, +LinearSpec::AddConstraint(double coeff1, Variable* var1, OperatorType op, double rightSide, double penaltyNeg, double penaltyPos) -{ +{ BList* summands = new BList(1); summands->AddItem(new Summand(coeff1, var1)); Constraint* c = new Constraint(this, summands, op, rightSide, @@ -233,7 +233,7 @@ LinearSpec::AddConstraint(double coeff1, Variable* var1, /** * Adds a new soft linear constraint to the specification with two summands. - * + * * @param coeff1 the constraint's first coefficient * @param var1 the constraint's first variable * @param coeff2 the constraint's second coefficient @@ -244,10 +244,10 @@ LinearSpec::AddConstraint(double coeff1, Variable* var1, * @param penaltyPos the coefficient penalizing positive deviations from the exact solution */ Constraint* -LinearSpec::AddConstraint(double coeff1, Variable* var1, - double coeff2, Variable* var2, OperatorType op, double rightSide, +LinearSpec::AddConstraint(double coeff1, Variable* var1, + double coeff2, Variable* var2, OperatorType op, double rightSide, double penaltyNeg, double penaltyPos) -{ +{ BList* summands = new BList(2); summands->AddItem(new Summand(coeff1, var1)); summands->AddItem(new Summand(coeff2, var2)); @@ -260,7 +260,7 @@ LinearSpec::AddConstraint(double coeff1, Variable* var1, /** * Adds a new soft linear constraint to the specification with three summands. - * + * * @param coeff1 the constraint's first coefficient * @param var1 the constraint's first variable * @param coeff2 the constraint's second coefficient @@ -273,8 +273,8 @@ LinearSpec::AddConstraint(double coeff1, Variable* var1, * @param penaltyPos the coefficient penalizing positive deviations from the exact solution */ Constraint* -LinearSpec::AddConstraint(double coeff1, Variable* var1, - double coeff2, Variable* var2, double coeff3, Variable* var3, +LinearSpec::AddConstraint(double coeff1, Variable* var1, + double coeff2, Variable* var2, double coeff3, Variable* var3, OperatorType op, double rightSide, double penaltyNeg, double penaltyPos) { BList* summands = new BList(2); @@ -290,7 +290,7 @@ LinearSpec::AddConstraint(double coeff1, Variable* var1, /** * Adds a new soft linear constraint to the specification with four summands. - * + * * @param coeff1 the constraint's first coefficient * @param var1 the constraint's first variable * @param coeff2 the constraint's second coefficient @@ -305,11 +305,11 @@ LinearSpec::AddConstraint(double coeff1, Variable* var1, * @param penaltyPos the coefficient penalizing positive deviations from the exact solution */ Constraint* -LinearSpec::AddConstraint(double coeff1, Variable* var1, - double coeff2, Variable* var2, double coeff3, Variable* var3, - double coeff4, Variable* var4, OperatorType op, double rightSide, +LinearSpec::AddConstraint(double coeff1, Variable* var1, + double coeff2, Variable* var2, double coeff3, Variable* var3, + double coeff4, Variable* var4, OperatorType op, double rightSide, double penaltyNeg, double penaltyPos) -{ +{ BList* summands = new BList(2); summands->AddItem(new Summand(coeff1, var1)); summands->AddItem(new Summand(coeff2, var2)); @@ -324,7 +324,7 @@ LinearSpec::AddConstraint(double coeff1, Variable* var1, /** * Adds a new penalty function to the specification. - * + * * @param var the penalty function's variable * @param xs the penalty function's sampling points * @param gs the penalty function's gradients @@ -339,7 +339,7 @@ LinearSpec::AddPenaltyFunction(Variable* var, BList* xs, BList* gs) /** * Gets the objective function. - * + * * @return BList containing the objective function's summands */ BList* @@ -352,7 +352,7 @@ LinearSpec::ObjFunction() /** * Sets a new objective function. * The old objective function summands are NOT deleted. - * + * * @param summands BList containing the objective function's summands */ void @@ -379,17 +379,17 @@ LinearSpec::UpdateObjFunction() coeffs[i] = current->Coeff(); varIndexes[i] = current->Var()->Index(); } - + if (!set_obj_fnex(fLP, size, &coeffs[0], &varIndexes[0])) printf("Error in set_obj_fnex."); - + RemovePresolved(); } /** * Remove a cached presolved model, if existent. - * This is automatically done each time after the model has been changed, + * This is automatically done each time after the model has been changed, * to avoid an old cached presolved model getting out of sync. */ void @@ -403,11 +403,11 @@ LinearSpec::RemovePresolved() /** - * Creates and caches a simplified version of the linear programming problem, - * where redundant rows, columns and constraints are removed, + * Creates and caches a simplified version of the linear programming problem, + * where redundant rows, columns and constraints are removed, * if it has not been created before. * Then, the simplified problem is solved. - * + * * @return the result of the solving attempt */ ResultType @@ -415,28 +415,28 @@ LinearSpec::Presolve() { bigtime_t start, end; start = system_time(); - + if (fLpPresolved == NULL) { fLpPresolved = copy_lp(fLP); set_presolve(fLpPresolved, PRESOLVE_ROWS | PRESOLVE_COLS | PRESOLVE_LINDEP, get_presolveloops(fLpPresolved)); } - + fResult = (ResultType)solve(fLpPresolved); fObjectiveValue = get_objective(fLpPresolved); - + if (fResult == OPTIMAL) { int32 size = fVariables->CountItems(); for (int32 i = 0; i < size; i++) { Variable* current = (Variable*)fVariables->ItemAt(i); - current->SetValue(get_var_primalresult(fLpPresolved, + current->SetValue(get_var_primalresult(fLpPresolved, get_Norig_rows(fLpPresolved) + current->Index())); } } - + end = system_time(); fSolvingTime = (end - start) / 1000.0; - + return fResult; } @@ -444,7 +444,7 @@ LinearSpec::Presolve() /** * Tries to solve the linear programming problem. * If a cached simplified version of the problem exists, it is used instead. - * + * * @return the result of the solving attempt */ ResultType @@ -452,29 +452,29 @@ LinearSpec::Solve() { if (fLpPresolved != NULL) return Presolve(); - + bigtime_t start, end; start = system_time(); - + fResult = (ResultType)solve(fLP); fObjectiveValue = get_objective(fLP); - + if (fResult == OPTIMAL) { int32 size = fVariables->CountItems(); double x[size]; if (!get_variables(fLP, &x[0])) printf("Error in get_variables."); - + int32 i = 0; while (i < size) { ((Variable*)fVariables->ItemAt(i))->SetValue(x[i]); i++; } } - + end = system_time(); fSolvingTime = (end - start) / 1000.0; - + return fResult; } @@ -482,13 +482,14 @@ LinearSpec::Solve() /** * Writes the specification into a text file. * The file will be overwritten if it exists. - * + * * @param fname the file name */ void -LinearSpec::Save(char* fname) +LinearSpec::Save(const char* fileName) { - write_lp(fLP, fname); + // TODO: Constness should be fixed in liblpsolve API. + write_lp(fLP, const_cast(fileName)); } @@ -507,7 +508,7 @@ LinearSpec::CountColumns() const /** * Gets the current optimization. * The default is minimization. - * + * * @return the current optimization */ OptimizationType @@ -520,7 +521,7 @@ LinearSpec::Optimization() const /** * Sets whether the solver should minimize or maximize the objective function. * The default is minimization. - * + * * @param optimization the optimization type */ void @@ -536,7 +537,7 @@ LinearSpec::SetOptimization(OptimizationType value) /** * Gets the the variables. - * + * * @return the variables */ BList* @@ -548,7 +549,7 @@ LinearSpec::Variables() const /** * Gets the constraints. - * + * * @return the constraints */ BList* @@ -560,7 +561,7 @@ LinearSpec::Constraints() const /** * Gets the result type. - * + * * @return the result type */ ResultType @@ -572,7 +573,7 @@ LinearSpec::Result() const /** * Gets the objective value. - * + * * @return the objective value */ double @@ -584,7 +585,7 @@ LinearSpec::ObjectiveValue() const /** * Gets the solving time. - * + * * @return the solving time */ double @@ -594,54 +595,47 @@ LinearSpec::SolvingTime() const } -BString* -LinearSpec::ToBString() +LinearSpec::operator BString() const { - BString* str = new BString(); - *str << "LinearSpec " << (int32)this << ":\n"; + BString string; + GetString(string); + return string; +} + + +void +LinearSpec::GetString(BString& string) const +{ + string << "LinearSpec " << (int32)this << ":\n"; for (int i = 0; i < fVariables->CountItems(); i++) { Variable* variable = static_cast(fVariables->ItemAt(i)); - BString* vStr = variable->ToBString(); - *str << *vStr << "=" << (float)variable->Value() << " "; - delete vStr; + variable->GetString(string); + string << "=" << (float)variable->Value() << " "; } - *str << "\n"; + string << "\n"; for (int i = 0; i < fConstraints->CountItems(); i++) { - Constraint* c = static_cast(fConstraints->ItemAt(i)); - BString* cStr = c->ToBString(); - *str << i << ": " << *cStr; - delete cStr; - *str << "\n"; + Constraint* c = static_cast(fConstraints->ItemAt(i)); + string << i << ": "; + c->GetString(string); + string << "\n"; } - *str << "Result="; + string << "Result="; if (fResult==-1) - *str << "ERROR"; + string << "ERROR"; else if (fResult==0) - *str << "OPTIMAL"; + string << "OPTIMAL"; else if (fResult==1) - *str << "SUBOPTIMAL"; + string << "SUBOPTIMAL"; else if (fResult==2) - *str << "INFEASIBLE"; + string << "INFEASIBLE"; else if (fResult==3) - *str << "UNBOUNDED"; + string << "UNBOUNDED"; else if (fResult==4) - *str << "DEGENERATE"; + string << "DEGENERATE"; else if (fResult==5) - *str << "NUMFAILURE"; + string << "NUMFAILURE"; else - *str << fResult; - *str << " SolvingTime=" << (float)fSolvingTime << "ms"; - return str; -} - - -const char* -LinearSpec::ToString() -{ - BString* str = ToBString(); - char* result = (char*) malloc(str->Length() + 1); - str->CopyInto(result, 0, str->Length()); - delete str; - return result; + string << fResult; + string << " SolvingTime=" << (float)fSolvingTime << "ms"; } diff --git a/src/libs/linprog/Variable.cpp b/src/libs/linprog/Variable.cpp index 16457b75d4..7cc51a8cfb 100644 --- a/src/libs/linprog/Variable.cpp +++ b/src/libs/linprog/Variable.cpp @@ -26,11 +26,11 @@ /** * Gets index of the variable. - * + * * @return the index of the variable */ int32 -Variable::Index() +Variable::Index() const { int32 i = fLS->Variables()->IndexOf(this); if (i == -1) { @@ -43,7 +43,7 @@ Variable::Index() /** * Gets the current linear specification. - * + * * @return the current linear specification */ LinearSpec* @@ -55,7 +55,7 @@ Variable::LS() const /** * Gets the value. - * + * * @return the value */ double @@ -67,7 +67,7 @@ Variable::Value() const /** * Sets the value. - * + * * @param value the value */ void @@ -79,7 +79,7 @@ Variable::SetValue(double value) /** * Gets the minimum value of the variable. - * + * * @return the minimum value of variable */ double @@ -91,7 +91,7 @@ Variable::Min() const /** * Sets the minimum value of the variable. - * + * * @param min minimum value */ void @@ -107,7 +107,7 @@ Variable::SetMin(double min) /** * Gets the maximum value of the variable. - * + * * @return the maximum value of variable */ double @@ -119,7 +119,7 @@ Variable::Max() const /** * Sets the maximum value of the variable. - * + * * @param max maximum value */ void @@ -135,7 +135,7 @@ Variable::SetMax(double max) /** * Sets the minimum and maximum values of the variable. - * + * * @param min minimum value * @param max maximum value */ @@ -166,45 +166,40 @@ Variable::SetLabel(const char* label) } -/** - * Returns index of the variable as String. - * E.g. "Var2" - * - * @return the String index of the variable - */ -BString* -Variable::ToBString() +Variable::operator BString() const { - BString* str = new BString(); - if (fLabel) { - *str << fLabel; - if (!fIsValid) - *str << "(invalid)"; - } else { - *str << "Var"; - if (!fIsValid) - *str << "(invalid," << (int32)this << ")"; - else - *str << Index(); - } - return str; + BString string; + GetString(string); + return string; } -const char* -Variable::ToString() +/** + * Returns index of the variable as String. + * E.g. "Var2" + * + * @return the String index of the variable + */ +void +Variable::GetString(BString& string) const { - BString* str = ToBString(); - char* result = (char*) malloc(str->Length() + 1); - str->CopyInto(result, 0, str->Length()); - delete str; - return result; + if (fLabel) { + string << fLabel; + if (!fIsValid) + string << "(invalid)"; + } else { + string << "Var"; + if (!fIsValid) + string << "(invalid," << (int32)this << ")"; + else + string << Index(); + } } /** * Adds a constraint that sets this variable equal to the given one. - * + * * @param var variable that should have the same value * @return the new equality constraint */ @@ -220,7 +215,7 @@ Variable::IsEqual(Variable* var) /** * Adds a constraint that sets this variable smaller or equal to the given one. - * + * * @param var variable that should have a larger or equal value * @return the new constraint */ @@ -236,7 +231,7 @@ Variable::IsSmallerOrEqual(Variable* var) /** * Adds a constraint that sets this variable greater or equal to the given one. - * + * * @param var variable that should have a smaller or equal value * @return the new constraint */ @@ -341,7 +336,7 @@ Variable::Variable(LinearSpec* ls) fIsValid(true) { fLS->Variables()->AddItem(this); - + if (fLS->Variables()->CountItems() > fLS->CountColumns()) { double d = 0; int i = 0;