Как условное суммирование возможно в Cplex? как суффиксы в Excel?

Я хочу суммировать все использованные ресурсы по времени в моей модели (это модель rcpsp), как я могу сделать это в CPLEX? сначала я написал это:

forall(k in K)
  forall(t in 1..f[nAct])
    sum(i in I:f[i]-d[i]<=t-1 && t<=f[i]) r[i,k] <= aR[k]; 

(примечание: K - это диапазон ресурсов, nAct - количество действий, f[i] - массив dvar и указывает время окончания действия i, d[i] - продолжительность i,r[i,k] - требуемый ресурс. k для деятельности i и aR[k] доступны ресурсы k.)

Проблема в том, что cplex не принимает переменную решения в состоянии суммы. Я изменил это на:

forall(k in K)
  forall(t in 1..f[nAct])
    sum(i in I) (f[i]-d[i]<=t-1 && t<=f[i])*r[i,k] <= aR[k]; 

Но это не сработало. после запуска он сделал истинные ограничения в обозревателе задач (я не знаю почему) и сделал это ограничение неэффективным.

Есть идеи как это исправить?

2 ответа

Есть несколько способов поместить вашу проблему в целочисленную среду программирования. На эту тему написаны книги. Я думаю, что это самая простая формулировка.

Я предполагаю, что в вашей задаче r [i, k] и d [i] известны и что временной горизонт разбит на дискретные периоды времени.

  • на [i, t] указывает, что активность i активна в момент времени t
  • start [i, t] индикатор того, что активность i начинается в начале периода t
  • end [i, t] индикатор того, что действие i завершается в конце периода t

Таким образом, в [i, t] заменяется условие f[i]-d[i]<=t-1 && t<=f[i])*r[i,k] Ваше ограничение становится

forall(k in K)
   forall(t in 1..f[nAct])
      sum(i in I : r[i,k] = 1) on[i,t] <= aR[k]; 

Вы также должны добавить ограничения, чтобы обеспечить определение включения, запуска и выключения.

   forall(t in 2..f[nAct])
      forall(i in I)
         on[i,t-1] - on[i,t] = end[i,t-1] - start[i,t];

   forall(i in I)
      on[i,0] = start[i,0];

   forall(i in I)
      sum(t in 1..f[nAct]) start[i,t] = 1;
   forall(i in I)
      sum(t in 1..f[nAct]) end[i,t] = 1;
   forall(i in I)
      sum(t in 1..f[nAct]) on[i,t] = d[i];

Вы можете использовать dexpr для манипулирования переменными решения. Вот пример из того же ресурса IBM Knowledge Center.

Без декспра

dvar int x in 0..20;
dvar int y in 0..20;
dvar int d;
dvar int s;
maximize (d);
subject to {
  d==x-y;
  s==x+y;
  s<=15;
  s<=x-2*y;
  d>=2;
  d<=y+8;
  1<=d;
}

С dexpr

dvar int x in 0..20;
dvar int y in 0..20;
dexpr int d=x-y;
dexpr int s=x+y;
maximize (d);
subject to {
  s<=15;
  s<=x-2*y;
  d>=2;
  d<=y+8;
  1<=d;
}
Другие вопросы по тегам