Set i 'item' / i1*i7 / m 'machine' / m1, m2, m3, m4, m5, m6 /; $set lastrank i7 $set lastmachine m6 Table proctime(m,i) i1 i2 i3 i4 i5 i6 i7 m1 20 20 15 20 5 5 5 m2 80 25 20 30 20 20 25 m3 60 70 30 40 0 0 0 m4 0 35 0 50 0 0 10 m5 40 0 0 0 0 0 0 ; Alias (i,k); Variable rank(i,k) 'item i has position k' start(m,k) 'start time for job in position k on m' comp(m,k) 'completion time for job in postion k on m' totwait 'time before first job + times between jobs on last machine'; Binary Variable rank; Positive Variable start, comp; Equation oneInPosition(k) 'every position gets a jobs' oneRankPer(i) 'every job is assigned a rank' onmachrel(m,k) 'relations between the end of job rank k on machine m and start of job rank k on machine m+1' permachrel(m,k) 'relations between the end of job rank k on machine m and start of job rank k+1 on machine m' defcomp(m,k) 'calculation of completetion time based on start time and proctime' defobj 'completion time of job rank last'; oneInPosition(k).. sum(i, rank(i,k)) =e= 1; oneRankPer(i).. sum(k, rank(i,k)) =e= 1; onmachrel(m,k+1).. start(m,k+1) =g= comp(m,k); permachrel(m+1,k).. start(m+1,k) =g= comp(m,k); defcomp(m,k).. comp(m,k) =e= start(m,k) + sum(i, proctime(m,i)*rank(i,k)); defobj.. totwait =g= comp('%lastmachine%','%lastrank%'); Model sequence / all /; option optCr = 0; solve sequence using mip min totwait; * Maybe the following is better info to output Parameter startjob(m,i); startjob(m,i) = sum(k$(rank.l(i,k)>0.5), start.l(m,k)); option startjob:0:1:1; display startjob; * For small data we can just enumerate all permutations and evaluate the schedule $ifE card(i)>8 $exit * Only test with some LP solvers $ifI %gams.rmip% == cplex $goto continue $ifI %gams.rmip% == xpress $goto continue $ifI %gams.rmip% == gurobi $goto continue $ifI %gams.rmip% == bdmlpd $goto continue $exit $label continue $eval pmax fact(card(i)) Set p / p1*p%pmax% / rankall(p,i,i); option rankall > i; Parameter prankall(p,i,i) 'parameter version of rankall' ptotwait(p) 'scenario objective'; prankall(rankall) = 1; * Use GUSS to evaluate all scenarios Set dict / p. scenario. '' rank. fixed. prankall totwait.level. ptotwait /; solve sequence using rmip min totwait scenario dict; Scalar besttotwait / +inf /; loop(p, if(besttotwait > ptotwait(p), besttotwait = ptotwait(p); rank.l(i,k) = 1$(rankall(p,i,k)); ); ); display besttotwait, rank.l;