电梯调度算法的改进
之前我说过最初是想做个能实时检测的电梯调度算法,但因为各种并发问题不能解决所以只能退而求其次,做了一个一轮过后重新求最值的电梯调度算法,现在经过改进终于发现了问题所在,原来我只考虑了各线程之间的同步而没考虑到与我的键盘监听器之间的同步(我的控制信息是监听键盘加入的),现在我新增了几条判断语句问题得以解决,一个可以实时检测的电梯调度算法完成了!以下是改进的部分。
1,控制存储结构改为链表时,易于插入信息,并且添加一些算法使其有序
1 class Contro//控制模块类 2 { 3 private LinkedList<Integer> arr;//记录需要到达的楼层 4 private LinkedList<Integer> jarr;//设置一个存奇数楼层的表 5 private LinkedList<Integer> darr;//存偶数楼层 6 View vie; 7 Contro(View vie)//构造函数 8 { 9 arr=new LinkedList<Integer>(); 10 jarr=new LinkedList<Integer>(); 11 darr=new LinkedList<Integer>(); 12 this.vie=vie; 13 } 14 public void add(Integer i)//添加到达楼层 15 { 16 if(!arr.contains(i)) 17 { 18 vie.map.get(new Point(300,500-i*20)).setBackground(Color.red); 19 int cout=0; 20 for(Integer in:arr) 21 { 22 if(in>i) 23 { 24 break; 25 } 26 cout++; 27 } 28 arr.add(cout, i); 29 if(i%2==0) 30 darr.add(i); 31 else 32 jarr.add(i); 33 } 34 } 35 public void remove(Integer i)//取消一个任务楼层 36 { 37 vie.map.get(new Point(300,500-i*20)).setBackground(Color.white); 38 arr.remove(i); 39 if(i%2==0) 40 darr.remove(i); 41 else 42 jarr.remove(i); 43 } 44 public Integer getmin()//得到最小楼层值 45 { 46 return arr.getFirst(); 47 } 48 public Integer getmax()//得到最大楼层值 49 { 50 return arr.getLast(); 51 } 52 public LinkedList<Integer> getlist(int mode)//得到存储楼层信息的列表 53 { 54 if(mode==0) 55 return arr; 56 if(mode==1) 57 return jarr; 58 if(mode==2) 59 return darr; 60 else 61 return null; 62 } 63 }
2,改进后的电梯调度算法部分
1 public void down()//定义一个下降函数 便于复用 2 { 3 for(;!con.getlist(this.mode).isEmpty()&&cout>=con.getmin();cout--) 4 { 5 synchronized(con) 6 { 7 if(cout<21) 8 vie.map.get(new Point(250-50*panmode,500-(cout+1)*20)).setBackground(Color.white); 9 vie.map.get(new Point(250-50*panmode,500-cout*20)).setBackground(Color.black); 10 if(con.getlist(this.mode).contains(cout)) 11 { 12 con.remove(cout); 13 System.out.println("到达"+cout+"层"); 14 //changepeople(); 15 try { 16 Thread.sleep(500); 17 } catch (InterruptedException e) { 18 // TODO Auto-generated catch block 19 e.printStackTrace(); 20 } 21 } 22 if(con.getlist(this.mode).isEmpty()||cout<con.getmin()||cout==con.getmin()) 23 break; 24 } 25 try { 26 Thread.sleep(200); 27 } catch (InterruptedException e) { 28 // TODO Auto-generated catch block 29 e.printStackTrace(); 30 } 31 } 32 } 33 public void run() //电梯运行算法 主要运行函数 34 { 35 while(true) 36 { 37 while(!con.getlist(this.mode).isEmpty()) 38 { 39 if(con.getmax()>cout) //和下面的if组成判断电梯是否向上运行 否则向下运行 40 { 41 if(con.getmin()>cout||(con.getmax()-cout)<=(cout-con.getmin())) 42 { 43 for(;!con.getlist(this.mode).isEmpty()&&cout<=con.getmax();cout++) 44 { 45 synchronized(con) 46 { 47 if(cout>0) 48 vie.map.get(new Point(250-50*panmode,500-(cout-1)*20)).setBackground(Color.white); 49 vie.map.get(new Point(250-50*panmode,500-cout*20)).setBackground(Color.black); 50 if(con.getlist(this.mode).contains(cout)) 51 { 52 con.remove(cout); 53 System.out.println("到达"+cout+"层"); 54 //changepeople(); 55 try { 56 Thread.sleep(500); 57 } catch (InterruptedException e) { 58 // TODO Auto-generated catch block 59 e.printStackTrace(); 60 } 61 } 62 if(con.getlist(this.mode).isEmpty()||cout>con.getmax()||cout==con.getmax()) 63 break; 64 } 65 try { 66 Thread.sleep(200); 67 } catch (InterruptedException e) { 68 // TODO Auto-generated catch block 69 e.printStackTrace(); 70 } 71 } 72 } 73 else 74 down(); 75 } 76 else //电梯向下运行的算法 77 down(); 78 } 79 try { 80 Thread.sleep(1000); 81 } catch (InterruptedException e) { 82 // TODO Auto-generated catch block 83 e.printStackTrace();} 84 while(con.getlist(this.mode).isEmpty()&&cout!=incout) //无任务回到初始楼层的函数 85 { 86 if(vie.map.get(new Point(250-50*panmode,500-cout*20))!=null) 87 vie.map.get(new Point(250-50*panmode,500-cout*20)).setBackground(Color.white); 88 if(cout>incout) 89 { 90 cout--; 91 vie.map.get(new Point(250-50*panmode,500-cout*20)).setBackground(Color.black); 92 try { 93 Thread.sleep(200); 94 } catch (InterruptedException e) { 95 // TODO Auto-generated catch block 96 e.printStackTrace(); 97 } 98 } 99 if(cout<incout) 100 { 101 cout++; 102 vie.map.get(new Point(250-50*panmode,500-cout*20)).setBackground(Color.black); 103 try { 104 Thread.sleep(200); 105 } catch (InterruptedException e) { 106 // TODO Auto-generated catch block 107 e.printStackTrace(); 108 } 109 } 110 } 111 } 112 }