Commit 9986bb6c authored by Georgios Dagkakis's avatar Georgios Dagkakis

blocking also to be calculate by the state

parent 9503d779
...@@ -154,7 +154,12 @@ class CoreObject(object): ...@@ -154,7 +154,12 @@ class CoreObject(object):
self.op_col_indx=None self.op_col_indx=None
# flag that locks the entry of an object so that it cannot receive entities # flag that locks the entry of an object so that it cannot receive entities
self.isLocked=False self.isLocked=False
# flag that shows if the Machine is processing state at any given time
self.isProcessing=False
# flag that shows if the Machine is blocked state at any given time
self.isBlocked=False
# ======================================================================= # =======================================================================
# the main process of the core object # the main process of the core object
# this is dummy, every object must have its own implementation # this is dummy, every object must have its own implementation
...@@ -196,7 +201,8 @@ class CoreObject(object): ...@@ -196,7 +201,8 @@ class CoreObject(object):
# as argument by getEntity of the receiver # as argument by getEntity of the receiver
# ======================================================================= # =======================================================================
def removeEntity(self, entity=None): def removeEntity(self, entity=None):
self.addBlockage() self.isBlocked=False
self.addBlockage()
activeObjectQueue=self.Res.users activeObjectQueue=self.Res.users
activeObjectQueue.remove(entity) #remove the Entity from the queue activeObjectQueue.remove(entity) #remove the Entity from the queue
......
...@@ -189,10 +189,7 @@ class Machine(CoreObject): ...@@ -189,10 +189,7 @@ class Machine(CoreObject):
self.preemptQueue=self.env.event() self.preemptQueue=self.env.event()
# signal used for informing objectInterruption objects that the current entity processed has finished processnig # signal used for informing objectInterruption objects that the current entity processed has finished processnig
self.endedLastProcessing=self.env.event() self.endedLastProcessing=self.env.event()
# flag that shows if the Machine is processing state at any given time
self.isProcessing=False
#=========================================================================== #===========================================================================
# create an operatorPool if needed # create an operatorPool if needed
#=========================================================================== #===========================================================================
...@@ -468,6 +465,7 @@ class Machine(CoreObject): ...@@ -468,6 +465,7 @@ class Machine(CoreObject):
# timeLastProcessingStarted : dummy variable to keep track of the time that the processing starts after # timeLastProcessingStarted : dummy variable to keep track of the time that the processing starts after
# every interruption # every interruption
self.timeLastProcessingStarted=self.env.now self.timeLastProcessingStarted=self.env.now
# processing starts, update the flag
self.isProcessing=True self.isProcessing=True
# wait for the processing time left tinM, if no interruption occurs then change the processingEndedFlag and exit loop, # wait for the processing time left tinM, if no interruption occurs then change the processingEndedFlag and exit loop,
# else (if interrupted()) set interruption flag to true (only if tinM==0), # else (if interrupted()) set interruption flag to true (only if tinM==0),
...@@ -490,9 +488,12 @@ class Machine(CoreObject): ...@@ -490,9 +488,12 @@ class Machine(CoreObject):
# if there is a failure in the machine or interruption due to preemption, it is passivated # if there is a failure in the machine or interruption due to preemption, it is passivated
# passivate the Machine for as long as there is no repair # passivate the Machine for as long as there is no repair
yield self.interruptionEnd while 1:
assert self.env.now==self.interruptionEnd.value, 'the victim of the failure is not the object that received it' yield self.interruptionEnd # interruptionEnd to be triggered by ObjectInterruption
self.interruptionEnd=self.env.event() assert self.env.now==self.interruptionEnd.value, 'the victim of the failure is not the object that received it'
self.interruptionEnd=self.env.event()
if self.Up and self.onShift:
break
self.postInterruptionActions() self.postInterruptionActions()
...@@ -542,6 +543,7 @@ class Machine(CoreObject): ...@@ -542,6 +543,7 @@ class Machine(CoreObject):
if not self.signalReceiver(): if not self.signalReceiver():
# if there was no available receiver, get into blocking control # if there was no available receiver, get into blocking control
while 1: while 1:
self.timeLastBlockageStarted=self.env.now
# wait the event canDispose, this means that the station can deliver the item to successor # wait the event canDispose, this means that the station can deliver the item to successor
self.printTrace(self.id, waitEvent='(canDispose or interruption start)') self.printTrace(self.id, waitEvent='(canDispose or interruption start)')
receivedEvent=yield self.env.any_of([self.canDispose , self.interruptionStart]) receivedEvent=yield self.env.any_of([self.canDispose , self.interruptionStart])
...@@ -553,11 +555,15 @@ class Machine(CoreObject): ...@@ -553,11 +555,15 @@ class Machine(CoreObject):
self.interruptionStart=self.env.event() self.interruptionStart=self.env.event()
# wait for the end of the interruption # wait for the end of the interruption
self.interruptionActions() # execute interruption actions self.interruptionActions() # execute interruption actions
yield self.interruptionEnd # interruptionEnd to be triggered by ObjectInterruption while 1:
assert self.env.now==self.interruptionEnd.value, 'the victim of the failure is not the object that received it' yield self.interruptionEnd # interruptionEnd to be triggered by ObjectInterruption
self.interruptionEnd=self.env.event() assert self.env.now==self.interruptionEnd.value, 'the victim of the failure is not the object that received it'
self.interruptionEnd=self.env.event()
if self.Up and self.onShift:
break
self.postInterruptionActions() self.postInterruptionActions()
if self.signalReceiver(): if self.signalReceiver():
self.timeLastBlockageStarted=self.env.now
break break
else: else:
continue continue
...@@ -591,8 +597,12 @@ class Machine(CoreObject): ...@@ -591,8 +597,12 @@ class Machine(CoreObject):
# actions to be carried out when the processing of an Entity ends # actions to be carried out when the processing of an Entity ends
# ======================================================================= # =======================================================================
def endProcessingActions(self): def endProcessingActions(self):
# set isProcessing to False
self.isProcessing=False self.isProcessing=False
# add working time
self.totalWorkingTime+=self.env.now-self.timeLastProcessingStarted self.totalWorkingTime+=self.env.now-self.timeLastProcessingStarted
self.timeLastBlockageStarted=self.env.now
activeObjectQueue=self.Res.users activeObjectQueue=self.Res.users
activeEntity=activeObjectQueue[0] activeEntity=activeObjectQueue[0]
self.printTrace(self.getActiveObjectQueue()[0].name, processEnd=self.objName) self.printTrace(self.getActiveObjectQueue()[0].name, processEnd=self.objName)
...@@ -622,13 +632,8 @@ class Machine(CoreObject): ...@@ -622,13 +632,8 @@ class Machine(CoreObject):
G.pendingEntities.append(activeObjectQueue[0]) G.pendingEntities.append(activeObjectQueue[0])
# set the variable that flags an Entity is ready to be disposed # set the variable that flags an Entity is ready to be disposed
self.waitToDispose=True self.waitToDispose=True
# update the total working time # blocking starts
# the total processing time for this entity is what the distribution initially gave self.isBlocked=True
# if not self.shouldPreempt:
# self.totalWorkingTime+=self.totalProcessingTimeInCurrentEntity
# # if the station was preemptied for a critical order then calculate the total working time accordingly
# else:
# self.totalWorkingTime+=self.env.now-self.timeLastProcessingStarted
# update the variables keeping track of Entity related attributes of the machine # update the variables keeping track of Entity related attributes of the machine
self.timeLastEntityEnded=self.env.now # this holds the time that the last entity ended processing in Machine self.timeLastEntityEnded=self.env.now # this holds the time that the last entity ended processing in Machine
self.nameLastEntityEnded=self.currentEntity.name # this holds the name of the last entity that ended processing in Machine self.nameLastEntityEnded=self.currentEntity.name # this holds the name of the last entity that ended processing in Machine
...@@ -663,9 +668,18 @@ class Machine(CoreObject): ...@@ -663,9 +668,18 @@ class Machine(CoreObject):
# actions to be carried out when the processing of an Entity ends # actions to be carried out when the processing of an Entity ends
# ======================================================================= # =======================================================================
def interruptionActions(self): def interruptionActions(self):
# if we are processing add the working time
# only if object is not preempting though
# in case of preemption endProcessingActions will be called
if self.isProcessing and not self.shouldPreempt: if self.isProcessing and not self.shouldPreempt:
self.totalWorkingTime+=self.env.now-self.timeLastProcessingStarted self.totalWorkingTime+=self.env.now-self.timeLastProcessingStarted
if self.isBlocked:
self.addBlockage()
# set isProcessing to False
self.isProcessing=False self.isProcessing=False
# set isBlocked to False
self.isBlocked=False
activeObjectQueue=self.Res.users activeObjectQueue=self.Res.users
activeEntity=activeObjectQueue[0] activeEntity=activeObjectQueue[0]
self.printTrace(activeEntity.name, interrupted=self.objName) self.printTrace(activeEntity.name, interrupted=self.objName)
...@@ -862,6 +876,13 @@ class Machine(CoreObject): ...@@ -862,6 +876,13 @@ class Machine(CoreObject):
and self.waitToDispose\ and self.waitToDispose\
and (thecaller in self.next)\ and (thecaller in self.next)\
and (self.canDeliverOnInterruption or self.checkIfActive()) and (self.canDeliverOnInterruption or self.checkIfActive())
# =======================================================================
# adds the blockage time to totalBlockageTime
# each time an Entity is removed
# =======================================================================
def addBlockage(self):
self.totalBlockageTime+=self.env.now-self.timeLastBlockageStarted
# ======================================================================= # =======================================================================
# calculates the setup time # calculates the setup time
...@@ -953,17 +974,20 @@ class Machine(CoreObject): ...@@ -953,17 +974,20 @@ class Machine(CoreObject):
if self.onShift==False: # and self.interruptedBy=='ShiftScheduler': if self.onShift==False: # and self.interruptedBy=='ShiftScheduler':
offShiftTimeInCurrentEntity=self.env.now-activeObject.timeLastShiftEnded offShiftTimeInCurrentEntity=self.env.now-activeObject.timeLastShiftEnded
# if there is an entity that finished processing in a Machine but did not get to reach # # if there is an entity that finished processing in a Machine but did not get to reach
# the following Object till the end of simulation, # # the following Object till the end of simulation,
# we have to add this blockage to the percentage of blockage in Machine # # we have to add this blockage to the percentage of blockage in Machine
# we should exclude the failure time in current entity though! # # we should exclude the failure time in current entity though!
if (len(activeObjectQueue)>0) and (mightBeBlocked)\ # if (len(activeObjectQueue)>0) and (mightBeBlocked)\
and ((activeObject.nameLastEntityEntered == activeObject.nameLastEntityEnded)) and self.onShift: # and ((activeObject.nameLastEntityEntered == activeObject.nameLastEntityEnded)) and self.onShift:
# be careful here, might have to reconsider # # be careful here, might have to reconsider
activeObject.totalBlockageTime+=self.env.now-(activeObject.timeLastEntityEnded+activeObject.downTimeInTryingToReleaseCurrentEntity) # activeObject.totalBlockageTime+=self.env.now-(activeObject.timeLastEntityEnded+activeObject.downTimeInTryingToReleaseCurrentEntity)
if activeObject.Up==False: # if activeObject.Up==False:
activeObject.totalBlockageTime-=self.env.now-activeObject.timeLastFailure # activeObject.totalBlockageTime-=self.env.now-activeObject.timeLastFailure
alreadyAdded=True # alreadyAdded=True
if self.isBlocked:
self.addBlockage()
#if Machine is currently processing an entity we should count this working time #if Machine is currently processing an entity we should count this working time
if(self.isProcessing): if(self.isProcessing):
...@@ -987,17 +1011,17 @@ class Machine(CoreObject): ...@@ -987,17 +1011,17 @@ class Machine(CoreObject):
# we also need to add the last blocking time to total blockage time # we also need to add the last blocking time to total blockage time
if(activeObject.Up==False): if(activeObject.Up==False):
activeObject.totalFailureTime+=self.env.now-activeObject.timeLastFailure activeObject.totalFailureTime+=self.env.now-activeObject.timeLastFailure
# we add the value only if it hasn't already been added # # we add the value only if it hasn't already been added
if((mightBeBlocked) and (activeObject.nameLastEntityEnded==activeObject.nameLastEntityEntered) and (not alreadyAdded)): # if((mightBeBlocked) and (activeObject.nameLastEntityEnded==activeObject.nameLastEntityEntered) and (not alreadyAdded)):
activeObject.totalBlockageTime+=(self.env.now-activeObject.timeLastEntityEnded)-(self.env.now-activeObject.timeLastFailure)-activeObject.downTimeInTryingToReleaseCurrentEntity # activeObject.totalBlockageTime+=(self.env.now-activeObject.timeLastEntityEnded)-(self.env.now-activeObject.timeLastFailure)-activeObject.downTimeInTryingToReleaseCurrentEntity
alreadyAdded=True # alreadyAdded=True
#if the machine is off shift,add this to the off-shift time #if the machine is off shift,add this to the off-shift time
# we also need to add the last blocking time to total blockage time # we also need to add the last blocking time to total blockage time
if activeObject.onShift==False: if activeObject.onShift==False:
self.totalOffShiftTime+=self.env.now-self.timeLastShiftEnded self.totalOffShiftTime+=self.env.now-self.timeLastShiftEnded
if((mightBeBlocked) and (activeObject.nameLastEntityEnded==activeObject.nameLastEntityEntered) and (not alreadyAdded)): # if((mightBeBlocked) and (activeObject.nameLastEntityEnded==activeObject.nameLastEntityEntered) and (not alreadyAdded)):
activeObject.totalBlockageTime+=(self.env.now-activeObject.timeLastEntityEnded)-offShiftTimeInCurrentEntity # activeObject.totalBlockageTime+=(self.env.now-activeObject.timeLastEntityEnded)-offShiftTimeInCurrentEntity
#Machine was idle when it was not in any other state #Machine was idle when it was not in any other state
activeObject.totalWaitingTime=MaxSimtime-activeObject.totalWorkingTime-activeObject.totalBlockageTime-activeObject.totalFailureTime-activeObject.totalLoadTime-activeObject.totalSetupTime-self.totalOffShiftTime activeObject.totalWaitingTime=MaxSimtime-activeObject.totalWorkingTime-activeObject.totalBlockageTime-activeObject.totalFailureTime-activeObject.totalLoadTime-activeObject.totalSetupTime-self.totalOffShiftTime
......
...@@ -44,8 +44,11 @@ class MachineJobShop(Machine): ...@@ -44,8 +44,11 @@ class MachineJobShop(Machine):
# actions to be carried out when the processing of an Entity ends # actions to be carried out when the processing of an Entity ends
# ======================================================================= # =======================================================================
def endProcessingActions(self): def endProcessingActions(self):
# set isProcessing to False
self.isProcessing=False self.isProcessing=False
# add working time
self.totalWorkingTime+=self.env.now-self.timeLastProcessingStarted self.totalWorkingTime+=self.env.now-self.timeLastProcessingStarted
self.timeLastBlockageStarted=self.env.now
activeObject=self.getActiveObject() activeObject=self.getActiveObject()
activeObjectQueue=activeObject.Res.users activeObjectQueue=activeObject.Res.users
...@@ -87,11 +90,6 @@ class MachineJobShop(Machine): ...@@ -87,11 +90,6 @@ class MachineJobShop(Machine):
#do this so that if it is overtime working it is not counted as off-shift time #do this so that if it is overtime working it is not counted as off-shift time
if not activeObject.onShift: if not activeObject.onShift:
activeObject.timeLastShiftEnded=self.env.now activeObject.timeLastShiftEnded=self.env.now
# update the total working time # the total processing time for this entity is what the distribution initially gave
# if not self.shouldPreempt:
# activeObject.totalWorkingTime+=activeObject.totalProcessingTimeInCurrentEntity
# else:
# activeObject.totalWorkingTime+=self.env.now-(self.timeLastEntityEntered)
# update the variables keeping track of Entity related attributes of the machine # update the variables keeping track of Entity related attributes of the machine
activeObject.timeLastEntityEnded=self.env.now # this holds the time that the last entity ended processing in Machine activeObject.timeLastEntityEnded=self.env.now # this holds the time that the last entity ended processing in Machine
activeObject.nameLastEntityEnded=activeObject.currentEntity.name # this holds the name of the last entity that ended processing in Machine activeObject.nameLastEntityEnded=activeObject.currentEntity.name # this holds the name of the last entity that ended processing in Machine
...@@ -99,7 +97,9 @@ class MachineJobShop(Machine): ...@@ -99,7 +97,9 @@ class MachineJobShop(Machine):
# reset flags # reset flags
self.shouldPreempt=False self.shouldPreempt=False
self.isProcessingInitialWIP=False self.isProcessingInitialWIP=False
# blocking starts
self.isBlocked=True
# TODO: collapse that to Machine # TODO: collapse that to Machine
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment