ResourcePool


Defines a set of resource units that can be seized and released by agents using Seize, Release, Assembler and Service flowchart blocks.

Resource types

The resources can be of three types: static, moving, and portable:

Moving and portable resources have their home locations where they can optionally return or be returned. The resource units in one pool can have individual properties, can be animated, collect unit-based statistics, etc. You can define your own resource types representing staff, equipment, etc. The agent uses the pool name to refer to the resource units, and can pick a particular unit by analyzing the unit attributes.

Any resource unit can be either idle or busy. This object collects utilization statistics, which is continuous time statistics on the percent of busy units. Resource units always collect their individual utilization statistics.

Library objects that work with resources

There is a variety of possible operations with resource units supported by the Process Modeling Library: the agent can seize one or several units (Seize), release units (Release), send seized units to a particular location (ResourceSendTo), attach units so that they will move with the agent (ResourceAttach), and detach attached units (ResourceDetach). Whenever an operation is done over multiple resource units, the list of their  ResourcePool objects is specified, for example to seize two nurses and X-Ray room you would specify: Nurse, Nurse, XRay.

The requests from different Seize and Service objects are queuing at the ResourcePool if cannot be immediately satisfied. The queue may be simple FIFO or based on priorities.

Defining the resources capacity

The capacity of this object (the number of units) can be defined directly as a number that you type in its Capacity parameter. Then, if you want to change the number of resources dynamically at the model runtime, use can call the function set_capacity(new value). If the capacity is dynamically reduced by calling set_capacity(), but the number of currently seized units exceeds the new capacity, the extra units will only be disposed from the pool when they are released.

Another way to define capacity is by resources' home location. The special markup objects called nodes are used as the home locations for resources. Click the button to add a node or click this button first and then select a node in the graphical editor.

The number of nodes that you add as a home location will define the resources' capacity. You can even add one and the same node several times in this parameter.

In the figure below, you can see that the ...based on attractors option has also been selected. Then, the ResourcePool object will count the number of attractors in the home node and treat that number as the number of the resource units in this pool.

If you define the capacity both with several nodes as the home locations and with attractors in those nodes, the total number of resources will be the sum of all elements.

Defining an operating schedule for the resources

You can define a work schedule for your resources. There are four different ways how you can use the Schedule element to define the capacity for the resources. The Schedule element is part of the Agent palette. You can also add the Clock object from the Pictures palette to the agent diagram to keep track of time at the model runtime.

Demonstration model: Capacity Schedules

Parameters

In all dynamic parameters the resource unit is available as the unit local variable.
Resource type
The type of the resource units in this pool: Static, Moving, Portable.
Get value: type
Default value: Moving (ResourcePool.RESOURCE_MOVING)
Valid values:  ResourcePool.RESOURCE_MOVING
           ResourcePool.RESOURCE_STATIC
           ResourcePool.RESOURCE_PORTABLE
Capacity defined
Defines how the number of resource units is defined:
Directly
- explicitly as a fixed number, in the Capacity field below.
By home location - it will be defined by the home location nodes (equal to the number of nodes specified as the Home location (nodes), or to the number of attractors inside these node(s), if the based on attractors option is selected)
By schedule - with a schedule that defines how the number of resources changes over time (the schedule Type is integer).
By "on/off" schedule - with a schedule that defines how the resources availability changes over time (the schedule Type is on/off).
By shifts: group schedules - here you can choose several schedules (integer) to define the resources' capacity.
By shift plan - here you use one schedule (integer) to define the resources' capacity for different shifts. 
Get value: capacityDefinitionType
Default value: Directly (ResourcePool.CAPACITY_DIRECT)
Valid values:  ResourcePool.CAPACITY_DIRECT
           ResourcePool.CAPACITY_HOME_LOCATION
           ResourcePool.CAPACITY_SCHEDULE
           ResourcePool.CAPACITY_SCHEDULE_ON_OFF
           ResourcePool.CAPACITY_SHIFT_GROUP_SCHEDULES
           ResourcePool.CAPACITY_SHIFT_PLAN
Capacity
[Visible if capacity is defined Directly] The number of resource units in the pool.
Syntax: int capacity
Default value: 1
When capacity decreases
[Visible if capacity is defined Directly, By schedule or By on/off schedule]
Select here what should be done with the excess units:
units are preserved ('End of shift')
 - units are retained alive when the capacity of pool decreases (this is like their shift ends) and reactivated when capacity recovers.
units are destroyed - once the capacity of pool decreases, all the excess units will be destroyed (and removed from their population, if any), so for the next capacity recovery, brand new units will be created.
Syntax: boolean destroyExcessUnits
Based on attractors
[Visible if capacity is defined By home location] - If selected, the number of resource units in the pool will be equal to the number of attractors inside the node specified as the Home location (nodes) for this resource pool. Otherwise the number of resources is equal to the number of Home location (nodes).
Syntax: boolean capacityBasedOnAttractors
Capacity schedule
[Visible if capacity is defined By schedule] Schedule that defines how the number of resources changes over time (the schedule Type is integer).
Syntax: Schedule<Integer> capacitySchedule
On/off schedule
[Visible if capacity is defined By "on/off" schedule] Schedule that defines how the resources availability changes over time (the schedule Type is on/off).
When the schedule value is off - there are no resources.
When the schedule value is on - there are Capacity when "On" resources.
Syntax: Schedule<Boolean> capacityScheduleOnOff
Capacity when "On" [dynamic]
[Visible if capacity is defined By "on/off" schedule]  The number of resource units in the pool when the schedule value is on.
Value type: int
Default value: 1
Schedules
[Visible if capacity is defined By shifts: group schedules] Several schedules of the integer type.
Syntax: Schedule<Integer>[] shiftGroupSchedules
Shift group sizes { size1, size2,.. }
[Visible if capacity is defined By shift plan] Type the number of resources for each shift ID (delimited with commas).
Syntax: int[] shiftGroupSizes
Schedule of shift group IDs (1, 2,..)
[Visible if capacity is defined By shift plan] Schedule containing IDs of shiftGroups, where 1 = the first shift group.
Use -1 to mark common out-of-shift time when all shiftGroups are off.
Syntax: Schedule<Integer> shiftGroupsPlan
New resource unit [dynamic]
Specify here the type of the resources in this resource pool.
Default value: Agent
Speed
[Visible if the Resource type is Moving] The speed with which resource units move.
Syntax:
double speed
Default value: 10 meters per second
Home location (nodes)
Choose here the node(s) that will be used as the home location(s) for these resources.
Syntax: Node[] homeNodes
Show default animation
[Visible if the Resource type is Static] If selected, and the resources are of default Agent type (not of some user-created custom resource type), the static resources will be animated as small multi-colored circles. This option is mostly used to check that the static resources are correctly placed in the desired node(s).
Default value: true
Shifts, breaks, failures, maintenance...
'End of shift' priority [dynamic]
The priority of the shift schedule. Higher value means higher priority. 
Value type: double
Default value: 100
Local variable: T unit - the resource unit.
'End of shift' preemption policy [dynamic]
Here you can choose whether other tasks may terminate the current task (Terminate option), or not (No preemption option).
Default value: No Preemption (ResourcePool.PP_NO_PREEMPTION)
Local variable: T unit - the resource unit.
'End of shift' may preempt [dynamic]
Sets whether End of shift task may preempt the task currently being executed, if any. In other words, true means that unit will "drop its work" right at the moment of its shift end. If false, then the unit will finish all its tasks with less priority.
Value type: boolean
Default value: false
Local variable: T unit - the resource unit.
Breaks
If selected, the resource units of this pool will have breaks. The breaks are configured using the properties below.
Syntax: boolean enableBreaks
Breaks schedule 
[Visible if Breaks is enabled] - Specify here the name of the schedule that defines the schedule of breaks for this resource pool (the schedule Type should be on/off).
Syntax:
Schedule<Boolean> breaksSchedule
'Break' priority [dynamic]
[Visible if Breaks is enabled] - The priority of the break task. Higher value means higher priority. It will be compared to other task priorities when making decisions what task may preempt other, etc.
Value type: double
Default value: 50
Local variable: T unit - the resource unit.
'Break' may preempt [dynamic]
[Visible if Breaks is enabled] - If selected, break may preempt the currently performed task (if allowed in the task properties & the task priority is lower).
Value type:  boolean
Local variable: T unit - the resource unit.
'Break' preemption policy [dynamic]
[Visible if Breaks is enabled] - Here you can choose whether other tasks may terminate the current break (Terminate option), or not (No preemption option).
Default value: Terminate (ResourcePool.PP_TERMINATE)
Local variable: T unit - the resource unit.
Usage statistics are [dynamic]
[Visible if Breaks is enabled] Here you choose whether you consider breaks time in the collected usage statistics as 'busy' time, 'idle' time, or not take it into account at all.
Default value: not collected (ResourcePool.USAGE_NOT_COUNTED)
Local variable: T unit - the resource unit.
Failures / Repairs
If selected, the resource units of this pool will have failures. The failures are configured using the properties below.
Syntax: boolean enableFailuresRepairs
Initial time to failure [dynamic]
[Visible if Failures / Repairs is enabled] - Time before the first failure.
Value type: double
Default value: uniform( 0, 1000 ) seconds
Local variable: T unit - the resource unit.
Time to next failure [dynamic]
[Visible if Failures / Repairs is enabled] - Time between failures (starts counting from the repair moment).
Value type: double
Local variable: T unit - the resource unit
Repair type
[Visible if Failures / Repairs is enabled] - Here you can choose how you simulate the repair: simply as a delay (Delay option), or as a complex process described by a specific flowchart (Send to flowchart option).
Syntax: repairType
Default value: Delay  (ResourcePool.REPAIR_DELAY)
Task start block (repair) [dynamic]
[Visible if Repair type is defined as Send to flowchart] - ResourceTaskStart block defining the start of the flowchart simulating the resource repair process.
Local variable: T unit - the resource unit.
Time to repair [dynamic]
[Visible if Repair type is defined as Delay] - Time required to fix the failure.
Value type: double
Default value: triangularAV( 10, 0.1 ) seconds
Local variable: T unit - the resource unit.
Usage statistics are [dynamic]
[Visible if Failures / Repairs is enabled] - Here you choose whether you want to consider the failures in the collected usage statistics as 'busy' time, 'idle' time, or not take them into account at all.
Default value: not collected (ResourcePool.USAGE_NOT_COUNTED)
Local variable: T unit - the resource unit
Maintenance
If selected, the resource units of this pool will have maintenance. The maintenance task parameters are configured using the properties below.
Syntax: boolean enableMaintenance
Initial time to maintenance [dynamic]
[Visible if Maintenance is enabled] - Time before the first maintenance.
Value type: double
Local variable: T unit - the resource unit.
Time to next maintenance [dynamic]
[Visible if Maintenance is enabled] - Time between maintenance tasks (starts counting when the maintenance task ends).
Value type: double
Local variable: T unit - the resource unit
'Maintenance' priority [dynamic]
[Visible if Maintenance is enabled] The priority of the maintenance task. Higher value means higher priority. It will be compared to other task priorities when making decisions what task may preempt other, etc.
Value type: double
Default value: 100
Local variable: T unit - the resource unit.
'Maintenance' may preempt [dynamic]
[Visible if Maintenance is enabled] - If selected, maintenance may preempt the currently performed task (if allowed in the task properties & the task priority is lower).
Value type: boolean
Local variable: T unit - the resource unit.
Maintenance type
[Visible if Maintenance is enabled] - Here you can choose how you simulate the maintenance: simply as a delay (Delay option), or as a complex process described by a specific flowchart (Send to flowchart option).
Get value: maintenanceType
Default value: Delay (ResourcePool.MAINTENANCE_DELAY)
Task start block (maintenance) [dynamic]
[Visible if Maintenance type is defined as Send to flowchart] - ResourceTaskStart block defining the start of the flowchart simulating the resource maintenance process.
Local variable: T unit - the resource unit
Maintenance time [dynamic]
[Visible if Maintenance type is defined as Delay] - Maintenance time.
Value type: double
Local variable: T unit - the resource unit
Usage statistics are [dynamic]
[Visible if Maintenance is enabled] Here you choose whether you want to consider maintenance time in the collected usage statistics as 'busy' time, 'idle' time, or not take it into account at all.
Default value: not collected (ResourcePool.USAGE_NOT_COUNTED)
Local variable: T unit - the resource unit
Custom tasks
If selected, you can define more tasks for the resources with ResourceTask blocks. Use this option, when your task cannot be defined with standard patterns provided for Failures, breaks, maintenance.
Syntax: boolean enableCustomTasks
List of tasks
[Visible if Custom tasks is enabled] The list of ResourceTask blocks, defining additional custom tasks for these resources.
Get value:
customTasks
Advanced
Add units to
Here you specify where the units created by this block will be stored: in the default population of root agent, or in some custom population (specified below in the Population property).
Syntax: boolean addToCustomPopulation
Default value: Default population of root agent (false)
Population [dynamic]
[Visible if Add units to: Custom population] The name of the agent population where the units created by this block will be stored.
Value type: AgentList
Local variable: T unit - the resource unit
Force statistics collection
If the option is selected (true), statistics are collected for this and embedded objects, otherwise statistics collection is configured by PMLSettings block (where the default is true).
Syntax: boolean forceStatisticsCollection
Default value: false
Actions
On new unit [code]
Code executed when new resource unit is generated and can be used to do additional setup.
Local variable: T unit - just created resource unit.
On destroy unit [code]
Code executed when a resource unit is destroyed.
Local variables: T unit - the resource unit.
On seize [code]
Code executed when a resource unit is seized.
Local variables: T unit - the resource unit.
                          Agent agent - the agent that seized the unit.
On release [code]
Code executed when a resource unit is released.
Local variables: T unit - the resource unit.
                          Agent agent - the agent.
On wrap up [code]
Code executed when a resource unit is wrapped up.
Local variables: T unit - the resource unit.
                          Agent agent - the agent.
On break start [code]
[Visible if Breaks is enabled] Code executed when a resource unit starts break task.
Local variables: T unit - the resource unit.
On break end [code]
[Visible if Breaks is enabled] Code executed when a resource unit finishes break task.
Local variables: T unit - the resource unit.
On break terminated [code]
[Visible if Breaks is enabled] Code executed when break task is terminated.
Local variables: T unit - the resource unit.
On failure [code]
[Visible if Failures / Repairs is enabled] Code executed on when the failure task starts.
Local variables: T unit - the resource unit.
On repair [code]
[Visible if Failures / Repairs is enabled] Code executed when the repair task ends.
Local variables: T unit - the resource unit.
On maintenance start [code]
[Visible if Maintenance is enabled] Code executed when a resource unit starts maintenance task.
Local variables: T unit - the resource unit.
On maintenance end [code]
[Visible if Maintenance is enabled] Code executed when a resource unit finishes maintenance task.
Local variables: T unit - the resource unit.
On unit state changed [code]
Code executed when a resource unit changes its activity.
Local variables:
T unit - the resource unit.
boolean busytrue if the unit is busy (this doesn't mean that it was idle before), false if idle.
ResourceTaskType type - type of task, if unit is busy, one of: TASK_ENTITY, TASK_END_OF_SHIFT, TASK_WRAP_UP, TASK_BREAK, TASK_REPAIR, TASK_MAINTENANCE, TASK_CUSTOM constants.
Agent agent - agent associated with this resource unit's task. Actual for TASK_ENTITY type (where it is the agent possessing the unit) and for TASK_WRAP_UP (agent which previously used this unit and has recently released it).
ResourceTask task - task descriptor, this can be used in case of TASK_CUSTOM type: there will be a reference to ResourceTask  block which represents the current task of the unit.

Functions

double utilization() - Returns utilization of this resource pool. The returned value is the mean over all individual unit utilization, calculated from the most recent resetStats() call up to current time. If the number and availability of resource units is defined by a schedule, utilization will be calculated only for the operating hours of the corresponding resource unit. 

int idle()- Returns the number of currently idle resource units. (Units out of shift aren't counted).

int busy() - Returns the number of busy units, including those who are in wrap-up/maintenance/break/failure. (Units out of shift aren't counted).

boolean containsUnit(Agent unit) - Checks whether the resource pool contains the specified unit (Returns true, if yes; false otherwise).

void setShiftGroupCapacity(int id, int capacity) - Sets new size of shift group. Doesn't kill excess resource units. Instead assigns Out-of-shift task to them (idle units are the first to be pushed to Out-of-shift, the next are units with less-priority tasks).

int size() - Returns the total number of units in this resource pool (including those that are out of shift).

int sizeActive() - Returns the total number of resource units in the current shift.

int sizeOfShiftGroup(int id) - Returns the total number of units (including those that are out of shift) in the shift group with the given id.
Parameters: id - the id of shift group (1, 2, 3...)

void resetStats() - Resets the statistics collected for this block.

Collection<ResourceRequest> getRequests() - Returns the current queue of requests for resource units of this pool, ordered by their priority.
This list is unmodifiable.