|
6 | 6 | import matplotlib.pyplot as plt
|
7 | 7 |
|
8 | 8 | import interior_point
|
9 |
| -from simplex import simplex |
| 9 | +import simplex |
10 | 10 |
|
11 | 11 |
|
12 | 12 | GREATER_EQUAL = -1
|
@@ -105,6 +105,10 @@ def copy(self) -> "LinearProgrammingProblem":
|
105 | 105 | lp.is_maximizing = self.is_maximizing
|
106 | 106 | lp.objective = self.objective.copy()
|
107 | 107 |
|
| 108 | + lp._A_updated = False |
| 109 | + lp._b_updated = False |
| 110 | + lp._c_updated = False |
| 111 | + |
108 | 112 | return lp
|
109 | 113 |
|
110 | 114 |
|
@@ -220,22 +224,54 @@ def compute_feasible_basis(self):
|
220 | 224 | def is_feasible(lp: "LinearProgrammingProblem", x: np.array, tol=10e-5) -> bool:
|
221 | 225 | return all(np.isclose(lp.A @ x, lp.b, atol=tol))
|
222 | 226 |
|
223 |
| - def solve(self, method=SOLVER_SIMPLEX): |
224 |
| - if (method == SOLVER_SIMPLEX): |
225 |
| - lp_slacked = self.slacken_problem() |
| 227 | + def solve(self, method=None): |
| 228 | + lp_slacked = self.slacken_problem() |
| 229 | + # Decide which solver to use |
| 230 | + # Simplex? |
| 231 | + if (method == None): |
| 232 | + x_zero = simplex.zero_point_solution(lp_slacked.A, lp_slacked.b, lp_slacked.c) |
| 233 | + if (simplex.is_feasible(lp_slacked.A, x_zero, lp_slacked.b)): |
| 234 | + # If zero point solution is feasible, use simplex |
| 235 | + method = SOLVER_SIMPLEX |
| 236 | + |
| 237 | + if (method == None): |
| 238 | + # Solve using interior point algorithm |
| 239 | + x_ones = np.ones(len(self.variables)) |
| 240 | + x_initial = np.hstack((x_ones, self.b - (self.A @ x_ones))) |
| 241 | + if (self.is_feasible(self, x_initial)): |
| 242 | + # IPA is feasible |
| 243 | + method = SOLVER_INTERIOR_POINT_METHOD |
226 | 244 |
|
227 |
| - x_sol = simplex(lp_slacked.A, lp_slacked.b, lp_slacked.c, lp_slacked.vars_slack_amount) |
| 245 | + |
| 246 | + x_sol = None |
| 247 | + iterations_count = None |
| 248 | + |
| 249 | + if (method == SOLVER_SIMPLEX): |
| 250 | + # Solve using simplex |
| 251 | + x_sol, iterations_count = simplex.simplex(lp_slacked.A, lp_slacked.b, lp_slacked.c, lp_slacked.vars_slack_amount) |
228 | 252 |
|
229 | 253 | # Cut slack variables
|
230 | 254 | x_sol = x_sol[:lp_slacked.c.size - lp_slacked.vars_slack_amount]
|
231 |
| - print(x_sol) |
232 | 255 |
|
233 |
| - return x_sol |
| 256 | + elif (method == SOLVER_INTERIOR_POINT_METHOD): |
| 257 | + # Solve using interior point algorithm |
| 258 | + x_ones = np.ones(len(self.variables)) |
| 259 | + x_initial = np.hstack((x_ones, self.b - (self.A @ x_ones))) |
| 260 | + |
| 261 | + #x_initial = np.array([1 for _ in range(len(lp_slacked.variables))]) |
| 262 | + x_sol, path, iterations_count = interior_point.interior_point(lp_slacked.A, lp_slacked.c, x_initial) |
| 263 | + |
| 264 | + # Cut slack variables |
| 265 | + x_sol = x_sol[:lp_slacked.c.size - lp_slacked.vars_slack_amount] |
| 266 | + |
| 267 | + else: |
| 268 | + print("No solution found") |
| 269 | + return |
234 | 270 |
|
235 |
| - if (method == SOLVER_INTERIOR_POINT_METHOD): |
236 |
| - pass |
| 271 | + print(f"Solving using {method}") |
| 272 | + print(f"Solved in {iterations_count} iterations") |
237 | 273 |
|
238 |
| - return "x" |
| 274 | + return x_sol |
239 | 275 |
|
240 | 276 |
|
241 | 277 | def plot_solution_path(self):
|
|
0 commit comments