全球FlexSim系统仿真中文论坛

搜索
查看: 4992|回复: 3
打印 上一主题 下一主题

【琢磨琢磨推拉】该用推式还是拉式?

[复制链接]
跳转到指定楼层
1#
zorsite 发表于 2016-5-8 16:07:19 | 只看该作者 回帖奖励 |倒序浏览 |阅读模式
本帖最后由 zorsite 于 2016-5-8 16:19 编辑 ; A! G' z8 q; Z* e  V0 j: R

6 M5 X! r: M/ H, ~  s估计这将是一篇冷贴,高手不屑看,新手看了脑袋大。  r' D, x: x+ _+ X
QQ群里有人在问某案例如果不用拉式策略该怎么办?9 N: ^* V6 x- o
这是一个很简单但又很经典的一个案例,布局如下:
" G! a- q. u/ ?& I/ t5 v6 G* R& E. ]2 k) z1 E2 i
这个案例的核心要求是:上面两台处理器只处理临时实体类型1,下面三台处理器只处理临时实体类型2.
; n& a1 [$ z% Q' |) p: O4 b. |解决方法1:8 Q4 }: H2 n  o9 s# \' J1 Y: F
如果使用拉式策略,在处理器中设置拉入条件即可:
; Y4 B4 S0 z' b/ ?; N4 @9 r6 P4 h; F1 `/ \1 _6 E& r
5 ], q! B+ w% v
解决方法2:( s& y2 ?, o4 Z  S: j
有人坚持要用推式策略
2 P# @5 {; K9 A! }9 b$ d在暂存区的发送至端口中编写以下代码:
  1. if (getitemtype(item)==1) return duniform(1,2);$ ~- p7 Q. r0 G' j
  2. else return duniform(3,5);
复制代码
简单粗暴,问题解决。注意,记得把处理器中的拉式策略取消。
* x5 I7 }" c& N1 F6 R4 S
但是有一个问题,有可能随机产生的端口所连接的处理器正在使用中,而另外有处理器处于空闲状态。如何把临时实体发往处于空闲状态的那个处理器呢?
  {( R6 K0 E0 q  a2 R* g, X解决方法3:
- W1 i1 U' ~" u3 _删掉上面那两行代码,输入以下代码:
  1. int totalop;
    8 b8 ?7 T5 N; ]- z4 a
  2. int startop;
    5 d$ r, ~+ @* s2 |/ w* P% S
  3. if (getitemtype(item)==1)   
    9 o/ c$ t! {6 C+ n, D
  4. { startop=1;  ]5 X7 r+ `9 {0 B7 I6 w
  5. totalop=2;5 O9 L+ v' E' x3 |- m/ M% i
  6. }: Z6 g6 e3 ^) Y/ U
  7. else   / `9 C6 }8 U" J
  8. {7 ?$ |. @) q! E$ a1 C4 ?
  9. startop=3;
    & h6 A6 y, j6 S- B$ G$ j
  10. totalop=3;0 V% i# J& a4 v
  11. }
    ) l7 @, ]3 e8 z: n& }2 w6 z3 G
  12. doublearray openports = makearray(totalop);
    + N) T1 z! N; _) a& F9 N
  13. int nrofportsopen = 0;( Q6 l& t* I. J& u0 g
  14. for ( int index = startop; index < startop+totalop; index++)
      O& V7 V- W0 R" M' A+ V2 O: d( g. K- V
  15. {+ n' E- z) A' X4 [) d
  16. if (opavailable(current,index)) : `+ N' R6 h& P5 ?: a
  17. {
    9 A9 W0 u1 I3 {
  18.   nrofportsopen++;
    " z8 Z' z) u" ?3 I* i: H" I
  19.   openports[ nrofportsopen ] = index;
    2 ^& G0 X# F0 x; ]5 b
  20. }4 V/ l) {+ z$ g; J
  21. }/ J* N, D8 ?& a/ I9 v, f
  22. double returnvalue;. Q7 t+ s0 R6 W) K8 J. K& t
  23. if (nrofportsopen > 0)
    ) R! ^& i& H0 a: E; W. m2 h( ?4 T( g
  24. {
    , H( m. K2 U' P0 Q
  25. int returnindex = duniform(1, nrofportsopen);8 L6 B% n0 E2 w- J* a
  26. returnvalue = openports[returnindex];8 z6 l) c8 {! P/ g" ^: \4 }
  27. } else
    " E; Y+ b4 t" p2 h( A
  28.    returnvalue = duniform(startop,startop+totalop-1);8 D. ]4 M2 Z, ]5 M- ^
  29. return returnvalue;
复制代码
这段代码是由系统自带的“随机可用端口”稍作修改得到的,在这个案例中其实也不完美,比如说,3台暂存区都处于加工状态,这个时候来了新的临时实体,发往哪个端口?代码中设置的是随机端口。可是这3台处理器加工完毕的时间有先有后,能不能发送至最先加工完的那个处理器上?对不起,这段代码做不到。) d7 j" ?3 E' d
为了能够直观的观察这段代码的缺陷,可以把发生器的发生时间间隔设置小一些,比如均值设置为6或者3,重置模型后点击步进按钮来观察模型。# _. h8 C  y5 u" k
解决方法4:
4 u% G- a5 e' c
转换一下思路,如果要解决上面的问题,就必须要知道每一台处理器还剩多少时间能加工完毕,然后找到最先加工完的那一台。这样一来,目标就转换成了找到剩余加工时间最短的那一台处理器。
) s% E3 S$ f( x, U% p. G* v8 V剩余加工时间=安装时间+加工时间+进入时间-当前时间, D. ^' ~2 J  g) a# Y3 Z, ~; P* B% l6 p
删掉以上代码,输入以下代码:
  1. int totalop;
    ) u- e) E: Y2 m' f* ^+ B' o
  2. int startop;
    9 `6 {% v5 [7 }8 C) m- ~2 C' f
  3. if (getitemtype(item)==1)   " T  n( g, j+ ?8 Y
  4. {
    8 J. M3 y& Q8 k8 F
  5. startop=1;
    8 j: x4 X; ~+ R# z
  6. totalop=2;
    2 w/ ]/ i, i( |2 ^6 W' b
  7. }$ _& v: Y! P/ h+ R
  8. else   
    / A% ^7 i3 i; L! Z+ H
  9. {
    $ n9 @0 m' Z- u8 z4 `
  10. startop=3;4 h- t* v( s. C' u8 a" h% y
  11. totalop=3;  ^9 [$ G' {, V" B* T6 {  M* ]
  12. }' C, s5 s  T) V2 R# _/ g) i
  13. double minitime= 2147483647;
    0 d/ H+ }0 r) S! K( }/ o
  14. int returnvalue=0;( A) D8 v5 K' P- k* \
  15. for (int i = startop; i < totalop+startop ; i++)
    / f2 W0 I) I: [3 P
  16. {
    7 r5 m7 U- K7 x7 H$ r: v5 I
  17. double protime=getitemvar(rank(outobject(current,i),1),2);
    8 ]  m. G+ J, d) P( U9 W# N0 y
  18. double setuptime=getitemvar(rank(outobject(current,i),1),3);
    ! W! h7 ?8 h% x- |3 v5 K; A
  19. double entrytime=getentrytime(rank(outobject(current,i),1));$ {6 t" B3 L- p, u8 r
  20. double remainingtime=protime+setuptime+entrytime-time();
    " {+ L5 }/ \, X2 W" t
  21. if (remainingtime<minitime)
    & ]3 n6 {1 m5 O; W9 x/ k) ^
  22. {
    3 {5 ]; k& ~8 q( @. ^, M: D) B0 S9 B
  23.   minitime=remainingtime;
    2 E7 H3 {6 l  A, ?8 L# O. o/ A! @
  24.   returnvalue=i;& [# V, T9 F! e
  25. }
    ; T' A; X- U: T$ _8 r5 S
  26. }+ y# _2 O% k: ^  j4 c
  27. return returnvalue;' G# j; w- Q! Q( O- F
复制代码
终于把问题解决了,缺点是这段代码不具备随机性。把这段代码加入到上一次代码的else区域试一下?此时可以把发生时间的均值改回10,然后步进模型查看效果。- z' W9 J# l% ?/ Z7 }. J  |. }
2 e6 Y( B6 i2 j0 C: |3 }
该出手时就出手,该用拉式就用拉式吧,原谅我写代码不加注释吧!
9 j! Z- s, b! ?

本帖子中包含更多资源

您需要 登录 才可以下载或查看,没有帐号?立即注册

x
2#
Kimver 发表于 2016-5-8 22:30:41 | 只看该作者
我也想过这个问题,学习了,点个赞
3#
慧娴亚伦 发表于 2016-5-9 09:22:02 | 只看该作者
用 FlexSim建模要重点领会flex这个词。
1 j7 U+ w7 ?& G在FlexSim仿真世界中,抵达一个目的地有无数条路,对于实际建模需求而言,只要能够抵达,那么这条“路”就不孬。但是选择一条更好的更快捷的“路”是一个仿真建模师从入门到精通必须要掌握的一个过程,也是真正区分高手的方法。
+ \$ z: |2 h2 W4 R3 M9 [# ~6 w" b加老师给出的思考过程,对于深入学习FlexSim是非常重要的,学习仿真过程中提出“能不能用其他方式来完成这个建模要求”只是第一步,更为关键的是能不能通过进一步的思考和测试,通过自己的力量去实现新的解决方式。
' D0 d$ D- f: M# V) R$ M但是在这个过程中,千万不要“钻牛角尖”,作为学习是可以尝试各种不同的方法,但是在实际应用中请务必使用最简单最直观的方法。此外,也不要想着一口气就将所有的原理弄透,把一些暂时无法理解的东西记录下来,只要坚持学习使用,就会在逐步深入的过程中“顿悟”原先那些看上去非常不合理的存在。
, h! i( t2 X5 Z8 I8 p& h( E
" a/ T4 q4 H2 P/ \" e, n5 L, R感谢加老师分享。
4#
ldl89772962 发表于 2016-9-30 10:52:40 | 只看该作者
感谢老师分享
您需要登录后才可以回帖 登录 | 立即注册

本版积分规则

QQ|小黑屋|手机版|Archiver|全球FlexSim系统仿真中文论坛 ( 京ICP备14043114号-2 )

GMT+8, 2025-9-6 12:36 , Processed in 0.086116 second(s), 14 queries .

Powered by Discuz! X3.3© 2001-2013 Comsenz Inc.

快速回复 返回顶部 返回列表