@@ -18,8 +18,9 @@ class AFHMM(Disaggregator):
1818 def __init__ (self , params ):
1919 self .MODEL_NAME = 'AFHMM'
2020 self .models = []
21- self .num_appliances = 0
22- self .appliances = []
21+ self .means_vector = OrderedDict ()
22+ self .pi_s_vector = OrderedDict ()
23+ self .transmat_vector = OrderedDict ()
2324 self .signal_aggregates = OrderedDict ()
2425 self .time_period = params .get ("time_period" , 720 )
2526 self .default_num_states = params .get ("default_num_states" , 2 )
@@ -29,62 +30,41 @@ def __init__(self, params):
2930 if self .load_model_path :
3031 self .load_model (self .load_model_path )
3132
33+ @nilmtk .docinherit .doc_inherit
3234 def partial_fit (self , train_main , train_appliances , ** load_kwargs ):
33- self .models = []
34- self .num_appliances = 0
35- self .appliances = []
36- train_main = pd .concat (train_main , axis = 0 )
37- train_app_tmp = []
38- for app_name , df_list in train_appliances :
39- df_list = pd .concat (df_list , axis = 0 )
40- train_app_tmp .append ((app_name ,df_list ))
41-
42- # All the initializations required by the model
43- train_appliances = train_app_tmp
44- learnt_model = OrderedDict ()
45- means_vector = []
46- one_hot_states_vector = []
47- pi_s_vector = []
48- transmat_vector = []
49- states_vector = []
50- train_main = train_main .values .flatten ().reshape ((- 1 ,1 ))
51-
52- for appliance_name , power in train_appliances :
53- # Learning the pi's and transistion probablities for each appliance using a simple HMM
54- self .appliances .append (appliance_name )
55- X = power .values .reshape ((- 1 ,1 ))
56- learnt_model [appliance_name ] = hmm .GaussianHMM (self .default_num_states , "full" )
57- # Fit
58- learnt_model [appliance_name ].fit (X )
59- means = learnt_model [appliance_name ].means_ .flatten ().reshape ((- 1 ,1 ))
60- states = learnt_model [appliance_name ].predict (X )
61- transmat = learnt_model [appliance_name ].transmat_
35+ """
36+ train_main: pd.DataFrame It will contain the mains reading.
37+ train_appliances: list of tuples [('appliance1', [ df1 ]),('appliance2', [ df2 ]),...]
38+ """
39+ for appli_name , df_list in train_appliances :
40+ # Compute model parameters for this chunk.
41+ app_df = pd .concat (df_list , axis = 0 )
42+ X = app_df .values .reshape (( - 1 , 1 ))
43+ learnt_model = hmm .GaussianHMM (self .default_num_states , "full" )
44+ learnt_model .fit (X )
45+ means = learnt_model .means_ .flatten ().reshape (( - 1 , 1 ))
46+ states = learnt_model .predict (X )
47+ transmat = learnt_model .transmat_ .T
6248 counter = Counter (states .flatten ())
63- total = 0
64- keys = list (counter .keys ())
65- keys .sort ()
66-
67- for i in keys :
68- total += counter [i ]
69- pi = []
70-
71- for i in keys :
72- pi .append (counter [i ]/ total )
73- pi = np .array (pi )
74- nb_classes = self .default_num_states
75- targets = states .reshape (- 1 )
76- means_vector .append (means )
77- pi_s_vector .append (pi )
78- transmat_vector .append (transmat .T )
79- states_vector .append (states )
80- self .num_appliances += 1
81- self .signal_aggregates [appliance_name ] = (np .mean (X )* self .time_period ).reshape ((- 1 ,))
82-
83- self .means_vector = means_vector
84- self .pi_s_vector = pi_s_vector
85- self .means_vector = means_vector
86- self .transmat_vector = transmat_vector
87- print ("Finished Training" )
49+ total = sum (counter .values ())
50+ pi = np .array ([ v / total for v in counter .values () ])
51+ sigagg = (np .mean (X ) * self .time_period ).reshape (( - 1 , ))
52+ # Merge with previous values.
53+ # Hypothesis 1: chunk size is constant. (mean of means)
54+ # Hypothesis 2: if the appliance is already registered in
55+ # self.means_vector, then it is also known in all other dicts.
56+ if appli_name in self .means_vector :
57+ self .means_vector [appli_name ] = (self .means_vector [appli_name ] + means ) / 2
58+ self .pi_s_vector [appli_name ] = (self .pi_s_vector [appli_name ] + pi ) / 2
59+ self .transmat_vector [appli_name ] = (self .transmat_vector [appli_name ] + transmat ) / 2
60+ self .signal_aggregates [appli_name ] = (self .signal_aggregates [appli_name ] + sigagg ) / 2
61+ else :
62+ self .means_vector [appli_name ] = means
63+ self .pi_s_vector [appli_name ] = pi
64+ self .transmat_vector [appli_name ] = transmat
65+ self .signal_aggregates [appli_name ] = sigagg
66+
67+ print ("{}: Finished training" .format (self .MODEL_NAME ))
8868
8969 def disaggregate_thread (self , test_mains ,index ,d ):
9070 means_vector = self .means_vector
0 commit comments