Skip to content
Alejandro Bernardin edited this page Nov 23, 2016 · 43 revisions

PISKa

PISKa is a Parallel Implementation of Spatial Kappa, based on KaSim, a stochastic simulator for rule-based models. With PISKa you can create 'compartments' connected by 'links', and create 'transports' instructions among 'compartments'. This is useful when you have a non homogeneous space. PISKa is highly scalable due to its MPI implementation, which allows you to create many compartments and run your simulation in many cores.

Installation

To install follow the next steps:

As root

  • Install Opam (in Ubuntu 14.04, for other OS visit http://opam.ocaml.org/doc/Install.html)

    add-apt-repository ppa:avsm/ppa

    apt-get update

    apt-get install ocaml ocaml-native-compilers camlp4-extra opam m4

  • and now the next packages

aptitude install libopenmpi1.6

aptitude install openmpi-bin

aptitude install libopenmpi-dev

Now, NOT as root

  • Install OCaml, with opam init --comp 4.02.1

  • opam config env

  • opam install mpi

  • make in PISKa directory

This should produce PISKa binaries. You will need your own plotting program (like gnuplot) to visualize curves.

If make doesn't works (Error: Unbound module Mpi), you should change the path in the Makefile to aims to OCaml mpi, ie,

OCAMLOPT = $(OCAMLBINPATH)ocamlopt.opt -I PATH_TO_YOUR_OPAM_MPI/.opam/SOMETHING/lib/mpi unix.cmxa mpi.cmxa str.cmxa #-p #-g -ccopt -g -ccopt -pg

and run make again.

If you are reinstalling just run:

  • opam config env
  • make in PISKa directory

Now that PISKa is working you can put it in /usr/bin/ directory, so, as root:

cp PISKa /usr/bin/

Usage

In order to run a simulation of 1000 rule applications of 2 compartment, type

mpirun -n 2 PISKa -i piskaFile.cka -t 1000 -p 1000 -sync-t 1

This will produce a data file of 1000 point (-p option) containing the trajectory of 1000 time step (-t) with synchronization time among compartments of 1 time step (-sync-t). The number of process (-n) must be equal to the number of compartments.

Type:

PISKa --help

for a complete list of options.

##New functionality with regard to KaSim:

###Compartment: To create a compartment of name 'compartmentA' and volume 1 we write:

%compartment: 'compartmentA' 1

and a matrix of 4x4 and each compartment of volume 1.5

%compartment: 'compartmentA' [4][4] 1.5

###Link: The link is the connection among compartment, it can be unidirectional or bidirectional. To set an unidirectional link among two compartments we write

%link: 'link_name' 'compartmentA' -> 'compartmentB' $ 1

where only the agents presents in 'compartmentA' can travel to 'compartmentB' with a delay time of 1. We can assume the delay time among compartment as the travel time. To set a bidirectional link we write

%link: 'link_name' 'compartmentA' <-> 'compartmentB' $ 1

where agents in both compartment can move in any direction.

*The unit of time is defined in the model by the rates, it can be seconds, weeks, years, etc.

###Transport: The transport defines a rate of agents per unit of time traveling in a link. To set a rate of 1.3 to agent 'agentA()' in a link called 'link_name' we write

%transport: 'link_name' agentA() @ 1.3

and if we want to move joints or separated agents we write

%transport: <move-join> 'link_name' agentA() @ 0.2

%transport: <move-free> 'link_name' agentB() @ 0.7

where agentA will move with any agent join to it and agentB will separate and move alone. If you don't use the <move-join/free> option, by default is (CHECK)

###Use: The use instruction is to define the compartment that will be used, and set the initial conditions of it. If we want to initialize a compartment we write

%use: 'compartmentA'
%init: 100 agentA() #define the number of agents

where we initialize the compartmentA with 100 agents of name 'agentA()'. The instruction must go immediately after the instruction %use.

If the agents are initialized with no states in its sites, the default state will be the first define state. For example:

%agent: person(c~S~I)
%use: 'compartment1'
%init: 300 person()

will create 300 agent 'person' in state 'S', the first define state.

###Precompiled binaries files PISKa is able to create precompiled files to run faster simulations, saving time in system initialization. In this way you create a precompiled file, then load this file and change only parameters of interest. To create a precompiled file you should use the -make-sim option, and to load -load-sim. example:

mpirun -n 2 PISKa -i piskaFile.cka -make-sim precomp_file.out

where precomp_file.out is the precompiled binary file. Then, to load we use

mpirun -n 2 PISKa -t 1000 -p 1000 -sync-t 1 -load-sim precomp_file.out

in this way the system will not initialize again, saving that time. Using this option you can save about 20% of simulation time, depending on your model. Now, if you want to change some parameters of the precompiled file, you can create a perturbation file parameters.cka, and use it in this way

mpirun -n 2 PISKa -t 1000 -p 1000 -sync-t 1 -load-sim precomp_file.out -i parameters.cka

###Fixed rates in rules If you want to fix a rate, ie, you don't want it depends on the volume of a compartment, you use @*, for instance

'ruleName' agentA(),agentB() -> agentC() @* 1.5

will fix the rate of this rule at 1.5, independently of the size of compartment.

##Kappa Syntax The next information is available in KaSim/Kappa documentation, but we put here a brief resume to a fast implementation of a model in PISKa.

###Agent We define an agent in the following way

%agent: AgentName(site1~STATE1~STATE2, site2~STATE1, site3)

that mean the agent 'AgentName' has 3 sites, the first site is called 'site1' and has 2 possibles states, STATE1 and STATE2. Equal to site2. The third site 'site3' has no states.

###Agents binding We can joint two agents, binding by a site, in the following way

agentA(s~T, c!1), agentB(s~U, d!1)

that means that agentA and agentB are binding each other by the c and d site respectively. The sign ! and it consecutive number makes the binding.

###Rules The rules are what governs the agents interactions. A rules syntaxs is given by

'ruleName' agentA(),agentB() -> agentC() @ 1.5

in this case agentA and agentB joint and create the agentC with a rate of 1.5. In an other example we have

'ruleName' agentA(c~A), agentB(c~B) -> agentA(c~B), agentB(c~B) @ 0.5

where the interaction among agentA and agentB change the state of site c (from A to B) of agentA with a rate of 0.5. If the rate is replaced with an '[inf]', the reaction will always occur. Note that the rules are commutatives, ie,

'ruleName' agentA(),agentB() -> agentC() @ 1.5

is equal to

'ruleName' agentB(),agentA() -> agentC() @ 1.5

so you don't have to define two operations.

###Variables We can define some variables in the following way

%var: 'varName' 50

which is the same to varName=50. We can also do something like

%var: 'agentNumberA' agentA()

where we are defining agentNumberA equals to the number of agents with name agentA.

###Observable We can define the output of our simulation in the following way

%obs: 'varOutName' agentA(c~S)

this will show in a column the numbers of agents with name agentA and site c in state S. This can be done with many agents

%obs: 'varOutNameA' agentA(c~S)
%obs: 'varOutNameB' agentB(c~R)

and it will display two columns with the respective number of agents in its respective states.

###Perturbation language (Modifications, kind of scripting)

%mod:

In this link there is a very detailed description of the perturbation language.

You can find a more detailed description about kappa language here:

http://www.kappalanguage.org/syntax.html

and you can also read the KaSim manual here in pdf or here in html.

##Example Here we present a little and simple example of PISKa. It represent how an infection is spread in a population, with no control. This is an incomplete model, but it is useful to understand how to implement something in PISKa. For a complete model visit the folder PISKa/models/predator/ in the source code.

#We create 2 cities, the first with volume 1 and the second with volume 2
%compartment: 'cityA' 1 
%compartment: 'cityB' 2

#Here we create a bidirectional connection between cityA and cityB, with delay time 1
%link: 'highway' 'cityA' <-> 'cityB' $1

#We define who can transport between cities and how often. In this case all persons
#can travel between cityA and cityB through the link 'highway', with a rate of 0.01
%transport: 'highway' person() @ 0.01

#We create an agent person with a site 's' (it can be any letter) with states 
#S (susceptible) and I (infected) 
%agent: person(s~S~I)

#Rules
#We define that when 2 person meet, one in state 'S' and other in state 'I', then 
#the person in state 'S' will become 'I' with a rate of 0.001
'contact1' person(s~S), person(s~I) -> person(s~I), person(s~I) @ 0.001

#Now we initialize the cities
#First cityA, with 1000 healthy people and 1 infected
%use: 'cityA'
%init: 1000 person(s~S)
%init: 1 person(s~I)

#Now the cityB, with 1500 healthy people and no one infected
%use: 'cityB'
%init: 1500 person(s~S)

#And finally we define the output variables
%use: 
%obs: 'person_S' person(s~S)
%obs: 'person_I' person(s~I)

Now to run this simulation we execute:

mpirun -n 2 PISKa -i simple_example.cka -t 100 -p 100 -sync-t 1

where -n 2 is the number of cities (and processors where it will run), -i is the input file that we called, in this case, 'simple_example.cka', -t 100 is the simulation time, -p 100 are the points that will be saved in the output file and -sync-t 1 is the synchronization time among compartments.

##ERRORS ExceptionDefn.Semantics_Error(_, "Rule name Transport 1 superman() at 1.393503 (2,1) is already used") If this happens, the agent traveling by the link will be destroyed, so now there is one less agent. Should be fixed.

When reading parameters of a perturbation the program will freeze if there is a ";" at the end. There is no, still, warning message about this.

Clone this wiki locally