exo_proc per ts decorator & refactor mech_step
This commit is contained in:
parent
098fc04f3d
commit
ee5f912908
|
|
@ -1,5 +1,5 @@
|
||||||
import pandas as pd
|
import pandas as pd
|
||||||
from functools import partial, reduce
|
from functools import reduce
|
||||||
|
|
||||||
def state_identity(k):
|
def state_identity(k):
|
||||||
return lambda step, sL, s, _input: (k, s[k])
|
return lambda step, sL, s, _input: (k, s[k])
|
||||||
|
|
@ -37,9 +37,7 @@ def generate_config(state_dict, mechanisms, exo_proc):
|
||||||
sdf_values, bdf_values = sdf.values.tolist(), bdf.values.tolist()
|
sdf_values, bdf_values = sdf.values.tolist(), bdf.values.tolist()
|
||||||
else:
|
else:
|
||||||
sdf_values = sdf.values.tolist()
|
sdf_values = sdf.values.tolist()
|
||||||
# print(sdf_values)
|
|
||||||
bdf_values = [ [b_identity] * len(sdf_values) for n in range(mechanisms) ]
|
bdf_values = [ [b_identity] * len(sdf_values) for n in range(mechanisms) ]
|
||||||
# print(bdf_values)
|
|
||||||
return sdf_values, bdf_values
|
return sdf_values, bdf_values
|
||||||
|
|
||||||
def only_ep_handler(state_dict):
|
def only_ep_handler(state_dict):
|
||||||
|
|
|
||||||
|
|
@ -1,11 +1,14 @@
|
||||||
from copy import deepcopy
|
from copy import deepcopy
|
||||||
from fn import op, _
|
from fn.op import foldr, call
|
||||||
|
from fn import _
|
||||||
|
from ui.config import behavior_ops
|
||||||
|
|
||||||
def getColResults(step, sL, s, funcs):
|
def getColResults(step, sL, s, funcs):
|
||||||
return list(map(lambda f: f(step, sL, s), funcs))
|
return list(map(lambda f: f(step, sL, s), funcs))
|
||||||
|
|
||||||
def getBehaviorInput(step, sL, s, funcs):
|
# Data Type reduction
|
||||||
return op.foldr(_ + _)(getColResults(step, sL, s, funcs))
|
def getBehaviorInput(step, sL, s, funcs, ops = behavior_ops[::-1]):
|
||||||
|
return foldr(call, getColResults(step, sL, s, funcs))(ops)
|
||||||
|
|
||||||
def apply_env_proc(env_processes, state_dict, step):
|
def apply_env_proc(env_processes, state_dict, step):
|
||||||
for state in state_dict.keys():
|
for state in state_dict.keys():
|
||||||
|
|
@ -21,26 +24,23 @@ def exception_handler(f, m_step, sL, last_mut_obj, _input):
|
||||||
|
|
||||||
|
|
||||||
def mech_step(m_step, sL, state_funcs, behavior_funcs, env_processes, t_step):
|
def mech_step(m_step, sL, state_funcs, behavior_funcs, env_processes, t_step):
|
||||||
in_copy, mutatable_copy, out_copy = deepcopy(sL), deepcopy(sL), deepcopy(sL)
|
last_in_obj = sL[-1]
|
||||||
last_in_obj, last_mut_obj = in_copy[-1], mutatable_copy[-1]
|
|
||||||
|
|
||||||
_input = exception_handler(getBehaviorInput, m_step, sL, last_in_obj, behavior_funcs)
|
_input = exception_handler(getBehaviorInput, m_step, sL, last_in_obj, behavior_funcs)
|
||||||
|
# del last_in_obj
|
||||||
|
|
||||||
# print(len(state_funcs))
|
last_in_copy = dict([ exception_handler(f, m_step, sL, last_in_obj, _input) for f in state_funcs ])
|
||||||
|
# print(str(m_step) + ': ' + str(last_in_copy))
|
||||||
|
|
||||||
last_mut_obj = dict([
|
# mutating last_in_copy
|
||||||
exception_handler(f, m_step, sL, last_mut_obj, _input) for f in state_funcs
|
apply_env_proc(env_processes, last_in_copy, last_in_copy['timestamp'])
|
||||||
])
|
|
||||||
# print(str(m_step) + ': ' + str(last_mut_obj))
|
|
||||||
|
|
||||||
apply_env_proc(env_processes, last_mut_obj, last_mut_obj['timestamp'])
|
last_in_copy["mech_step"], last_in_copy["time_step"] = m_step, t_step
|
||||||
|
sL.append(last_in_copy)
|
||||||
|
|
||||||
last_mut_obj["mech_step"], last_mut_obj["time_step"] = m_step, t_step
|
del last_in_copy
|
||||||
out_copy.append(last_mut_obj)
|
|
||||||
|
|
||||||
del last_in_obj, last_mut_obj, in_copy, mutatable_copy,
|
return sL
|
||||||
|
|
||||||
return out_copy
|
|
||||||
|
|
||||||
|
|
||||||
def block_gen(states_list, configs, env_processes, t_step):
|
def block_gen(states_list, configs, env_processes, t_step):
|
||||||
|
|
@ -68,12 +68,13 @@ def pipeline(states_list, configs, env_processes, time_seq):
|
||||||
simulation_list = [states_list]
|
simulation_list = [states_list]
|
||||||
for time_step in time_seq:
|
for time_step in time_seq:
|
||||||
pipeline_run = block_gen(simulation_list[-1], configs, env_processes, time_step)
|
pipeline_run = block_gen(simulation_list[-1], configs, env_processes, time_step)
|
||||||
head, *pipeline_run = pipeline_run
|
_, *pipeline_run = pipeline_run
|
||||||
simulation_list.append(pipeline_run)
|
simulation_list.append(pipeline_run)
|
||||||
|
|
||||||
return simulation_list
|
return simulation_list
|
||||||
|
|
||||||
|
|
||||||
|
# Del head
|
||||||
def simulation(states_list, configs, env_processes, time_seq, runs):
|
def simulation(states_list, configs, env_processes, time_seq, runs):
|
||||||
pipeline_run = []
|
pipeline_run = []
|
||||||
for run in range(runs):
|
for run in range(runs):
|
||||||
|
|
@ -84,7 +85,7 @@ def simulation(states_list, configs, env_processes, time_seq, runs):
|
||||||
pipeline_run += simulation_list
|
pipeline_run += simulation_list
|
||||||
else:
|
else:
|
||||||
transient_states_list = [pipeline_run[-1][-1]]
|
transient_states_list = [pipeline_run[-1][-1]]
|
||||||
head, *tail = pipeline(transient_states_list, configs, env_processes, time_seq)
|
_, *tail = pipeline(transient_states_list, configs, env_processes, time_seq)
|
||||||
pipeline_run += tail
|
pipeline_run += tail
|
||||||
|
|
||||||
return pipeline_run
|
return pipeline_run
|
||||||
|
|
@ -17,7 +17,7 @@ def main():
|
||||||
# print(states_list)
|
# print(states_list)
|
||||||
# print(configs)
|
# print(configs)
|
||||||
# p = pipeline(states_list, configs, env_processes, range(10))
|
# p = pipeline(states_list, configs, env_processes, range(10))
|
||||||
T = range(5)
|
T = sim_config['T']
|
||||||
N = sim_config['N']
|
N = sim_config['N']
|
||||||
|
|
||||||
# Dimensions: N x r x mechs
|
# Dimensions: N x r x mechs
|
||||||
|
|
|
||||||
|
|
@ -1,6 +1,6 @@
|
||||||
from datetime import datetime, timedelta
|
from datetime import datetime, timedelta
|
||||||
from decimal import Decimal
|
from decimal import Decimal
|
||||||
from functools import partial
|
from fn.func import curried
|
||||||
|
|
||||||
flatten = lambda l: [item for sublist in l for item in sublist]
|
flatten = lambda l: [item for sublist in l for item in sublist]
|
||||||
|
|
||||||
|
|
@ -35,13 +35,12 @@ def bound_norm_random(rng, low, high):
|
||||||
res = bound_norm_random(rng, low, high)
|
res = bound_norm_random(rng, low, high)
|
||||||
return Decimal(res)
|
return Decimal(res)
|
||||||
|
|
||||||
def proc_trigger(trigger_step, update_f):
|
@curried
|
||||||
def step_trigger(trigger_step, update_f, step):
|
def proc_trigger(trigger_step, update_f, step):
|
||||||
if step == trigger_step:
|
if step == trigger_step:
|
||||||
return update_f
|
return update_f
|
||||||
else:
|
else:
|
||||||
return lambda x: x
|
return lambda x: x
|
||||||
return partial(step_trigger, trigger_step, update_f)
|
|
||||||
|
|
||||||
# accept timedelta instead of timedelta params
|
# accept timedelta instead of timedelta params
|
||||||
def time_step(dt_str, dt_format='%Y-%m-%d %H:%M:%S', days=0, minutes=0, seconds=30):
|
def time_step(dt_str, dt_format='%Y-%m-%d %H:%M:%S', days=0, minutes=0, seconds=30):
|
||||||
|
|
@ -56,6 +55,15 @@ def ep_time_step(s, dt_str, fromat_str='%Y-%m-%d %H:%M:%S', days=0, minutes=0, s
|
||||||
else:
|
else:
|
||||||
return dt_str
|
return dt_str
|
||||||
|
|
||||||
|
def exo_update_per_ts(ep):
|
||||||
|
@curried
|
||||||
|
def ep_decorator(f, y, step, sL, s, _input):
|
||||||
|
if s['mech_step'] + 1 == 1: # inside f body to reduce performance costs
|
||||||
|
return f(step, sL, s, _input)
|
||||||
|
else:
|
||||||
|
return (y, s[y])
|
||||||
|
return {es: ep_decorator(f, es) for es, f in ep.items()}
|
||||||
|
|
||||||
# def create_tensor_field(mechanisms, env_poc, keys=['behaviors', 'states']):
|
# def create_tensor_field(mechanisms, env_poc, keys=['behaviors', 'states']):
|
||||||
# dfs = [ create_matrix_field(mechanisms, k) for k in keys ]
|
# dfs = [ create_matrix_field(mechanisms, k) for k in keys ]
|
||||||
# df = pd.concat(dfs, axis=1)
|
# df = pd.concat(dfs, axis=1)
|
||||||
|
|
|
||||||
30
ui/config.py
30
ui/config.py
|
|
@ -1,4 +1,6 @@
|
||||||
from engine.utils import bound_norm_random, ep_time_step, proc_trigger
|
from engine.utils import bound_norm_random, ep_time_step, proc_trigger, exo_update_per_ts
|
||||||
|
from fn.op import foldr
|
||||||
|
from fn import _
|
||||||
|
|
||||||
import numpy as np
|
import numpy as np
|
||||||
from decimal import Decimal
|
from decimal import Decimal
|
||||||
|
|
@ -58,27 +60,23 @@ def s2m3(step, sL, s, _input):
|
||||||
# Exogenous States
|
# Exogenous States
|
||||||
proc_one_coef_A = 0.7
|
proc_one_coef_A = 0.7
|
||||||
proc_one_coef_B = 1.3
|
proc_one_coef_B = 1.3
|
||||||
|
|
||||||
def es3p1(step, sL, s, _input):
|
def es3p1(step, sL, s, _input):
|
||||||
y = 's3'
|
y = 's3'
|
||||||
if s['mech_step']+1 == 1: # inside f body to reduce performance costs
|
x = s['s3'] * bound_norm_random(seed['a'], proc_one_coef_A, proc_one_coef_B)
|
||||||
x = s['s3'] * bound_norm_random(seed['a'], proc_one_coef_A, proc_one_coef_B)
|
return (y, x)
|
||||||
return (y, x)
|
|
||||||
else:
|
|
||||||
return (y, s[y])
|
|
||||||
|
|
||||||
def es4p2(step, sL, s, _input):
|
def es4p2(step, sL, s, _input):
|
||||||
y = 's4'
|
y = 's4'
|
||||||
if s['mech_step']+1 == 1: # inside f body to reduce performance costs
|
x = s['s4'] * bound_norm_random(seed['b'], proc_one_coef_A, proc_one_coef_B)
|
||||||
x = s['s4'] * bound_norm_random(seed['b'], proc_one_coef_A, proc_one_coef_B)
|
return (y, x)
|
||||||
return (y, x)
|
|
||||||
else:
|
|
||||||
return (y, s[y])
|
|
||||||
|
|
||||||
def es5p2(step, sL, s, _input): # accept timedelta instead of timedelta params
|
def es5p2(step, sL, s, _input): # accept timedelta instead of timedelta params
|
||||||
y = 'timestamp'
|
y = 'timestamp'
|
||||||
x = ep_time_step(s, s['timestamp'], seconds=1)
|
x = ep_time_step(s, s['timestamp'], seconds=1)
|
||||||
return (y, x)
|
return (y, x)
|
||||||
|
|
||||||
|
|
||||||
# Environment States
|
# Environment States
|
||||||
def env_a(x):
|
def env_a(x):
|
||||||
return 10
|
return 10
|
||||||
|
|
@ -96,11 +94,13 @@ state_dict = {
|
||||||
'timestamp': '2018-10-01 15:16:24'
|
'timestamp': '2018-10-01 15:16:24'
|
||||||
}
|
}
|
||||||
|
|
||||||
exogenous_states = {
|
exogenous_states = exo_update_per_ts(
|
||||||
|
{
|
||||||
"s3": es3p1,
|
"s3": es3p1,
|
||||||
"s4": es4p2,
|
"s4": es4p2,
|
||||||
"timestamp": es5p2
|
"timestamp": es5p2
|
||||||
}
|
}
|
||||||
|
)
|
||||||
|
|
||||||
env_processes = {
|
env_processes = {
|
||||||
"s3": proc_trigger('2018-10-01 15:16:25', env_a),
|
"s3": proc_trigger('2018-10-01 15:16:25', env_a),
|
||||||
|
|
@ -110,6 +110,7 @@ env_processes = {
|
||||||
# test return vs. non-return functions as lambdas
|
# test return vs. non-return functions as lambdas
|
||||||
# test fully defined functions
|
# test fully defined functions
|
||||||
# genesis Sites should always be there
|
# genesis Sites should always be there
|
||||||
|
behavior_ops = [foldr(_ + _), lambda x: x + 0]
|
||||||
mechanisms = {
|
mechanisms = {
|
||||||
"m1": {
|
"m1": {
|
||||||
"behaviors": {
|
"behaviors": {
|
||||||
|
|
@ -144,5 +145,6 @@ mechanisms = {
|
||||||
}
|
}
|
||||||
|
|
||||||
sim_config = {
|
sim_config = {
|
||||||
"N": 2
|
"N": 2,
|
||||||
|
"T": range(5)
|
||||||
}
|
}
|
||||||
Loading…
Reference in New Issue