@@ -75,7 +75,8 @@ class Equation {
7575public:
7676 virtual ~Equation () = default ;
7777
78- virtual double Value (const MixedStrategyProfile<double > &p_profile, double p_lambda) const = 0;
78+ virtual double Value (const MixedStrategyProfile<double > &p_profile,
79+ const Vector<double > &p_strategyValues, double p_lambda) const = 0;
7980 virtual void Gradient (const MixedStrategyProfile<double > &p_profile, double p_lambda,
8081 Vector<double > &p_gradient) const = 0;
8182};
@@ -92,6 +93,7 @@ class EquationSystem {
9293 std::vector<std::shared_ptr<Equation>> m_equations;
9394 const Game &m_game;
9495 mutable MixedStrategyProfile<double > m_profile;
96+ mutable Vector<double > m_strategyValues;
9597};
9698
9799class SumToOneEquation final : public Equation {
@@ -116,17 +118,18 @@ class SumToOneEquation final : public Equation {
116118 }
117119
118120 ~SumToOneEquation () override = default ;
119- double Value (const MixedStrategyProfile<double > &p_profile, double p_lambda) const override ;
121+ double Value (const MixedStrategyProfile<double > &p_profile,
122+ const Vector<double > &p_strategyValues, double p_lambda) const override ;
120123 void Gradient (const MixedStrategyProfile<double > &p_profile, double p_lambda,
121124 Vector<double > &p_gradient) const override ;
122125};
123126
124127double SumToOneEquation::Value (const MixedStrategyProfile<double > &p_profile,
125- double p_lambda) const
128+ const Vector< double > &p_strategyValues, double p_lambda) const
126129{
127130 double value = -1.0 ;
128- for (const auto &strategy : m_player-> GetStrategies () ) {
129- value += p_profile[strategy ];
131+ for (int col = m_firstIndex; col < m_lastIndex; col++ ) {
132+ value += p_profile[col ];
130133 }
131134 return value;
132135}
@@ -135,34 +138,46 @@ void SumToOneEquation::Gradient(const MixedStrategyProfile<double> &p_profile, d
135138 Vector<double > &p_gradient) const
136139{
137140 p_gradient = 0.0 ;
138- int col = m_firstIndex;
139- for (const auto &strategy : m_player->GetStrategies ()) {
140- p_gradient[col++] = p_profile[strategy];
141+ for (int col = m_firstIndex; col < m_lastIndex; col++) {
142+ p_gradient[col] = p_profile[col];
141143 }
142144}
143145
144146class RatioEquation final : public Equation {
145147 Game m_game;
146148 GamePlayer m_player;
147149 GameStrategy m_strategy, m_refStrategy;
150+ int m_strategyIndex{0 }, m_refStrategyIndex{0 };
148151
149152public:
150153 RatioEquation (const GameStrategy &p_strategy, const GameStrategy &p_refStrategy)
151154 : m_game(p_strategy->GetGame ()), m_player(p_strategy->GetPlayer ()), m_strategy(p_strategy),
152155 m_refStrategy(p_refStrategy)
153156 {
157+ int col = 1 ;
158+ for (const auto &strategy : m_game->GetStrategies ()) {
159+ if (strategy == p_strategy) {
160+ m_strategyIndex = col;
161+ }
162+ else if (strategy == p_refStrategy) {
163+ m_refStrategyIndex = col;
164+ }
165+ col++;
166+ }
154167 }
155168
156169 ~RatioEquation () override = default ;
157- double Value (const MixedStrategyProfile<double > &p_profile, double p_lambda) const override ;
170+ double Value (const MixedStrategyProfile<double > &p_profile,
171+ const Vector<double > &p_strategyValues, double p_lambda) const override ;
158172 void Gradient (const MixedStrategyProfile<double > &p_profile, double p_lambda,
159173 Vector<double > &p_gradient) const override ;
160174};
161175
162- double RatioEquation::Value (const MixedStrategyProfile<double > &p_profile, double p_lambda) const
176+ double RatioEquation::Value (const MixedStrategyProfile<double > &p_profile,
177+ const Vector<double > &p_strategyValues, double p_lambda) const
163178{
164- return (std::log (p_profile[m_strategy ]) - std::log (p_profile[m_refStrategy ]) -
165- p_lambda * (p_profile. GetPayoff (m_strategy) - p_profile. GetPayoff (m_refStrategy) ));
179+ return (std::log (p_profile[m_strategyIndex ]) - std::log (p_profile[m_refStrategyIndex ]) -
180+ p_lambda * (p_strategyValues[m_strategyIndex] - p_strategyValues[m_refStrategyIndex] ));
166181}
167182
168183void RatioEquation::Gradient (const MixedStrategyProfile<double > &p_profile, double p_lambda,
@@ -193,7 +208,8 @@ void RatioEquation::Gradient(const MixedStrategyProfile<double> &p_profile, doub
193208}
194209
195210EquationSystem::EquationSystem (const Game &p_game)
196- : m_game(p_game), m_profile(p_game->NewMixedStrategyProfile (0.0 ))
211+ : m_game(p_game), m_profile(p_game->NewMixedStrategyProfile (0.0 )),
212+ m_strategyValues(m_profile.MixedProfileLength())
197213{
198214 for (const auto &player : m_game->GetPlayers ()) {
199215 m_equations.push_back (std::make_shared<SumToOneEquation>(player));
@@ -208,8 +224,12 @@ void EquationSystem::GetValue(const Vector<double> &p_point, Vector<double> &p_l
208224{
209225 PointToProfile (m_profile, p_point);
210226 const double lambda = p_point.back ();
227+ int col = 1 ;
228+ for (const auto &strategy : m_game->GetStrategies ()) {
229+ m_strategyValues[col++] = m_profile.GetPayoff (strategy);
230+ }
211231 std::transform (m_equations.begin (), m_equations.end (), p_lhs.begin (),
212- [this , lambda](auto e) { return e->Value (m_profile, lambda); });
232+ [this , lambda](auto e) { return e->Value (m_profile, m_strategyValues, lambda); });
213233}
214234
215235void EquationSystem::GetJacobian (const Vector<double > &p_point, Matrix<double > &p_matrix) const
0 commit comments