Agent Based Modelscoensys1.jpg (67398 bytes)
About Us Services Share-a-space AnyLogic Consulting Projects What's New Links Contact Us Opportunities Site Map

Coensys, Inc.

 

Home
Up

Agent Based Modeling (ABM) Using AnyLogic 6

 Anylogic can be used to develop agent based models (ABM). Agent Based Modeling arose out of the work on complex Adaptive Systems (CAS) at Santa Fe Institute. In ABM (Agent Based Modeling), the focus is on global behavior (of a system of individual agents) arising from local rules and interactions of individual agents. In ABM, focus is on individual agents, their rules, their behaviors, and their interactions with each other and the environment. Collectively agents may exhibit emergent behaviors such as self organization. Since agents do not follow a pre-scripted flow (as in Discrete Event) and their structure is not pre-specified at the global/aggregate level (as in System Dynamics), they can exhibit novel or surprising behaviors that were not anticipated during design. ABM is a great methodology for exploring non-linear, dynamic environments. ABM is also well suited for situations with no precedent or where past data or experience does not exist. When combined with data and data analytics, ABM forms one of the most powerful predictive analytics / forecasting methodology.

Some key characteristics of Agent Based Models are:

  • Complex, real-world systems are modeled as collections of autonomous decision-making entities, called “agents” 
  • These models are highly distributed in nature
  • There is no centralized control or planning required
  • The agents follow a few simple rules and have bounded rationality
  • Agents can be heterogeneous
  • Agents can be connected via networks (for example, social networks or scale-free networks)
  • Agents can be located in a geo-spatial or discrete (like cellular automata) environment
  • Agents only require local knowledge and visibility
  • Interactions between these agents result in complex emergent global behavior 
  • Behavior exhibits dynamic-equilibrium and adaptation
  • Agents can communicate with each other directly or through the environment (stigmergy)
  • This is often called “generative” or “bottom-up” modeling

 

Use Agent Based Modeling when:

  • The system has a lot of interconnected components
  • Environment is dynamic and uncertain
  • Agents exhibit autonomous behavior, bounded rationality, biases
  • Want to explore cascading effects, network effects, unintended consequences
  • Want to explore novel situations or effectiveness of novel interventions
  • Want to explore stability and failure modes of complex systems
  • Want to design robust systems or robust optimal behavior
 

Anylogic supports agents in a continuous or discrete environment. Agents can form social networks with other agents, can communicate and send messages to each other, can move in space, have states, and follow rules.

Click here to see an example of a dynamic network simulation.

Anylogic supports sophisticated animation capabilities to visualize agent behaviors.

 

Agent Based Modeling with Anylogic 6

Although you can find a number of various definitions of Agent Based Modeling in the literature, from the viewpoint of practical applications agent based modeling can be defined simply as essentially decentralized, individual-centric (as opposed to system level) approach to model design. When designing an agent based model the modeler identifies the active entities, the agents (which can be people, companies, projects, assets, vehicles, cities, animals, ships, products, etc.), defines their behavior (main drivers, reactions, history, ...), puts them in a certain environment, maybe establishes connections, and runs the simulation. The global (system-level) behavior then emerges as a result of interactions of many individual behaviors. AnyLogic supports Agent Based modeling (as well as Discrete Event and System Dynamics Modeling) and allows you to efficiently combine it with other approaches.

Before deciding to use the agent based approach you should investigate the problem and verify whether traditional approaches can be used. For example, if the system you are modeling fits well with the process flow paradigm (i.e. can be described as a sequence of operations on essentially passive entities) it may be beneficial to use AnyLogic Enterprise Library objects instead of specifying individual behaviors of those entities. Similarly, if the entities in your system have no individuality (no individual history, timing, etc.) it may be worth applying System Dynamics approach. 

Agent based models, especially practically useful, are very diverse, and it would be impossible to develop a universal "Agent Based Library" and reduce the modeler's work to a number of drag-and-drop operations. There are however some reusable "design patterns" that simplify development of agent based models and are directly supported by AnyLogic. These patterns are in:

·             Model architecture

·             Agent synchronization ("steps")

·             Space (continuoius or discrete), mobility and spatial animation

·             Agent connections (networks, e.g. social networks) and communication

·             Dynamic creation and destruction of agents

From architectural viewpoint, a typical AnyLogic agent based model would have at least two active object classes: Main class for a top-level object where agents would be contained and a class for an agent, e.g. Person. The Person class in most cases would be declared as Agent - this is a special subclass of ActiveObject class that extends the latter with services useful for agent based modeling. A number of agents would be embedded into the Main object, e.g. as a replicated object people of type Person. One or more Environment constructs may be defined at the level of Main to specify properties shared by the agents. You are free however to define other hierarchies in your agent based model, for example you may have companies-agents that contain employees-agents and communicate with consumers-agents.

 

Environment

In AnyLogic environment is a special construct that is used to define the properties common to a group of agents. Although you do not have to define the environment in your agent based model, most of agent-specific functionality is available through and with the help of environment. There can be more than one environment in your model; environments can be hiererchically organized (for example, agents-companies can live in one environment and agents-eployees can live in local company environments). An agent can belong to at most one environment. Typically, you would have the environment construct defined at the Main level - at the same place where agents are embedded. To register the agent/replicated agent with the environment you must specify the environment at each agent instance.

 To add an environment

1.       Choose the Environment  element from the Model page of the Palette view.

2.       Click in the graphical editor where you want to place the environment object.

  To set the environment for an agent

1.       On the General page of the embedded object (agent instance) Properties specify the appropriate environment object in the Environment field

Please note that this field is enabled only if the active object class of the agent has been declared as Agent.

Accessing the agents in the environment

The first thing environment gives you is the ability to access (e.g. iterate through or send messages to) all agents registered with the environment in a uniform way (no matter whether they belong to same or different replicated or not replicated embedded active objects). This is the API:

class AgentCollection extends AbstractCollection<Agent> - a special collection class that allows to to iterate through all agents and retrieve them by index

AgentCollection getAgentCollection() - returns the collection of all agents in the environment

size() - returns the number of agents in the environment

Agent getRandomAgent() - returns a randomly chosen agent

deliverToAll( Object msg ) - immediately delivers a message to all agents in the environment

deliverToRandom( Object msg ) - immediately delivers a message to a randomly chosen agent

A typcial code that you would write in order to perform e.g. a specific action over all agents is this:

for( Agent a : environment.getAgentCollection() )

a.<action>;

Agent synchronization

Environment takes care of agent synchronization if you wish to have discrete time steps in your model. For more information on this topic see Agent Synchronization.

Space

Environment is responsible for maintaining space in the model. While in the case of continuous space the only thing it does is creation of various layouts (the related API and properties are described in Continuous space section), in discrete space it keeps track of which agent is in which cell and hase some additional API:

int[] findRandomEmptyCell() - returns coordinates {row,column} of a pseudo-randomly located empty cell, or null if all cells are occupied

Agent getAgentAtCell( int r, int c ) - returns the agent that occupies a given cell, or null if the cell is empty

Networks

Environment can create networks oif several types. The corresponding API and properties are described in Agent Connections and Networks section.

 

 

Agent

Agent in Agent Based Modeling is a unit of model design that can have behavior, memory (history), timing, contacts, etc. Agents can represent people, companies, projects, assets, vehicles, cities, animals, ships, products, etc. AnyLogic ActiveObject class is a natural basis for developing agents as it has all necessary properties: within an active object you can define variables, events, statecharts, System Dynamics stock and flow diagrams, you can also embed other active objects, in particular process flowcharts built with AnyLogic Enterprise Library. You can define as many active object classes in your model as there are different types of agents.

Typically, you would embed agents into a higher level object (such as Main), and in most cases they are embedded as replicated: replication allows you to create as many agents as you need (the number can be a parameter), and also gives you an easy way to dynamically create and destroy them.

Design of an agent typically starts with identifying its main drivers and interface with the external world. If you plan to create agent networks graphically using drag and drop (this may make sense for small networks with fixed connections, such as supply chains), you can use ports as agent interface points. In case of large number of agents with dynamic connections (such as social networks) agents can communicate by calling methods of each other or through the environment.

The agent internal state and behavior can be implemented in a number of ways. The state (the accumulated history) of the agent can be represented by a number of variables, by the statechart state, etc. The behavior can be so to say passive (e.g. there are agents that only react to message arrivals or to method calls and do not have their own timing), or active, when internal dynamics (timeouts or system dynamics processes) of the agent causes it to act. In the latter case agents most probably would have event and/or statechart objects inside.

To access AnyLogic services specifically designed for agent based modeling, you need to declare your active object as Agent.

  To declare an ActiveObject class as Agent

1.       On the General page of the active object class Properties check the Agent checkbox.

The icon of the active object class then changes to .

By doing that you tell AnyLogic that your active object class is a subclass of AnyLogic built-in class Agent, which extends the class ActiveObject. The class Agent provides the following services via its API and also at the Agent page of its Propeties tab that becomes available once you check the Agent checkbox:

·             Allows different agents to share the same environment. The environment is specified at the instances of the active object class (i.e. where it is embedded)

·             Enables you to introduce discrete steps to synchronize agent actions

·             Supports agent movement in 2D continuous space or 2D discrete space (on a grid)

·             Supports agent connections and networks

·             Supports agent communication via message passing.

If none of the above features are needed for your agents, and also if you plan to create very large numbers of agents you may consider to leave your agents as regular active objects (i.e. leave the Agent checkbox unchecked) because agent-specific funstionality consumes some additional memory (36+ bytes per agent).

 

 

 

 

Dynamic Creation and Destruction

AnyLogic gives you the ability to dynamically create and destroy active objects, in particular agents. To enable dynamic creation or destruction, the active object must be declared as replicated where it is embedded (even if you expect to create only one instance of it). The Replication field in the embedded object properties is used to specify the initial number of instances that will be created when the container object is created and can be 0 if you do not want any instances at that time.

Assume you have declared a replicated object people of type Person within the Main object. Then AnyLogic automatically generates two methods (at the Main level) for adding and removing instances to that replicated object during the model execution:

Person add_people() - this method adds a new object of type Person to the replicated object (and return it so you can do additional setup), and

void remove_people( Person personToRemove ) - this method removes the given object from the replication and destroys it.

Please note that the methods are generated into the Main class, so they can be called directly from anywhere in Main (e.g. from an event Action code, from Startup Code etc.). Should you need to create or destroy an active object from another such object or from itself, you have to access the Main object first. For example, if a person gives birth to another person, you should write within the "parent" person:

get_Main().add_people() or, equivalently, ((Main)getOwner()).add_people();

Another frequently used pattern: an object wishes to destroy itself:

get_Main().remove_people( this );

If the (dynamically created or destroyed) embedded object has ports or variables connected to ports or variables of other objects, these connections will be automatically established when a new instance is added and broken when an instance is destroyed.

 

 

 

Agent Synchronization

AnyLogic supports synchronous, asynchronous and mixed modeling. Asynchronous modeling means truly continuous time axis and ability to schedule events at arbitrary time moments and execute continuous processes such as System Dynamics ones. Synchronous modeling assumes discrete time steps and agents (and maybe environment) executing their actions synchronously at these time steps. While in most cases asynchronous models are closer to reality and also computationally more efficient (no "empty" steps are done), sometimes the problem is best solved with synchronized model (this is true for many academic models and for those real-world systems where decisions are made regularly at discrete time points, e.g. every day or every month).

You can implement synchronization "manually" or you may use AnyLogic services provided by environment and Agent constructs. The simplest manual implementation would be the this: at the Main object (or other agent container) you create a cyclic timeout event with timeout 1 and the following action code:

for( Person p : people )
    p.step();

where Person is the active object class of your agents, people is its replicated instance in Main , and step() is the method of class Person.

Alternatively you can utilize AnyLogic built-in support for agent synchronization. Assume you have declared your active object class Person for agents as Agent, defined environment object at Main and specified that embedded object people belongs to the environment.

  To add synchronization to your agent based model

1.       On the General page of the environment Properties check the checkbox Enable Steps. The default step duration is 1 time unit but may be changed (use field Step duration)

2.       In the fields On before step and On after step on the same page write actions that you wish be executed before and after all agents perform their individual steps, if any

3.       On the Agent page of active object class Person Properties specify actions On before step and On step (obviously, you may leave any fields empty).

The following execution order is guaranteed at the time moments 0, 1, 2, 3, ...: 

1.       On before step action of the environment is executed

2.       On before step actions of all agents are executed in some deterministic order

3.       On step actions of all agents are executed in same deterministic order

4.       On after step action of the environment is executed

Typically, the two phases of environment action are used to prepare the model for a step and to wrap up a step, e.g. update statistics. The two phases of agent action are used to collect information and to make and apply the decisions. For example, in the well-known Game of Life every cell would count the alive neighbor cells in On before step and change its state in On step.

By adding such synchronization you do not restrict the dynamics of your model with discrete time steps. Your agents as well as other objects are still able to schedule events, execute state transitions and run other processes - this will go in parallel with steps execution.

 

 

 

Continuous Space

AnyLogic supports two-dimensional continuous and discrete space types for agents. The 2D continuous space support includes ability to set and retrieve the current agent location, to move the agent with the specified speed from one location to another, to execute action upon arrival, to animate the (static or moving) agent at its location, to establish connections based on agents layout, and other useful services. To utilize them you need to declare your active object class as Agent (see Agent). Part of continuous space functionality does not even require the agents to belong to an explicitly specified environment - without the environment the default space type assumed is continuous 2D space (but if the agents belong to an environment its space type should be set correspondingly).

  To set the environment space type to continuous

1.       On the Advanced page of the environment Properties set Space Type to Continuous.

The space dimensions specified on the same page (Width and Height) are only used to lay out agents when any of the standard layout types are applied and do not restrict the agents mobility.

Location of an agent in 2D continuous space is defined by two coordinates (x,y) of Java type double.

Initial locations of agents. Layouts

The initial location can either be defined "centrally" by environment or specified at the agent class. 

  To define the initial layout of all agents via environment

1.       On the Advanced page of the environment Properties choose the Layout type and, unless you have chosen the User-defined layout, check the Apply on startup checkbox

2.       On the Agent page of the agent class Properties check the Environment defines initial location checkbox

The User-defined layout type assumes you will take care of the agent locations yourself in e.g. Startup code of the Main object. The standard continuous layouts supported by AnyLogic are:

Random (Environment.LAYOUT_RANDOM) - an agent location is chosen randomly and uniformly within the space dimensions

Arranged (Environment.LAYOUT_ARRANGED) - the agents are arranged within the space dimensions

Ring (Environment.LAYOUT_RING) - the agents are uniformly distributed on a ring whose diameter is smaller than the smallest space dimension

Spring mass (Environment.LAYOUT_SPRING_MASS) - the agents are located as a spring mass system where agents are masses and their connections are springs. This is network-dependent layout type

You can change the layout type dynamically while the model is running using the environment API, for example:

environment.setLayoutType( type ); //this will just set the default type of layout, the agents will not get relocated
environment.applyLayout(); //this will relocate the agents according to the layout type currently set.

The type parameter can take one of the above constants or Environment.LAYOUT_USER_DEFINED.

  To set the agent initial location via the agent class

1.       On the Agent page of the agent class Properties uncheck the Environment defines initial location checkbox

2.       Specify X and Y on the same page.

Moving and jumping

Agent class has a rich API for moving in 2D continuous space. First, there are methods to obtain the current location and distance (these methods work when the agent is moving as well):

double getX() - returns the current X coordinate of the agent

double getY() - returns the current Y coordinate of the agent

double distanceTo( Agent other ) - returns the distance to a given other agent

Then there is a set of methods for relocating the agent and getting the related information:

jumpTo( double x, double y ) - immediately places the agent at a given location

moveTo( double x, double y ) - starts moving to the given target location along the shortest straight line. The movement will go at the given Velocity (which however can be changed dynamically). The agent will execute On Arrival action when (and if) it reaches the target location

stop() - stops the agent (if it was moving) and leaves it at the current location. On Arrival is not executed

boolean isMoving() - tests if the agent is currently moving

double getTargetX() - returns the x coordinate of the target location if the agent is moving, and its current x otherwise

double getTargetY() - returns the y coordinate of the target location if the agent is moving, and its current y otherwise

double getVelocity() - returns the current velocity of the agent (velocity is a parameter of the agent, its "cruising speed", non-zero velocity does not mean the agent is moving)

double getHeading() - returns the current heading (orientation) of the agent in radians, 0 is 3 o'clock, clockwise. When the agent starts moving, its heading is set in the direction of movement.

double timeToArrival() - if the agent is moving, returns the remaining time to arrival assuming the velocity will not change. If the agent is not moving, returns 0

setVelocity( double newVelocity ) - sets the velocity ("cruising speed") of the agent. If the agent is moving, it will continue moving from the current location with the new velocity. If the agent is not moving, it will not start moving until you call moveTo()

setHeading( double newHeading ) - sets the heading (orientation) of the agent. Will be overridden in a subsequent call of moveTo(), which you can in turn override by calling setHeading() after moveTo()

  To set the initial velocity and heading of the agent

1.       On the Agent page of the agent class Properties specify Velocity and Heading in the Movement parameters section

  To define the action that should be executed when the agent reaches the target location after moveTo() has been called

1.       On the Agent page of the agent class Properties enter the corresponding code in the On Arrival field

While the agent is moving, its presentation will also be animated as moving and will always be at its current position (x,y) relative to its origin. This means that if in design time the agent's presentation was placed at (50,100) on the container (e.g. Main diagram) and the current location of the agent is (17,64), the agent will be shown at (67,164). The rotation of the agent's presentation is always set to its heading. Note that if you have several embedded objects representing agents living in the same space, you need to place their (embedded) presentations at the same location on the container diagram to get a consistent picture.

Although AnyLogic directly supports movement at a constant speed and zero acceleration, you can model acceleration/deceleration by changing the velocity at the appropriate time moments. You can use statechart with states like Static, Slow, Medium, Fast, etc and timeout transitions to control the motion.

 

 

 

Discrete Space

AnyLogic supports two-dimensional continuous and discrete space types for agents. The 2D discrete space is a rectangular array of cells fully or partially occupied by the agents. There can be at most one agent in one cell. AnyLogic support for this kind of space includes agent distribution over the cells, moving to a neighboring cell or jumping to arbitrary cell, finding out who are the agent's neighbors (with respect to the neighborhood model), finding empty cells, and other useful services. To utilize these services you need to declare your active object class as Agent (see Agent), and put it into the environment whose space type is discrete.

  To set the environment space type to discrete

1.       On the Advanced page of the environment Properties set Space Type to Discrete

The space dimensions (the number of Columns and Rows) are specified on the same page. The Width and Height fields will then be used to visualize the space. For example, if the space has 100x100 cells and its width and height are 500x500, then each cell will have the size of 5x5 when displayed.

Location of an agent in 2D discrete space is defined by two coordinates (row,column) of Java type int.

Should you need a different space functionality for your model, you can build it either on top of this standard discrete space or you can implement your own space.Examples:

·             If you wish to have a torus space instead of a rectangular one, you can override the corresponding methods for moving and getting neighbors

·             If you need multiple agents per cell, you can either use standard space and have a static "container" agent in every cell or you can implement cells from scratch in your Main object

·             If you need additional information to be associated with each cell (such as altitude, vegetation, etc.), you may define a two-dimensional array (line double[][] altitude) at the Main level and let the agents to read and write to it as they are simulated.

Initial locations of agents. Layouts

The initial location can either be defined "centrally" by environment or specified at the agent class. 

  To define the initial layout of all agents via environment

1.       On the Advanced page of the environment Properties choose the Layout type and, unless you have chosen the User-defined layout, check the Apply on startup checkbox

2.       On the Agent page of the agent class Properties check the Environment defines initial location checkbox

The User-defined layout type assumes you will take care of the agent locations yourself in e.g. Startup code of the Main object. The standard discrete layouts supported by AnyLogic are:

Random (Environment.LAYOUT_RANDOM) - the agents are randomly distributed over the cells (with at most one agent per cell)

Arranged (Environment.LAYOUT_ARRANGED) - the cells are filled by the agents left to right and top down.

You can change the layout type dynamically while the model is running using the environment API, for example:

environment.setLayoutType( type ); //this will just set the default type of layout, the agents will not get relocated
environment.applyLayout(); //this will relocate the agents according to the layout type currently set.

The type parameter can take one of the above constants or Environment.LAYOUT_USER_DEFINED. Please note that if the number of agents exceeds the number of cells, a runtime error will occur.

  To set the agent initial location via the agent class

1.       On the Agent page of the agent class Properties uncheck the Environment defines initial location checkbox

2.       Specify Column and Row on the same page.

Moving and Jumping

AnyLogic class Agent offers the following API for moving in 2D discrete space:

int getR() - returns the row of the agent's current cell

int getC() - returns the column of the agent's current cell

jumpToCell( int r, int c ) - puts the agent to the cell with the specified coordinates, raises a runtime error if the cell is occupied

moveToNextCell( int direction ) - puts the agent into a neighboring cell in the specified direction (see below the possible direction values)

int[] findRandomEmptyCell() - returns coordinates {row,column} of a pseudo-randomly located empty cell, or null if all cells are occupied

boolean jumpToRandomEmptyCell() - puts the agent into a pseudo-randomly located empty cell, returns false if all cells are occupied

The term "pseudo-randomly" in the methods described above means the following: for performance purposes, the algorithm of finding an empty cell may pick among the set of empty cells with not always equal probabilities. The less populated is the space, the more fair is the choice.

The direction parameter may take the following values: NORTH, SOUTH, EAST, WEST, NORTHEAST, NORTHWEST, SOUTHEAST, SOUTHWEST.

The agent's presentation will be animated at the position of its current cell relative to its origin. This means that if in design time the agent's presentation was placed at (50,100) on the container (e.g. Main diagram) and if the current cell of the agent in in row 10 and column 20 and the cell dimension is 5 x 5, the agent will be shown at ( 50 + 10*5, 100 + 20 *5), i.e. at (100, 200). Therefore if you have designed some graphical background for your space, it makes sense to put the embedded agent presentation at the top left corner of it.

Neighbors. Neighborhood models

An agent can find out who are in the cells nearby or who lives in a particular cell:

Agent getAgentAtCell( int r, int c ) - returns the agent that occupies a given cell, or null if the cell is empty

Agent getAgentNextToMe( int dir ) - returns the agent in a neighboring cell in the specified direction (see above the possible direction values)

You can set a neighborhood model that will determine the way the agent neighbors are defined. There are two options:

Moore model (Environment.NEIGHBORHOOD_MOORE) - the neighbors are counted in 4 cells to the NORTH, SOUTH, EAST, and WEST only

Euclidean model (Environment.NEIGHBORHOOD_EUCLIDEAN) - the neighbors are counted in all 8 cells (to the NORTH, SOUTH, EAST, WEST, NORTHEAST, NORTHWEST, SOUTHEAST, SOUTHWEST)

  To set the neighborhood model

1.       On the Advanced page of the environment Properties choose the appropriate Neighborhood type 

The neighborhood model will affect the result of the following method:

Agent[] getNeighbors() - returns the array of agents in the cells that are counted as neighbors

and also the methods send() and deliver() if they are called with ALL_NEIGHBORS or RANDOM_NEIGHBOR parameter (see Agent communication).

 

 

 

Agent Connections and Networks

The interaction of agents in agent based models can be implemented in many different ways (see Agent communication). If relations between agents are more or less persistent, an agent needs to remember one or several other agents. The meaning of these relations can be e.g.: friend, colleague, parent, child, owner, etc. One way of keeping references to other agents is to store them in plain variables or in collections. For example, if a person has parents, spouse and children, then the corresponding agent can have these references:

Person father
Person mother
Person spouse

<collection of type
Person> children

These references can be set when the agents are created or dynamically during simulation.

For "flat" relation types such as friends, social contacts, etc. AnyLogic has built-in support. Any agent (active object declared as Agent) can have a number of connections - references to other agents in the same environment. These connections are always bi-directional: if agent A has B in his list of connections then B also has A. The connections can be managed manually via agent API and/or setup automatically by the environment. The API related to connections is the following:

LinkedList<Agent> getConnections() - returns the list of all connected agents, or null if there have been no connections established

int getConnectionsNumber() - returns the number of connected agents

Agent getConnectedAgent( int index ) - returns the connected agent with the given index

connectTo( Agent a ) - adds a given agent to the connections of this agent and vice versa

boolean isConnectedTo( Agent a ) - tests if this agent is connected to a given agent

boolean disconnectFrom( Agent a ) - disconnects this agent from a given other agent, returns false if the agents were not connected

disconnectFromAll() - disconnects the agent from all other agents

The list of connections is used when the agent calls its send() or deliver() methods with ALL_CONNECTED or RANDOM_CONNECTED parameters, see Agent communication.

Networks

Several types of agent networks are directly supported by AnyLogic. They are:

Random (Environment.NETWORK_RANDOM) - agents are connected randomly with a given average number of connections per agent

Distance based (Environment.NETWORK_ALL_IN_RANGE) - any two agents are connected if distance between them is less than a given maximum (in continuous space only)

Ring lattice (Environment.NETWORK_RING_LATTICE) - agent connections form a ring where an agent is connected to a given number of closest agents

Small world (Environment.NETWORK_SMALL_WORLD) - can be considered as ring lattice where some links have been "re-wired" to long-distance agents

Scale free (Environment.NETWORK_SCALE_FREE) - some agents are "hubs" with a lot of connections and some are "hermits" with few connections

The network types and parameters are set at the environment.

  To define the network type

1.       On the Advanced page of the environment Properties choose the Network type

2.       If you wish this network to be constructed when the model starts, check the Apply on startup checkbox

3.       Specify the network parameter that apply

The network type can also be set dynamically during simulation via the environment API, for example:

environment.setNetworkRingLattice( 5 ); //this will just set the default type of network, the agents will not get (re)connected
environment.applyNetwork(); //this will (re)connect the agents according to the network type currently set.

 

 

 

Communication between Agents

First of all, you are free to use any regular AnyLogic inter-object communication facilities for your agents: calling methods, sending messages via ports, linking continuously changing variables, etc. In that case you do not even need to declare your active objects as Agent and have them in the sane environment. If you do that howvever, you enable yet one more way of agent communication: message passing via environment. This type of communication offers several methods for sending messages:

send( Object msg, Agent dest ) - sends the message to the explicitly specified agent

send( Object msg, int mode ) - sends the message to one or group of recipients, subject to mode

deliver( Object msg, Agent dest ) - immediately delivers the message to the explicitly specified agent

deliver( Object msg, int mode ) - immediately delivers the message to one or group of recipients, subject to mode

The difference between send() and deliver() is the following: send() schedules the mesage delivery/reception in a separate event that will be execued after the current event in 0 time, while deliver() executes the delivery/reception directly inside its body. If the recepients may try to communicate other agents during incoming message handling, using deliver() may cause undesirable loops, and it is recommended to use send(). The mode parameter may have the following values:

ALL - the message will be delivered to all agents in the environment

ALL_CONNECTED - the message will be delivered to all connected agents

ALL_NEIGHBORS - (in discrete space only) the message will be delivered to all agents in the neighboring cells, subject to the current neighborhood model

RANDOM - the message will be delivered to one randomly chosen agent in the environment

RANDOM_CONNECTED - the message will be delivered to one randomly chosen connected agent, if any

RANDOM_NEIGHBOR - (in discrete space only) the message will be delivered to one randomly chosen neighbor, subject to the current neighborhood model

Once the message is delivered a destination agent, its action dode is executed, if defined.

  To define agent's reaction on message arrival

1.       On the Agent page of the active object class Properties enter the corresponding code in the On Message Received section. Use msg to access the received message (of type Object) and sender to access the sender Agent (may be null if the message was sent centrally via environment).

If, for example, you want to forward the message to a statechart inside the agent, you need to type there:

statechart.receiveMessage( msg );

For more information on the Agent API please see its Java doc.