ICode9

精准搜索请尝试: 精确搜索
首页 > 其他分享> 文章详细

Cplex解决JSP问题

2022-02-24 09:34:40  阅读:267  来源: 互联网

标签:机器 r1 r2 -- Cplex .. JSP 解决 工件


我的上一篇博客Cplex解决FSP问题 - 加油,陌生人! - 博客园 (cnblogs.com)用Cplex完成了FSP的建模,这篇文章主要是解决JSP问题(车间调度问题)。

JSP问题:n个工件,m台机器,每个工件都有自己的加工路线,要求找出最佳的加工顺序,使得完工时间最小。从问题的描述来看,FSP是一种特殊的JSP,因为它所有工件的加工路线都是相同的。

下面就来考虑如何解决JSP问题。

先附上数据文件(.dat),如下

数据文件.dat

n=4;//工件数量
m=3;//机器数量
p=[[20,87,31],
   [25,32,24],
   [72,23,28],
   [86,76,97]];//各工件在各机器上的加工时间
/*prec=[[1,3,2],
        [3,1,2],
        [3,2,1],
        [2,3,1]];*/
temp=[  [[0,0,0,0],//表示加工顺序
         [0,0,0,1],
         [0,0,0,0],
         [0,0,1,0]],
        [[0,0,0,0],
         [0,0,1,0],
         [0,0,0,0],
         [0,1,0,0]],
        [[0,0,0,0],
         [0,0,0,0],
         [0,1,0,0],
         [0,0,1,0]],
        [[0,0,0,0],
         [0,0,0,0],
         [0,0,0,1],
         [0,1,0,0]] ];

p表示各工件在各机器上的加工时间,例如工件1在机器1上的加工时间为20。temp用来表示每个工件的加工工艺,是个三维矩阵,里面包含了n个(m+1)*(m+1)的二维矩阵。例如在第一个二维矩阵arr中

可以看到arr[1][3]=1,表示机器1-->机器3;arr[3][2]=1,表示机器3-->2。于是工件1的加工顺序为m1-->m3-->m2,其他的工件也是类似的原理。

模型文件.mod

int n=...;//工件数量
int m=...;//机器数量,也可以理解为工序数量,因为一道工序只有一台机器
int M=100000;//一个非常大的数
range r1=1..n;
range r2=1..m;
int temp[r1][0..m][0..m]=...;


dvar float+ c[r1][r2];//表示完工时间
int p[r1][r2]=...;

dvar boolean a[r1][0..m][0..m];//i,h,k.机器h优先于机器k加工工件i
dvar boolean x[0..n][0..n][r2];//i,j,k.工件i优先于工件j在机器k上加工

minimize max(i in r1,k in r2) c[i][k];//机器i在机器k上的完工时间

subject to{
    forall(i in r1,h in r2,k in r2)
      c[i][k]-p[i][k]+M*(1-a[i][h][k])>=c[i][h];//机器h优先于机器k加工工件i
    forall(i in r1,j in r1,k in r2)
      c[j][k]-c[i][k]+M*(1-x[i][j][k])>=p[i][k];//工件i优先于工件j在机器k上加工
    forall(j in r1,k in r2)
      //对于任意一台机器上的工件j,必然有一个紧前作业i
      sum(i in 0..n) x[i][j][k]==1;
    forall(i in r1,k in r2)
      //对于任意一台机器上的工件i,必然有一个紧后作业j
      sum(j in 0..n) x[i][j][k]==1;
    forall(k in r2)
      //对于每台机器来说,只能由一个作业位于最后
      sum(i in 0..n) x[i][0][k]<=1;
    forall(k in r2)
      //对于每台机器来说,只能有一个作业首先加工
      sum(j in 0..n) x[0][j][k]<=1;
    /*************************/  
    forall(i in r1,k in r2)
      //对于任意一个工件,必然有一个紧前工序
      sum(h in 0..m) a[i][h][k]==1;
    forall(i in r1,h in r2)
      //对于任意一个工件,必然有一个紧后工序
      sum(k in 0..m) a[i][h][k]==1;
    forall(i in r1)
      //对于每个工件来说,只能有一个工序处于第一位
      sum(k in 0..m) a[i][0][k]<=1;
    forall(i in r1)
      //对于每个工件来说,只能有一个工序处于最后一位
      sum(h in 0..m) a[i][h][0]<=1;
    /************************/
    forall(i in r1)
      sum(h in 0..m,k in 0..m) temp[i][h][k]*a[i][h][k]==2;
}
execute{
    writeln("每台机器上工件加工的顺序:");
    for(var k in r2){
        for(var i in r1){
            for(var j in r1){
                if(x[i][j][k]==1){
                    writeln(k+":"+i+"-->"+j);                
                }            
            }        
        }    
    }
    writeln("每个工件的加工顺序:")
    for(var i in r1){
        for(var h in r2){
            for(var k in r2){
                if(a[i][h][k]==1){
                    writeln(i+":"+h+"-->"+k);                
                }            
            }        
        }    
    }
}

结果:

// solution (optimal) with objective 220
// Quality Incumbent solution:
// MILP objective                                2.2000000000e+002
// MILP solution norm |x| (Total, Max)           2.58900e+003 2.20000e+002
// MILP solution error (Ax=b) (Total, Max)       0.00000e+000 0.00000e+000
// MILP x bound error (Total, Max)               0.00000e+000 0.00000e+000
// MILP x integrality error (Total, Max)         0.00000e+000 0.00000e+000
// MILP slack bound error (Total, Max)           0.00000e+000 0.00000e+000
// 

c = [[0
             118 31]
             [87 220 62]
             [148 76 0]
             [220 0 97]];
a = [[[0 1 0 0]
                 [0 0 0 1]
                 [1 0 0 0]
                 [0 0 1 0]]
             [[0 0 0 1]
                 [0 0 1 0]
                 [1 0 0 0]
                 [0 1 0 0]]
             [[0 0 0 1]
                 [1 0 0 0]
                 [0 1 0 0]
                 [0 0 1 0]]
             [[0 0 1 0]
                 [1 0 0 0]
                 [0 0 0 1]
                 [0 1 0 0]]];
x = [[[0 0 0]
                 [1 0 0]
                 [0 0 0]
                 [0 0 1]
                 [0 1 0]]
             [[0 0 0]
                 [0 0 0]
                 [1 1 1]
                 [0 0 0]
                 [0 0 0]]
             [[0 1 0]
                 [0 0 0]
                 [0 0 0]
                 [1 0 0]
                 [0 0 1]]
             [[0 0 0]
                 [0 1 1]
                 [0 0 0]
                 [0 0 0]
                 [1 0 0]]
             [[1 0 1]
                 [0 0 0]
                 [0 0 0]
                 [0 1 0]
                 [0 0 0]]];
/*----------------脚本信息---------------*/

// solution (optimal) with objective 220
每台机器上工件加工的顺序:
1:1-->2
1:2-->3
1:3-->4
2:1-->2
2:3-->1
2:4-->3
3:1-->2
3:2-->4
3:3-->1
每个工件的加工顺序:
1:1-->3
1:3-->2
2:1-->2
2:3-->1
3:2-->1
3:3-->2
4:2-->3
4:3-->1

 

标签:机器,r1,r2,--,Cplex,..,JSP,解决,工件
来源: https://www.cnblogs.com/xiaojun65/p/15930232.html

本站声明: 1. iCode9 技术分享网(下文简称本站)提供的所有内容,仅供技术学习、探讨和分享;
2. 关于本站的所有留言、评论、转载及引用,纯属内容发起人的个人观点,与本站观点和立场无关;
3. 关于本站的所有言论和文字,纯属内容发起人的个人观点,与本站观点和立场无关;
4. 本站文章均是网友提供,不完全保证技术分享内容的完整性、准确性、时效性、风险性和版权归属;如您发现该文章侵犯了您的权益,可联系我们第一时间进行删除;
5. 本站为非盈利性的个人网站,所有内容不会用来进行牟利,也不会利用任何形式的广告来间接获益,纯粹是为了广大技术爱好者提供技术内容和技术思想的分享性交流网站。

专注分享技术,共同学习,共同进步。侵权联系[81616952@qq.com]

Copyright (C)ICode9.com, All Rights Reserved.

ICode9版权所有