-
Notifications
You must be signed in to change notification settings - Fork 73
/
example6DynamicCallingMutualInfo.py
113 lines (102 loc) · 5.8 KB
/
example6DynamicCallingMutualInfo.py
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
##
## Java Information Dynamics Toolkit (JIDT)
## Copyright (C) 2012, Joseph T. Lizier
##
## This program is free software: you can redistribute it and/or modify
## it under the terms of the GNU General Public License as published by
## the Free Software Foundation, either version 3 of the License, or
## (at your option) any later version.
##
## This program is distributed in the hope that it will be useful,
## but WITHOUT ANY WARRANTY; without even the implied warranty of
## MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
## GNU General Public License for more details.
##
## You should have received a copy of the GNU General Public License
## along with this program. If not, see <http://www.gnu.org/licenses/>.
##
# = Example 6 - Mutual information calculation with dynamic specification of calculator =
# This example shows how to write Python code to take advantage of the
# common interfaces defined for various information-theoretic calculators.
# Here, we use the common form of the infodynamics.measures.continuous.MutualInfoCalculatorMultiVariate
# interface (which is never named here) to write common code into which we can plug
# one of three concrete implementations (kernel estimator, Kraskov estimator or
# linear-Gaussian estimator) by dynamically supplying the class name of
# the concrete implementation.
from jpype import *
import random
import string
import numpy
import readFloatsFile
import os
# Change location of jar to match yours (we assume script is called from demos/python):
jarLocation = os.path.join(os.getcwd(), "..", "..", "infodynamics.jar");
if (not(os.path.isfile(jarLocation))):
exit("infodynamics.jar not found (expected at " + os.path.abspath(jarLocation) + ") - are you running from demos/python?")
# Start the JVM (add the "-Xmx" option with say 1024M if you get crashes due to not enough memory space)
startJVM(getDefaultJVMPath(), "-ea", "-Djava.class.path=" + jarLocation)
#---------------------
# 1. Properties for the calculation (these are dynamically changeable):
# The name of the data file (relative to this directory)
datafile = '../data/4ColsPairedNoisyDependence-1.txt'
# List of column numbers for univariate time seres 1 and 2:
# (you can select any columns you wish to be contained in each variable)
univariateSeries1Column = 0 # array indices start from 0 in python
univariateSeries2Column = 2
# List of column numbers for joint variables 1 and 2:
# (you can select any columns you wish to be contained in each variable)
jointVariable1Columns = [0,1] # array indices start from 0 in python
jointVariable2Columns = [2,3]
# The name of the concrete implementation of the interface
# infodynamics.measures.continuous.MutualInfoCalculatorMultiVariate
# which we wish to use for the calculation.
# Note that one could use any of the following calculators (try them all!):
# implementingClass = "infodynamics.measures.continuous.kraskov.MutualInfoCalculatorMultiVariateKraskov1" # MI(0;2) as 0.10044, MI([0,1]; [2,3]) = 0.36353 (NATS not bits)
# implementingClass = "infodynamics.measures.continuous.kernel.MutualInfoCalculatorMultiVariateKernel"
# implementingClass = "infodynamics.measures.continuous.gaussian.MutualInfoCalculatorMultiVariateGaussian"
implementingClass = "infodynamics.measures.continuous.kraskov.MutualInfoCalculatorMultiVariateKraskov1"
#---------------------
# 2. Load in the data
data = readFloatsFile.readFloatsFile(datafile)
# As numpy array:
A = numpy.array(data)
# Pull out the columns from the data set for a univariate MI calculation:
univariateSeries1 = A[:,univariateSeries1Column]
univariateSeries2 = A[:,univariateSeries2Column]
# Pull out the columns from the data set for a multivariate MI calculation:
jointVariable1 = A[:,jointVariable1Columns]
jointVariable2 = A[:,jointVariable2Columns]
#--------------------
# 3. Dynamically instantiate an object of the given class:
# (in fact, all java object creation in python is dynamic - it has to be,
# since the languages are interpreted. This makes our life slightly easier at this
# point than it is in demos/java/example6 where we have to handle this manually)
indexOfLastDot = implementingClass.rfind(".")
implementingPackage = implementingClass[:indexOfLastDot]
implementingBaseName = implementingClass[indexOfLastDot+1:]
miCalcClass = eval('JPackage(\'%s\').%s' % (implementingPackage, implementingBaseName))
miCalc = miCalcClass()
#--------------------
# 4. Start using the MI calculator, paying attention to only
# call common methods defined in the interface type
# infodynamics.measures.continuous.MutualInfoCalculatorMultiVariate
# not methods only defined in a given implementation class.
# a. Initialise the calculator for a univariate calculation:
miCalc.initialise(1, 1)
# b. Supply the observations to compute the PDFs from:
miCalc.setObservations(JArray(JDouble, 1)(univariateSeries1.tolist()), JArray(JDouble, 1)(univariateSeries2.tolist()))
# c. Make the MI calculation:
miUnivariateValue = miCalc.computeAverageLocalOfObservations()
#---------------------
# 5. Continue onto a multivariate calculation, still
# only calling common methods defined in the interface type.
# a. Initialise the calculator for a multivariate calculation
# to use the required number of dimensions for each variable:
miCalc.initialise(len(jointVariable1Columns), len(jointVariable2Columns))
# b. Supply the observations to compute the PDFs from:
miCalc.setObservations(JArray(JDouble, 2)(jointVariable1.tolist()), JArray(JDouble, 2)(jointVariable2.tolist()))
# c. Make the MI calculation:
miJointValue = miCalc.computeAverageLocalOfObservations()
print("MI calculator %s computed the univariate MI(%d;%d) as %.5f and joint MI([%s];[%s]) as %.5f\n" %
(implementingClass, univariateSeries1Column, univariateSeries2Column, miUnivariateValue,
str(jointVariable1Columns).strip('[]'), str(jointVariable2Columns).strip('[]'), miJointValue))