JWally / jsLPSolver

Simple OOP javaScript library to solve linear programs, and mixed integer linear programs
The Unlicense
420 stars 69 forks source link

Constraints for sum and relations of the variables #59

Closed PaulRBerg closed 7 years ago

PaulRBerg commented 7 years ago

Hello! Firstly, thank you for the library, it's just amazing.

I'm somehow new to Javascript and of course to jsLPSolver and I have to solve the following equation:

    Objective: Maximize r17

    Variables:
    - Floats: q7, q8, q9, q10, q11, q12, q13, q14, q15, q16, q17
    - Floats: r7, r8, r9, r10, r11, r12, r13, r14, r16, r16, r17

    Relations:
    - q7 +q8 +q9 +q10 + q11 + q12 + q13 + q14 + q15 + q16 = q17
    - r7 +r8 +r9 +r10 + r11 + r12 + r13 + r14 + r15 + r16 = r17
    - r7 = q7 / 0.50
    - r8 = q8 / 0.75
    - r9 = q9 / 0.88
    - r10 = q10 / 1.00
    - r11 = q11 / 1.13
    - r12 = q12 / 1.18
    - r13 = q13 / 1.76
    - r14 = q14 / 2.11
    - r15 = q15 / 2.33
    - r16 = q16 / 2.50

    Constraints:
    - 1000 <= q7 <= 17500
    - 2000 <= q8 <= 6300
    - 5000 <= q9 <= 19292
    - 1200 <= q10 <= 29820
    - 100 <= q11 <=2887.50
    - 700 <= q12 <= 20825
    - 300 <= q13 <= 9481.50
    - 150 <= q14 <= 5764.50,
    - 1200 <= q15 <= 48594,
    - 300 <= q16 <= 12600 
    - 60500 <= q17 <= 60500

Basically, I don't have any idea right now how could I plug in these rules into the library's model. Like the relations or the sum constraints?

PaulRBerg commented 7 years ago

I'll close the issue as I sorted it out myself using LP arrays.

I've taken a thorough look here and managed to solve my equation. Apparently, division is not allowed, so I converted my division relationships into coefficients like this:

a =  b / c is the equivalent of a = b * (1 / c)

And thus I had float values such as 0.4 for 2.5 (1/2.5=0.4). Unfortunately, the issues were still not gone, as apparently you can't have floats in lpsolve (take a look). So I multiplied the coefficients with 100 and we can safely do that all the time because lpsolve scales it automatically.

I kept playing with my equation and realised the results are starting to have the desired shape, but my q's still could have values of 0. Wonder why? Apparently, jsLPSolver can't parse a multi-comparison restriction, such as 1000 <= q7 <= 17500. I had to split that into:

q7 >= 1000
q7 <= 17500

@JWally Thanks again for this library, but, if you're open to suggestions, I would recommend explicitly marking these restrictions on the first page (no division, no floats, no multi-comparison etc). It would help a lot people like me which had to solve a complex linear equation.

Finally, the solution:

var model = [
          "max: 200 q7 + 134 q8 + 114 q9 + 100 q10 + 88 q11 + 85 q12 + 57 q13 + 47 q14 + 43 q15 + 40 q16",
          "q7 >= 1000", "q7 <= 17500",
          "q8 >= 2000", "q8 <= 6300",
          "q9 >= 5000", "q9 <= 19292",
          "q10 >= 1200", "q10 <= 29820",
          "q11 >= 100", "q11 <=2887",
          "q12 >= 700", "q12 <= 20825",
          "q13 >= 300", "q13 <= 9481",
          "q14 >= 150", "q14 <= 5764",
          "q15 >= 1200", "q15 <= 48594",
          "q16 >= 300", "q16 <= 12600",
          "sum: q7 + q8 + q9 + q10 + q11 + q12 + q13 + q14 + q15 + q16 = 60500",
          "int q7, q8, q9, q10, q11, q12, q13, q14, q15, q16"
        ];
apolinario commented 3 years ago

How do you run an LP array instead of the object with jsLPSolver?