[MATLAB] Minimum dla ograniczeń równościowych (linprog)

0

Wszystkie ograniczenia równościowe są następujące:

x1 + x2 + x3 + x4 = 1600 
30x1 + 60x2 + 70x3 + 80x4 = 62.5*(x1 + x2 + x3 + x4) 
30x1 + 40x2 + 0x3 + 20x4 = 18.75*(x1 + x2 + x3 + x4) 
Cel: 45x1 + 54x2 + 42x3 + 36x4 -> min.

Przeniosłem wszystko na lewą stronę równania i skorzystałem z linprog, gdzie:

 
Aeq = [1 1 1 1; -32.5 -2.5 7.5 17.5; 11.25 21.25 -18.75 1.25]; 
beq = [1600; 0; 0]; 
f = [45 54 42 36]; 
linprog(f, [], [], Aeq, beq) 

Niestety, zamiast otrzymać wektor jednostek produktów (składajacy się na sumę 1600), otrzymałem następujący błąd:

 
Exiting: One or more of the residuals, duality gap, or total relative error 
 has grown 100000 times greater than its minimum value so far: 
         the dual appears to be infeasible (and the primal unbounded).      
         (The primal residual < OptimalityTolerance=1.00e-08.) 
 
ans = 
 
   1.0e+28 * 
 
    0.5520 
   -1.0120 
   -0.7360 
    1.1960 

Mógłby ktoś powiedzieć, co tutaj poprawić? Wydaje mi się dosłownie wszystko dobrze (ewentualnie źle zapisałem ograniczenia równościowe, w razie potrzeby mogę podać treść zadania, ale nawet jeśli, powinien być zwrócony w miarę sensowny wynik).

1
darkrat napisał(a):

Aeq = [1 1 1 1; -32.5 -2.5 7.5 17.5; 11.25 21.25 -18.75 1.25];
beq = [1600; 0; 0];
f = [45 54 42 36];
linprog(f, [], [], Aeq, beq)

Spróbuj stosować spójną konwencję budowania wektorów beq i f. Czyli, buduj konsekwentnie wektory wierszowe albo kolumnowe. Teraz beq masz kolumnowy, a f wierszowy.

0

Ustawiłem najpierw ze średnikami, potem oba bez, niestety nie podziałało (co więcej, w poprzednim zadaniu, które rozwiązywaliśmy, był dobry rezultat mimo tej niespójności).

1
darkrat napisał(a):

Ustawiłem najpierw ze średnikami, potem oba bez, niestety nie podziałało (co więcej, w poprzednim zadaniu, które rozwiązywaliśmy, był dobry rezultat mimo tej niespójności).

Nie mam Matlaba, więc zrobiłem Twoje zadanie w Octave przy użyciu glpk (Octave nie ma toolboxa do optymalizacji) i mi ładnie wszystko policzyło:

>> Aeq = [1 1 1 1; -32.5 -2.5 7.5 17.5; 11.25 21.25 -18.75 1.25];
>> Aeq
Aeq =

    1.0000    1.0000    1.0000    1.0000
  -32.5000   -2.5000    7.5000   17.5000
   11.2500   21.2500  -18.7500    1.2500

>> beq = [1600; 0; 0];
>> beq
beq =

   1600
      0
      0

>> f = [45 54 42 36];
>> f
f =

   45   54   42   36

>> f=f'
f =

   45
   54
   42
   36

>> answer = glpk(f,Aeq,beq)
answer =

   490.90909
     0.00000
   345.45455
   763.63636

>> Aeq*answer
ans =

  1.6000e+003
  1.8190e-012
  9.0949e-013

>> f'*answer
ans =   6.4091e+004
>>

Podejrzewam, że robisz jakiś błąd. Zawsze możesz przerzucić się na Octave, jest darmowy.

0

A jednak Octave pobierać nie trzeba. Dla potomnych: dla podobnych warunków, jak spodziewamy się dodatnich wyników, może okazać się konieczne zaznaczenie tegoż (aczkolwiek nie musi, jak w przykładzie z poprzedniego tematu).

Example: To specify that all x-components are positive, lb = zeros(size(f))

Zatem zamiast:

linprog(f, [], [], Aeq, beq) 

tworzymy:

lb = zeros(size(f));
linprog(f, [], [], Aeq, beq, lb) 

I otrzymamy:

Optimization terminated.

ans =

  490.9091
    0.0000
  345.4545
  763.6364

1 użytkowników online, w tym zalogowanych: 0, gości: 1