diff --git a/.history/am_220512.csv b/.history/am_220512.csv new file mode 100644 index 0000000000000000000000000000000000000000..68a8171405c3d86794eab0fa3bae098cf4863e79 --- /dev/null +++ b/.history/am_220512.csv @@ -0,0 +1,21 @@ +loss,categorical_crossentropy,categorical_accuracy,categorical_hinge,val_loss,val_categorical_crossentropy,val_categorical_accuracy,val_categorical_hinge +0.6102505922317505,0.6102591753005981,0.7721169590950012,0.5578135251998901,0.2365977168083191,0.23661620914936066,0.9482620358467102,0.21556608378887177 +0.2410024255514145,0.24101324379444122,0.9489823579788208,0.22259768843650818,0.22830058634281158,0.22832421958446503,0.9520950317382812,0.219150111079216 +0.22811080515384674,0.22812050580978394,0.9507037997245789,0.22212223708629608,0.20287160575389862,0.20289486646652222,0.9597100019454956,0.21067200601100922 +0.2257438749074936,0.225755974650383,0.9488319158554077,0.22673241794109344,0.19838610291481018,0.19840732216835022,0.9598119854927063,0.1895865648984909 +0.24677418172359467,0.24678997695446014,0.9415083527565002,0.24014297127723694,0.20171019434928894,0.20173151791095734,0.9596517086029053,0.1882585883140564 +0.22916194796562195,0.22917920351028442,0.9510580897331238,0.22440536320209503,0.1999731957912445,0.19999487698078156,0.9598484039306641,0.19534263014793396 +0.21525806188583374,0.2152738720178604,0.9554435610771179,0.21104231476783752,0.19979862868785858,0.19982029497623444,0.9598557353019714,0.19377031922340393 +0.21643704175949097,0.2164536565542221,0.9556373953819275,0.21280315518379211,0.19801299273967743,0.19803403317928314,0.9598265886306763,0.1905786246061325 +0.22762203216552734,0.2276403158903122,0.9521276950836182,0.2212676852941513,0.21021290123462677,0.21023407578468323,0.9591853022575378,0.20358486473560333 +0.23046843707561493,0.2304823100566864,0.949951708316803,0.23079520463943481,0.19998398423194885,0.20000584423542023,0.9586096405982971,0.1999059021472931 +0.21614259481430054,0.21616177260875702,0.9552162289619446,0.21368272602558136,0.19799767434597015,0.19801850616931915,0.9597464203834534,0.19059626758098602 +0.2314920574426651,0.23151175677776337,0.950182318687439,0.23680256307125092,0.19927160441875458,0.1992924064397812,0.9598192572593689,0.19148322939872742 +0.19912201166152954,0.19913870096206665,0.9593844413757324,0.197440966963768,0.1971137374639511,0.1971348226070404,0.9596953988075256,0.1911185085773468 +0.22077631950378418,0.22079353034496307,0.9546881318092346,0.21700823307037354,0.19683417677879333,0.1968551129102707,0.9598119854927063,0.1903052181005478 +0.19817253947257996,0.19818846881389618,0.9590468406677246,0.1978733092546463,0.19659003615379333,0.19661082327365875,0.9597901105880737,0.1899634152650833 +0.21108753979206085,0.211105078458786,0.9546680450439453,0.21126605570316315,0.19589678943157196,0.19591759145259857,0.9598557353019714,0.1899382472038269 +0.20053814351558685,0.2005544900894165,0.9582446217536926,0.20047253370285034,0.19655226171016693,0.19657309353351593,0.959863007068634,0.19047877192497253 +0.19827072322368622,0.19828687608242035,0.95877605676651,0.19837716221809387,0.19621789455413818,0.19623875617980957,0.9598119854927063,0.189311683177948 +0.2156815230846405,0.2156958281993866,0.955353319644928,0.2140825092792511,0.1963217407464981,0.19634267687797546,0.9598484039306641,0.19015157222747803 +0.2074679136276245,0.20748521387577057,0.9574725031852722,0.2063201367855072,0.1954033225774765,0.19542405009269714,0.959863007068634,0.19042037427425385 diff --git a/.model/attention/keras_metadata.pb b/.model/attention/keras_metadata.pb index a85a548eb098711de803bb25c8e4aac7f2e3d7e9..1306f144c426de97e9581c893da239d2dba815ef 100755 --- a/.model/attention/keras_metadata.pb +++ b/.model/attention/keras_metadata.pb @@ -1,15 +1,15 @@ -‘root"_tf_keras_sequential*ì{"name": "sequential", "trainable": true, "expects_training_arg": true, "dtype": "float32", "batch_input_shape": null, "must_restore_from_config": false, "class_name": "Sequential", "config": {"name": "sequential", "layers": [{"class_name": "InputLayer", "config": {"batch_input_shape": {"class_name": "__tuple__", "items": [null, 10, 7]}, "dtype": "float32", "sparse": false, "ragged": false, "name": "input_1"}}, {"class_name": "Attention", "config": {"name": "attention", "trainable": true, "dtype": "float32", "units": 16}}, {"class_name": "Dense", "config": {"name": "dense", "trainable": true, "dtype": "float32", "units": 4, "activation": "linear", "use_bias": true, "kernel_initializer": {"class_name": "GlorotUniform", "config": {"seed": null}}, "bias_initializer": {"class_name": "Zeros", "config": {}}, "kernel_regularizer": null, "bias_regularizer": null, "activity_regularizer": null, "kernel_constraint": null, "bias_constraint": null}}]}, "shared_object_id": 5, "input_spec": [{"class_name": "InputSpec", "config": {"dtype": null, "shape": {"class_name": "__tuple__", "items": [null, 10, 7]}, "ndim": 3, "max_ndim": null, "min_ndim": null, "axes": {}}}], "build_input_shape": {"class_name": "TensorShape", "items": [null, 10, 7]}, "is_graph_network": true, "full_save_spec": {"class_name": "__tuple__", "items": [[{"class_name": "TypeSpec", "type_spec": "tf.TensorSpec", "serialized": [{"class_name": "TensorShape", "items": [null, 10, 7]}, "float32", "input_1"]}], {}]}, "save_spec": {"class_name": "TypeSpec", "type_spec": "tf.TensorSpec", "serialized": [{"class_name": "TensorShape", "items": [null, 10, 7]}, "float32", "input_1"]}, "keras_version": "2.8.0", "backend": "tensorflow", "model_config": {"class_name": "Sequential", "config": {"name": "sequential", "layers": [{"class_name": "InputLayer", "config": {"batch_input_shape": {"class_name": "__tuple__", "items": [null, 10, 7]}, "dtype": "float32", "sparse": false, "ragged": false, "name": "input_1"}, "shared_object_id": 0}, {"class_name": "Attention", "config": {"name": "attention", "trainable": true, "dtype": "float32", "units": 16}, "shared_object_id": 1}, {"class_name": "Dense", "config": {"name": "dense", "trainable": true, "dtype": "float32", "units": 4, "activation": "linear", "use_bias": true, "kernel_initializer": {"class_name": "GlorotUniform", "config": {"seed": null}, "shared_object_id": 2}, "bias_initializer": {"class_name": "Zeros", "config": {}, "shared_object_id": 3}, "kernel_regularizer": null, "bias_regularizer": null, "activity_regularizer": null, "kernel_constraint": null, "bias_constraint": null}, "shared_object_id": 4}]}}, "training_config": {"loss": {"class_name": "CategoricalCrossentropy", "config": {"reduction": "auto", "name": "categorical_crossentropy", "from_logits": true, "label_smoothing": 0.0, "axis": -1}, "shared_object_id": 7}, "metrics": [[{"class_name": "CategoricalCrossentropy", "config": {"name": "categorical_crossentropy", "dtype": "float32", "from_logits": true, "label_smoothing": 0}, "shared_object_id": 8}, {"class_name": "CategoricalAccuracy", "config": {"name": "categorical_accuracy", "dtype": "float32"}, "shared_object_id": 9}, {"class_name": "CategoricalHinge", "config": {"name": "categorical_hinge", "dtype": "float32"}, "shared_object_id": 10}]], "weighted_metrics": null, "loss_weights": null, "optimizer_config": {"class_name": "Adam", "config": {"name": "Adam", "learning_rate": 0.0010000000474974513, "decay": 0.0, "beta_1": 0.8999999761581421, "beta_2": 0.9990000128746033, "epsilon": 1e-07, "amsgrad": false}}}}2 -µroot.layer_with_weights-0"_tf_keras_layer*þ{"name": "attention", "trainable": true, "expects_training_arg": true, "dtype": "float32", "batch_input_shape": null, "stateful": false, "must_restore_from_config": false, "class_name": "Attention", "config": {"name": "attention", "trainable": true, "dtype": "float32", "units": 16}, "shared_object_id": 1, "build_input_shape": {"class_name": "TensorShape", "items": [null, 10, 7]}}2 -Âroot.layer_with_weights-1"_tf_keras_layer*‹{"name": "dense", "trainable": true, "expects_training_arg": false, "dtype": "float32", "batch_input_shape": null, "stateful": false, "must_restore_from_config": false, "class_name": "Dense", "config": {"name": "dense", "trainable": true, "dtype": "float32", "units": 4, "activation": "linear", "use_bias": true, "kernel_initializer": {"class_name": "GlorotUniform", "config": {"seed": null}, "shared_object_id": 2}, "bias_initializer": {"class_name": "Zeros", "config": {}, "shared_object_id": 3}, "kernel_regularizer": null, "bias_regularizer": null, "activity_regularizer": null, "kernel_constraint": null, "bias_constraint": null}, "shared_object_id": 4, "input_spec": {"class_name": "InputSpec", "config": {"dtype": null, "shape": null, "ndim": null, "max_ndim": null, "min_ndim": 2, "axes": {"-1": 16}}, "shared_object_id": 11}, "build_input_shape": {"class_name": "TensorShape", "items": [null, 16]}}2 +ÿroot"_tf_keras_sequential*Ú{"name": "sequential", "trainable": true, "expects_training_arg": true, "dtype": "float32", "batch_input_shape": null, "must_restore_from_config": false, "class_name": "Sequential", "config": {"name": "sequential", "layers": [{"class_name": "InputLayer", "config": {"batch_input_shape": {"class_name": "__tuple__", "items": [null, 10, 7]}, "dtype": "float32", "sparse": false, "ragged": false, "name": "input_1"}}, {"class_name": "CustomAttention", "config": {"name": "custom_attention", "trainable": true, "dtype": "float32", "units": 32}}, {"class_name": "Dense", "config": {"name": "dense", "trainable": true, "dtype": "float32", "units": 4, "activation": "linear", "use_bias": true, "kernel_initializer": {"class_name": "GlorotUniform", "config": {"seed": null}}, "bias_initializer": {"class_name": "Zeros", "config": {}}, "kernel_regularizer": null, "bias_regularizer": null, "activity_regularizer": null, "kernel_constraint": null, "bias_constraint": null}}]}, "shared_object_id": 5, "input_spec": [{"class_name": "InputSpec", "config": {"dtype": null, "shape": {"class_name": "__tuple__", "items": [null, 10, 7]}, "ndim": 3, "max_ndim": null, "min_ndim": null, "axes": {}}}], "build_input_shape": {"class_name": "TensorShape", "items": [null, 10, 7]}, "is_graph_network": true, "full_save_spec": {"class_name": "__tuple__", "items": [[{"class_name": "TypeSpec", "type_spec": "tf.TensorSpec", "serialized": [{"class_name": "TensorShape", "items": [null, 10, 7]}, "float32", "input_1"]}], {}]}, "save_spec": {"class_name": "TypeSpec", "type_spec": "tf.TensorSpec", "serialized": [{"class_name": "TensorShape", "items": [null, 10, 7]}, "float32", "input_1"]}, "keras_version": "2.8.0", "backend": "tensorflow", "model_config": {"class_name": "Sequential", "config": {"name": "sequential", "layers": [{"class_name": "InputLayer", "config": {"batch_input_shape": {"class_name": "__tuple__", "items": [null, 10, 7]}, "dtype": "float32", "sparse": false, "ragged": false, "name": "input_1"}, "shared_object_id": 0}, {"class_name": "CustomAttention", "config": {"name": "custom_attention", "trainable": true, "dtype": "float32", "units": 32}, "shared_object_id": 1}, {"class_name": "Dense", "config": {"name": "dense", "trainable": true, "dtype": "float32", "units": 4, "activation": "linear", "use_bias": true, "kernel_initializer": {"class_name": "GlorotUniform", "config": {"seed": null}, "shared_object_id": 2}, "bias_initializer": {"class_name": "Zeros", "config": {}, "shared_object_id": 3}, "kernel_regularizer": null, "bias_regularizer": null, "activity_regularizer": null, "kernel_constraint": null, "bias_constraint": null}, "shared_object_id": 4}]}}, "training_config": {"loss": {"class_name": "CategoricalCrossentropy", "config": {"reduction": "auto", "name": "categorical_crossentropy", "from_logits": true, "label_smoothing": 0.0, "axis": -1}, "shared_object_id": 7}, "metrics": [[{"class_name": "CategoricalCrossentropy", "config": {"name": "categorical_crossentropy", "dtype": "float32", "from_logits": true, "label_smoothing": 0}, "shared_object_id": 8}, {"class_name": "CategoricalAccuracy", "config": {"name": "categorical_accuracy", "dtype": "float32"}, "shared_object_id": 9}, {"class_name": "CategoricalHinge", "config": {"name": "categorical_hinge", "dtype": "float32"}, "shared_object_id": 10}]], "weighted_metrics": null, "loss_weights": null, "optimizer_config": {"class_name": "Adam", "config": {"name": "Adam", "learning_rate": 0.001, "decay": 0.0, "beta_1": 0.9, "beta_2": 0.999, "epsilon": 1e-07, "amsgrad": false}}}}2 +Éroot.layer_with_weights-0"_tf_keras_layer*’{"name": "custom_attention", "trainable": true, "expects_training_arg": true, "dtype": "float32", "batch_input_shape": null, "stateful": false, "must_restore_from_config": false, "class_name": "CustomAttention", "config": {"name": "custom_attention", "trainable": true, "dtype": "float32", "units": 32}, "shared_object_id": 1, "build_input_shape": {"class_name": "TensorShape", "items": [null, 10, 7]}}2 +Âroot.layer_with_weights-1"_tf_keras_layer*‹{"name": "dense", "trainable": true, "expects_training_arg": false, "dtype": "float32", "batch_input_shape": null, "stateful": false, "must_restore_from_config": false, "class_name": "Dense", "config": {"name": "dense", "trainable": true, "dtype": "float32", "units": 4, "activation": "linear", "use_bias": true, "kernel_initializer": {"class_name": "GlorotUniform", "config": {"seed": null}, "shared_object_id": 2}, "bias_initializer": {"class_name": "Zeros", "config": {}, "shared_object_id": 3}, "kernel_regularizer": null, "bias_regularizer": null, "activity_regularizer": null, "kernel_constraint": null, "bias_constraint": null}, "shared_object_id": 4, "input_spec": {"class_name": "InputSpec", "config": {"dtype": null, "shape": null, "ndim": null, "max_ndim": null, "min_ndim": 2, "axes": {"-1": 32}}, "shared_object_id": 11}, "build_input_shape": {"class_name": "TensorShape", "items": [null, 32]}}2 ø-root.layer_with_weights-0.attention_score_vec"_tf_keras_layer*{"name": "attention_score_vec", "trainable": true, "expects_training_arg": false, "dtype": "float32", "batch_input_shape": null, "stateful": false, "must_restore_from_config": false, "class_name": "Dense", "config": {"name": "attention_score_vec", "trainable": true, "dtype": "float32", "units": 7, "activation": "linear", "use_bias": false, "kernel_initializer": {"class_name": "GlorotUniform", "config": {"seed": null}, "shared_object_id": 12}, "bias_initializer": {"class_name": "Zeros", "config": {}, "shared_object_id": 13}, "kernel_regularizer": null, "bias_regularizer": null, "activity_regularizer": null, "kernel_constraint": null, "bias_constraint": null}, "shared_object_id": 14, "input_spec": {"class_name": "InputSpec", "config": {"dtype": null, "shape": null, "ndim": null, "max_ndim": null, "min_ndim": 2, "axes": {"-1": 7}}, "shared_object_id": 15}, "build_input_shape": {"class_name": "TensorShape", "items": [null, 10, 7]}}2 -· root.layer_with_weights-0.h_t"_tf_keras_layer*ü{"name": "last_hidden_state", "trainable": true, "expects_training_arg": true, "dtype": "float32", "batch_input_shape": null, "stateful": false, "must_restore_from_config": false, "class_name": "Lambda", "config": {"name": "last_hidden_state", "trainable": true, "dtype": "float32", "function": {"class_name": "__tuple__", "items": ["4wEAAAAAAAAAAAAAAAEAAAAFAAAAUwAAAHMWAAAAfABkAGQAhQJkAWQAZACFAmYDGQBTACkCTun/\n////qQApAdoBeHICAAAAcgIAAAD6MS9ob21lL250b3AvUHljaGFybVByb2plY3RzL2ZpbmFsX2xh\nYi9hdHRlbnRpb24ucHnaCDxsYW1iZGE+GwAAAHMCAAAAFgA=\n", null, null]}, "function_type": "lambda", "module": "attention", "output_shape": {"class_name": "__tuple__", "items": [7]}, "output_shape_type": "raw", "output_shape_module": null, "arguments": {}}, "shared_object_id": 16}2 +Ý root.layer_with_weights-0.h_t"_tf_keras_layer*¢{"name": "last_hidden_state", "trainable": true, "expects_training_arg": true, "dtype": "float32", "batch_input_shape": null, "stateful": false, "must_restore_from_config": false, "class_name": "Lambda", "config": {"name": "last_hidden_state", "trainable": true, "dtype": "float32", "function": {"class_name": "__tuple__", "items": ["4wEAAAAAAAAAAAAAAAEAAAAFAAAAUwAAAHMWAAAAfABkAGQAhQJkAWQAZACFAmYDGQBTACkCTun/\n////qQApAdoBeHICAAAAcgIAAAD6TS9Vc2Vycy9ub3dhZG1pbi9Eb2N1bWVudHMvU2Nob29sIEZv\nbGRlci9DUyA0MzcvTGFiL0ZpbmFsIFByb2plY3QvYXR0ZW50aW9uLnB52gg8bGFtYmRhPhoAAABz\nAgAAABYA\n", null, null]}, "function_type": "lambda", "module": "attention", "output_shape": {"class_name": "__tuple__", "items": [7]}, "output_shape_type": "raw", "output_shape_module": null, "arguments": {}}, "shared_object_id": 16}2 ™)root.layer_with_weights-0.attention_score"_tf_keras_layer*Ò{"name": "attention_score", "trainable": true, "expects_training_arg": false, "dtype": "float32", "batch_input_shape": null, "stateful": false, "must_restore_from_config": false, "class_name": "Dot", "config": {"name": "attention_score", "trainable": true, "dtype": "float32", "axes": [1, 2], "normalize": false}, "shared_object_id": 17, "build_input_shape": [{"class_name": "TensorShape", "items": [null, 7]}, {"class_name": "TensorShape", "items": [null, 10, 7]}]}2 —*root.layer_with_weights-0.attention_weight"_tf_keras_layer*Ï{"name": "attention_weight", "trainable": true, "expects_training_arg": false, "dtype": "float32", "batch_input_shape": null, "stateful": false, "must_restore_from_config": false, "class_name": "Activation", "config": {"name": "attention_weight", "trainable": true, "dtype": "float32", "activation": "softmax"}, "shared_object_id": 18}2 —(root.layer_with_weights-0.context_vector"_tf_keras_layer*Ñ{"name": "context_vector", "trainable": true, "expects_training_arg": false, "dtype": "float32", "batch_input_shape": null, "stateful": false, "must_restore_from_config": false, "class_name": "Dot", "config": {"name": "context_vector", "trainable": true, "dtype": "float32", "axes": [1, 1], "normalize": false}, "shared_object_id": 19, "build_input_shape": [{"class_name": "TensorShape", "items": [null, 10, 7]}, {"class_name": "TensorShape", "items": [null, 10]}]}2 ˆ*root.layer_with_weights-0.attention_output"_tf_keras_layer*À{"name": "attention_output", "trainable": true, "expects_training_arg": false, "dtype": "float32", "batch_input_shape": null, "stateful": false, "must_restore_from_config": false, "class_name": "Concatenate", "config": {"name": "attention_output", "trainable": true, "dtype": "float32", "axis": -1}, "shared_object_id": 20, "build_input_shape": [{"class_name": "TensorShape", "items": [null, 7]}, {"class_name": "TensorShape", "items": [null, 7]}]}2 -ì*root.layer_with_weights-0.attention_vector"_tf_keras_layer*¤{"name": "attention_vector", "trainable": true, "expects_training_arg": false, "dtype": "float32", "batch_input_shape": null, "stateful": false, "must_restore_from_config": false, "class_name": "Dense", "config": {"name": "attention_vector", "trainable": true, "dtype": "float32", "units": 16, "activation": "tanh", "use_bias": false, "kernel_initializer": {"class_name": "GlorotUniform", "config": {"seed": null}, "shared_object_id": 21}, "bias_initializer": {"class_name": "Zeros", "config": {}, "shared_object_id": 22}, "kernel_regularizer": null, "bias_regularizer": null, "activity_regularizer": null, "kernel_constraint": null, "bias_constraint": null}, "shared_object_id": 23, "input_spec": {"class_name": "InputSpec", "config": {"dtype": null, "shape": null, "ndim": null, "max_ndim": null, "min_ndim": 2, "axes": {"-1": 14}}, "shared_object_id": 24}, "build_input_shape": {"class_name": "TensorShape", "items": [null, 14]}}2 -¹droot.keras_api.metrics.0"_tf_keras_metric*‚{"class_name": "Mean", "name": "loss", "dtype": "float32", "config": {"name": "loss", "dtype": "float32"}, "shared_object_id": 25}2 -žeroot.keras_api.metrics.1"_tf_keras_metric*ç{"class_name": "CategoricalCrossentropy", "name": "categorical_crossentropy", "dtype": "float32", "config": {"name": "categorical_crossentropy", "dtype": "float32", "from_logits": true, "label_smoothing": 0}, "shared_object_id": 8}2 -çfroot.keras_api.metrics.2"_tf_keras_metric*°{"class_name": "CategoricalAccuracy", "name": "categorical_accuracy", "dtype": "float32", "config": {"name": "categorical_accuracy", "dtype": "float32"}, "shared_object_id": 9}2 -ßgroot.keras_api.metrics.3"_tf_keras_metric*¨{"class_name": "CategoricalHinge", "name": "categorical_hinge", "dtype": "float32", "config": {"name": "categorical_hinge", "dtype": "float32"}, "shared_object_id": 10}2 \ No newline at end of file +ì*root.layer_with_weights-0.attention_vector"_tf_keras_layer*¤{"name": "attention_vector", "trainable": true, "expects_training_arg": false, "dtype": "float32", "batch_input_shape": null, "stateful": false, "must_restore_from_config": false, "class_name": "Dense", "config": {"name": "attention_vector", "trainable": true, "dtype": "float32", "units": 32, "activation": "tanh", "use_bias": false, "kernel_initializer": {"class_name": "GlorotUniform", "config": {"seed": null}, "shared_object_id": 21}, "bias_initializer": {"class_name": "Zeros", "config": {}, "shared_object_id": 22}, "kernel_regularizer": null, "bias_regularizer": null, "activity_regularizer": null, "kernel_constraint": null, "bias_constraint": null}, "shared_object_id": 23, "input_spec": {"class_name": "InputSpec", "config": {"dtype": null, "shape": null, "ndim": null, "max_ndim": null, "min_ndim": 2, "axes": {"-1": 14}}, "shared_object_id": 24}, "build_input_shape": {"class_name": "TensorShape", "items": [null, 14]}}2 +¹_root.keras_api.metrics.0"_tf_keras_metric*‚{"class_name": "Mean", "name": "loss", "dtype": "float32", "config": {"name": "loss", "dtype": "float32"}, "shared_object_id": 25}2 +ž`root.keras_api.metrics.1"_tf_keras_metric*ç{"class_name": "CategoricalCrossentropy", "name": "categorical_crossentropy", "dtype": "float32", "config": {"name": "categorical_crossentropy", "dtype": "float32", "from_logits": true, "label_smoothing": 0}, "shared_object_id": 8}2 +çaroot.keras_api.metrics.2"_tf_keras_metric*°{"class_name": "CategoricalAccuracy", "name": "categorical_accuracy", "dtype": "float32", "config": {"name": "categorical_accuracy", "dtype": "float32"}, "shared_object_id": 9}2 +ßbroot.keras_api.metrics.3"_tf_keras_metric*¨{"class_name": "CategoricalHinge", "name": "categorical_hinge", "dtype": "float32", "config": {"name": "categorical_hinge", "dtype": "float32"}, "shared_object_id": 10}2 \ No newline at end of file diff --git a/.model/attention/saved_model.pb b/.model/attention/saved_model.pb old mode 100755 new mode 100644 index 573c7f905e81021bac35246e9f179dff9cdde29c..f6723fe642fc128973775f2a31a00316c259dabe Binary files a/.model/attention/saved_model.pb and b/.model/attention/saved_model.pb differ diff --git a/.model/attention/variables/variables.data-00000-of-00001 b/.model/attention/variables/variables.data-00000-of-00001 old mode 100755 new mode 100644 index 1a5c7b2d5f137e1a1170e292ea9a9f2f47e7e253..34dad5eb6ebaa13a8fbc124005614d9298a1ccf3 Binary files a/.model/attention/variables/variables.data-00000-of-00001 and b/.model/attention/variables/variables.data-00000-of-00001 differ diff --git a/.model/attention/variables/variables.index b/.model/attention/variables/variables.index index a31867933f61483597b04caaeebd956bbc4d30f3..656368049b507b76cdb628c7e9ca686b324b69f9 100755 Binary files a/.model/attention/variables/variables.index and b/.model/attention/variables/variables.index differ diff --git a/TEST.data-00000-of-00001 b/TEST.data-00000-of-00001 new file mode 100644 index 0000000000000000000000000000000000000000..aaa509c52a2a2a98952fade82f8df46c9b069474 Binary files /dev/null and b/TEST.data-00000-of-00001 differ diff --git a/TEST.index b/TEST.index new file mode 100644 index 0000000000000000000000000000000000000000..ee1b5b2072bd9e89bd13d78225591e292bc6673f Binary files /dev/null and b/TEST.index differ diff --git a/attention.py b/attention.py index 69a94dc5f9e7b31209dc252e9912404ea178c1a0..6fa0682ca93244255c63ce3539709a2cd06d1874 100644 --- a/attention.py +++ b/attention.py @@ -6,17 +6,16 @@ from tensorflow.keras import backend as K from tensorflow.keras.layers import Dense, Lambda, Dot, Activation, Concatenate, Layer # KERAS_ATTENTION_DEBUG: If set to 1. Will switch to debug mode. -# In debug mode, the class Attention is no longer a Keras layer. +# In debug mode, the class CustomAttention is no longer a Keras layer. # What it means in practice is that we can have access to the internal values # of each tensor. If we don't use debug, Keras treats the object # as a layer and we can only get the final output. debug_flag = int(os.environ.get('KERAS_ATTENTION_DEBUG', 0)) - -class Attention(object if debug_flag else Layer): +class CustomAttention(object if debug_flag else Layer): def __init__(self, units=128, **kwargs): - super(Attention, self).__init__(**kwargs) + super(CustomAttention, self).__init__(**kwargs) self.units = units # noinspection PyAttributeOutsideInit @@ -32,7 +31,7 @@ class Attention(object if debug_flag else Layer): self.attention_vector = Dense(self.units, use_bias=False, activation='tanh', name='attention_vector') if not debug_flag: # debug: the call to build() is done in call(). - super(Attention, self).build(input_shape) + super(CustomAttention, self).build(input_shape) def compute_output_shape(self, input_shape): return input_shape[0], self.units @@ -41,7 +40,7 @@ class Attention(object if debug_flag else Layer): if debug_flag: return self.call(inputs, training, **kwargs) else: - return super(Attention, self).__call__(inputs, training, **kwargs) + return super(CustomAttention, self).__call__(inputs, training, **kwargs) # noinspection PyUnusedLocal def call(self, inputs, training=None, **kwargs): @@ -75,6 +74,6 @@ class Attention(object if debug_flag else Layer): Returns the config of a the layer. This is used for saving and loading from a model :return: python dictionary with specs to rebuild layer """ - config = super(Attention, self).get_config() + config = super(CustomAttention, self).get_config() config.update({'units': self.units}) return config \ No newline at end of file diff --git a/checkpoint b/checkpoint new file mode 100644 index 0000000000000000000000000000000000000000..0b5781050d1d2280d85bcc3a92c7f3878a11404f --- /dev/null +++ b/checkpoint @@ -0,0 +1,2 @@ +model_checkpoint_path: "TEST" +all_model_checkpoint_paths: "TEST" diff --git a/tf_model.ipynb b/tf_model.ipynb index 1256f64518b0b070fd4b622c378bd36a9844a4d8..dbce03e928aa643cc0cca0910a02d1340ccd4aa9 100644 --- a/tf_model.ipynb +++ b/tf_model.ipynb @@ -25,7 +25,7 @@ "from tensorflow import keras\n", "from tensorflow.keras import layers\n", "import pandas as pd\n", - "from attention import Attention\n", + "from attention import CustomAttention\n", "import json" ] }, @@ -48,14 +48,15 @@ }, { "cell_type": "code", - "execution_count": 3, + "execution_count": 13, "metadata": {}, "outputs": [], "source": [ "# CONSTANTS\n", "RAW_SLEEP_DATA_PATH = \".data/raw_bed_sleep-state.csv\"\n", "CLEANED_SLEEP_DATA_PATH = \".data/clean_bed_sleep-state.csv\"\n", - "SLEEP_DATA_PATH = \".data/sleep_data_simple.csv\"" + "SLEEP_DATA_PATH = \".data/sleep_data_simple.csv\"\n", + "UPDATED_SLEEP_DATA_PATH = \".data/updated_sleep_data.csv\"" ] }, { @@ -243,7 +244,7 @@ }, { "cell_type": "code", - "execution_count": 5, + "execution_count": 79, "metadata": {}, "outputs": [], "source": [ @@ -253,7 +254,7 @@ }, { "cell_type": "code", - "execution_count": 6, + "execution_count": 80, "metadata": {}, "outputs": [], "source": [ @@ -268,7 +269,7 @@ }, { "cell_type": "code", - "execution_count": 7, + "execution_count": 81, "metadata": {}, "outputs": [], "source": [ @@ -281,7 +282,7 @@ }, { "cell_type": "code", - "execution_count": 8, + "execution_count": 82, "metadata": {}, "outputs": [], "source": [ @@ -291,7 +292,7 @@ }, { "cell_type": "code", - "execution_count": 9, + "execution_count": 83, "metadata": {}, "outputs": [ { @@ -327,7 +328,7 @@ }, { "cell_type": "code", - "execution_count": 10, + "execution_count": 84, "metadata": {}, "outputs": [ { @@ -604,7 +605,7 @@ "[551042 rows x 13 columns]" ] }, - "execution_count": 10, + "execution_count": 84, "metadata": {}, "output_type": "execute_result" } @@ -694,31 +695,61 @@ }, { "cell_type": "code", - "execution_count": 15, + "execution_count": 5, "metadata": {}, "outputs": [], "source": [ - "TEST_SIZE = 365*3//5\n", - "VALIDATION_SIZE = 365*4//5\n", + "TEST_SIZE = 365//2\n", + "VALIDATION_SIZE = 365\n", "\n", "BATCH_SIZE = 64\n", - "INPUT_TIME_STEP = 10 # in minutes\n", + "INPUT_TIME_STEP = 5 # in minutes\n", "INPUT_FEATURES_SIZE = 7\n", "MAX_EPOCHS = 20" ] }, { "cell_type": "code", - "execution_count": 16, + "execution_count": 6, "metadata": {}, "outputs": [], "source": [ - "sleep_data = pd.read_csv(SLEEP_DATA_PATH)" + "SAMPLE_COUNT = 1000\n", + "# A R L D\n", + "# A\n", + "# R\n", + "# L\n", + "# D\n", + "CONFUSION_MATRIX = np.array(\n", + " [\n", + " [66.2, 5.0, 22.5, 6.2],\n", + " [1.6, 60.7, 33.0, 4.7],\n", + " [3.8, 22.3, 55.4, 18.5],\n", + " [0.0, 1.3, 26.7, 72.0],\n", + " ]\n", + ")/100" + ] + }, + { + "cell_type": "markdown", + "metadata": {}, + "source": [ + "### Import Data" ] }, { "cell_type": "code", - "execution_count": 17, + "execution_count": 14, + "metadata": {}, + "outputs": [], + "source": [ + "# sleep_data = pd.read_csv(SLEEP_DATA_PATH)\n", + "sleep_data = pd.read_csv(UPDATED_SLEEP_DATA_PATH)" + ] + }, + { + "cell_type": "code", + "execution_count": 15, "metadata": {}, "outputs": [ { @@ -746,19 +777,27 @@ " <th>minutes_since_begin</th>\n", " <th>stage_start_hour</th>\n", " <th>stage_start_minute</th>\n", - " <th>awake_probability</th>\n", - " <th>rem_probability</th>\n", - " <th>light_probability</th>\n", - " <th>deep_probability</th>\n", + " <th>awake_probability_noisy</th>\n", + " <th>rem_probability_noisy</th>\n", + " <th>light_probability_noisy</th>\n", + " <th>deep_probability_noisy</th>\n", + " <th>awake_probability_original</th>\n", + " <th>rem_probability_original</th>\n", + " <th>light_probability_original</th>\n", + " <th>deep_probability_original</th>\n", " </tr>\n", " </thead>\n", " <tbody>\n", " <tr>\n", " <th>0</th>\n", - " <td>0</td>\n", - " <td>0</td>\n", - " <td>8</td>\n", - " <td>18</td>\n", + " <td>0.0</td>\n", + " <td>0.0</td>\n", + " <td>8.0</td>\n", + " <td>18.0</td>\n", + " <td>0.680</td>\n", + " <td>0.057</td>\n", + " <td>0.200</td>\n", + " <td>0.063</td>\n", " <td>1.0</td>\n", " <td>0.0</td>\n", " <td>0.0</td>\n", @@ -766,10 +805,14 @@ " </tr>\n", " <tr>\n", " <th>1</th>\n", - " <td>0</td>\n", - " <td>1</td>\n", - " <td>8</td>\n", - " <td>19</td>\n", + " <td>0.0</td>\n", + " <td>1.0</td>\n", + " <td>8.0</td>\n", + " <td>19.0</td>\n", + " <td>0.652</td>\n", + " <td>0.060</td>\n", + " <td>0.224</td>\n", + " <td>0.064</td>\n", " <td>1.0</td>\n", " <td>0.0</td>\n", " <td>0.0</td>\n", @@ -777,10 +820,14 @@ " </tr>\n", " <tr>\n", " <th>2</th>\n", - " <td>0</td>\n", - " <td>2</td>\n", - " <td>8</td>\n", - " <td>20</td>\n", + " <td>0.0</td>\n", + " <td>2.0</td>\n", + " <td>8.0</td>\n", + " <td>20.0</td>\n", + " <td>0.672</td>\n", + " <td>0.059</td>\n", + " <td>0.209</td>\n", + " <td>0.060</td>\n", " <td>1.0</td>\n", " <td>0.0</td>\n", " <td>0.0</td>\n", @@ -788,10 +835,14 @@ " </tr>\n", " <tr>\n", " <th>3</th>\n", - " <td>0</td>\n", - " <td>3</td>\n", - " <td>8</td>\n", - " <td>21</td>\n", + " <td>0.0</td>\n", + " <td>3.0</td>\n", + " <td>8.0</td>\n", + " <td>21.0</td>\n", + " <td>0.645</td>\n", + " <td>0.056</td>\n", + " <td>0.235</td>\n", + " <td>0.064</td>\n", " <td>1.0</td>\n", " <td>0.0</td>\n", " <td>0.0</td>\n", @@ -799,10 +850,14 @@ " </tr>\n", " <tr>\n", " <th>4</th>\n", - " <td>0</td>\n", - " <td>4</td>\n", - " <td>8</td>\n", - " <td>22</td>\n", + " <td>0.0</td>\n", + " <td>4.0</td>\n", + " <td>8.0</td>\n", + " <td>22.0</td>\n", + " <td>0.644</td>\n", + " <td>0.054</td>\n", + " <td>0.244</td>\n", + " <td>0.058</td>\n", " <td>1.0</td>\n", " <td>0.0</td>\n", " <td>0.0</td>\n", @@ -818,13 +873,21 @@ " <td>...</td>\n", " <td>...</td>\n", " <td>...</td>\n", + " <td>...</td>\n", + " <td>...</td>\n", + " <td>...</td>\n", + " <td>...</td>\n", " </tr>\n", " <tr>\n", " <th>551037</th>\n", - " <td>1132</td>\n", - " <td>426</td>\n", - " <td>13</td>\n", - " <td>17</td>\n", + " <td>1132.0</td>\n", + " <td>426.0</td>\n", + " <td>13.0</td>\n", + " <td>17.0</td>\n", + " <td>0.041</td>\n", + " <td>0.193</td>\n", + " <td>0.576</td>\n", + " <td>0.190</td>\n", " <td>0.0</td>\n", " <td>0.0</td>\n", " <td>1.0</td>\n", @@ -832,10 +895,14 @@ " </tr>\n", " <tr>\n", " <th>551038</th>\n", - " <td>1132</td>\n", - " <td>427</td>\n", - " <td>13</td>\n", - " <td>18</td>\n", + " <td>1132.0</td>\n", + " <td>427.0</td>\n", + " <td>13.0</td>\n", + " <td>18.0</td>\n", + " <td>0.027</td>\n", + " <td>0.209</td>\n", + " <td>0.563</td>\n", + " <td>0.201</td>\n", " <td>0.0</td>\n", " <td>0.0</td>\n", " <td>1.0</td>\n", @@ -843,10 +910,14 @@ " </tr>\n", " <tr>\n", " <th>551039</th>\n", - " <td>1132</td>\n", - " <td>428</td>\n", - " <td>13</td>\n", - " <td>19</td>\n", + " <td>1132.0</td>\n", + " <td>428.0</td>\n", + " <td>13.0</td>\n", + " <td>19.0</td>\n", + " <td>0.032</td>\n", + " <td>0.220</td>\n", + " <td>0.574</td>\n", + " <td>0.174</td>\n", " <td>0.0</td>\n", " <td>0.0</td>\n", " <td>1.0</td>\n", @@ -854,10 +925,14 @@ " </tr>\n", " <tr>\n", " <th>551040</th>\n", - " <td>1132</td>\n", - " <td>429</td>\n", - " <td>13</td>\n", - " <td>20</td>\n", + " <td>1132.0</td>\n", + " <td>429.0</td>\n", + " <td>13.0</td>\n", + " <td>20.0</td>\n", + " <td>0.036</td>\n", + " <td>0.256</td>\n", + " <td>0.530</td>\n", + " <td>0.178</td>\n", " <td>0.0</td>\n", " <td>0.0</td>\n", " <td>1.0</td>\n", @@ -865,10 +940,14 @@ " </tr>\n", " <tr>\n", " <th>551041</th>\n", - " <td>1132</td>\n", - " <td>430</td>\n", - " <td>13</td>\n", - " <td>21</td>\n", + " <td>1132.0</td>\n", + " <td>430.0</td>\n", + " <td>13.0</td>\n", + " <td>21.0</td>\n", + " <td>0.033</td>\n", + " <td>0.205</td>\n", + " <td>0.571</td>\n", + " <td>0.191</td>\n", " <td>0.0</td>\n", " <td>0.0</td>\n", " <td>1.0</td>\n", @@ -876,53 +955,79 @@ " </tr>\n", " </tbody>\n", "</table>\n", - "<p>551042 rows × 8 columns</p>\n", + "<p>551042 rows × 12 columns</p>\n", "</div>" ], "text/plain": [ " sleep_id minutes_since_begin stage_start_hour stage_start_minute \\\n", - "0 0 0 8 18 \n", - "1 0 1 8 19 \n", - "2 0 2 8 20 \n", - "3 0 3 8 21 \n", - "4 0 4 8 22 \n", + "0 0.0 0.0 8.0 18.0 \n", + "1 0.0 1.0 8.0 19.0 \n", + "2 0.0 2.0 8.0 20.0 \n", + "3 0.0 3.0 8.0 21.0 \n", + "4 0.0 4.0 8.0 22.0 \n", "... ... ... ... ... \n", - "551037 1132 426 13 17 \n", - "551038 1132 427 13 18 \n", - "551039 1132 428 13 19 \n", - "551040 1132 429 13 20 \n", - "551041 1132 430 13 21 \n", + "551037 1132.0 426.0 13.0 17.0 \n", + "551038 1132.0 427.0 13.0 18.0 \n", + "551039 1132.0 428.0 13.0 19.0 \n", + "551040 1132.0 429.0 13.0 20.0 \n", + "551041 1132.0 430.0 13.0 21.0 \n", + "\n", + " awake_probability_noisy rem_probability_noisy \\\n", + "0 0.680 0.057 \n", + "1 0.652 0.060 \n", + "2 0.672 0.059 \n", + "3 0.645 0.056 \n", + "4 0.644 0.054 \n", + "... ... ... \n", + "551037 0.041 0.193 \n", + "551038 0.027 0.209 \n", + "551039 0.032 0.220 \n", + "551040 0.036 0.256 \n", + "551041 0.033 0.205 \n", + "\n", + " light_probability_noisy deep_probability_noisy \\\n", + "0 0.200 0.063 \n", + "1 0.224 0.064 \n", + "2 0.209 0.060 \n", + "3 0.235 0.064 \n", + "4 0.244 0.058 \n", + "... ... ... \n", + "551037 0.576 0.190 \n", + "551038 0.563 0.201 \n", + "551039 0.574 0.174 \n", + "551040 0.530 0.178 \n", + "551041 0.571 0.191 \n", "\n", - " awake_probability rem_probability light_probability \\\n", - "0 1.0 0.0 0.0 \n", - "1 1.0 0.0 0.0 \n", - "2 1.0 0.0 0.0 \n", - "3 1.0 0.0 0.0 \n", - "4 1.0 0.0 0.0 \n", - "... ... ... ... \n", - "551037 0.0 0.0 1.0 \n", - "551038 0.0 0.0 1.0 \n", - "551039 0.0 0.0 1.0 \n", - "551040 0.0 0.0 1.0 \n", - "551041 0.0 0.0 1.0 \n", + " awake_probability_original rem_probability_original \\\n", + "0 1.0 0.0 \n", + "1 1.0 0.0 \n", + "2 1.0 0.0 \n", + "3 1.0 0.0 \n", + "4 1.0 0.0 \n", + "... ... ... \n", + "551037 0.0 0.0 \n", + "551038 0.0 0.0 \n", + "551039 0.0 0.0 \n", + "551040 0.0 0.0 \n", + "551041 0.0 0.0 \n", "\n", - " deep_probability \n", - "0 0.0 \n", - "1 0.0 \n", - "2 0.0 \n", - "3 0.0 \n", - "4 0.0 \n", - "... ... \n", - "551037 0.0 \n", - "551038 0.0 \n", - "551039 0.0 \n", - "551040 0.0 \n", - "551041 0.0 \n", + " light_probability_original deep_probability_original \n", + "0 0.0 0.0 \n", + "1 0.0 0.0 \n", + "2 0.0 0.0 \n", + "3 0.0 0.0 \n", + "4 0.0 0.0 \n", + "... ... ... \n", + "551037 1.0 0.0 \n", + "551038 1.0 0.0 \n", + "551039 1.0 0.0 \n", + "551040 1.0 0.0 \n", + "551041 1.0 0.0 \n", "\n", - "[551042 rows x 8 columns]" + "[551042 rows x 12 columns]" ] }, - "execution_count": 17, + "execution_count": 15, "metadata": {}, "output_type": "execute_result" } @@ -931,6 +1036,67 @@ "sleep_data" ] }, + { + "cell_type": "markdown", + "metadata": {}, + "source": [ + "### Create Randmonizations" + ] + }, + { + "cell_type": "code", + "execution_count": 54, + "metadata": {}, + "outputs": [], + "source": [ + "def softmax(arr):\n", + " val = np.exp(arr)\n", + " return val / sum(val)" + ] + }, + { + "cell_type": "code", + "execution_count": 133, + "metadata": {}, + "outputs": [], + "source": [ + "def noisy_randomizer(confusion_matrix_index: int, sample_count: int = SAMPLE_COUNT, confusion_matrix = CONFUSION_MATRIX):\n", + " return np.random.multinomial(sample_count, confusion_matrix[confusion_matrix_index], size=1)[0]/sample_count" + ] + }, + { + "cell_type": "code", + "execution_count": 173, + "metadata": {}, + "outputs": [], + "source": [ + "def create_updated(dataframe):\n", + " dataframe_array = dataframe.to_numpy()\n", + " updated_probs = np.array(list(map(noisy_randomizer, np.argmax(dataframe_array[:, -4:], axis=1))))\n", + " columns_tmp = dataframe.columns.to_list() \n", + " noisy_column = list(map(lambda name: f\"{name}_noisy\", columns_tmp[-4:]))\n", + " og_column = list(map(lambda name: f\"{name}_original\", columns_tmp[-4:]))\n", + " return pd.DataFrame(np.concatenate([dataframe_array[:, :-4], updated_probs, dataframe_array[:, -4:]], axis=1), columns = columns_tmp[:-4]+noisy_column+og_column)" + ] + }, + { + "cell_type": "code", + "execution_count": 174, + "metadata": {}, + "outputs": [], + "source": [ + "sleep_data_updated = create_updated(sleep_data)" + ] + }, + { + "cell_type": "code", + "execution_count": 176, + "metadata": {}, + "outputs": [], + "source": [ + "sleep_data_updated.to_csv(UPDATED_SLEEP_DATA_PATH, index=False, index_label=False)" + ] + }, { "cell_type": "markdown", "metadata": {}, @@ -940,7 +1106,7 @@ }, { "cell_type": "code", - "execution_count": 8, + "execution_count": 16, "metadata": {}, "outputs": [], "source": [ @@ -951,13 +1117,13 @@ }, { "cell_type": "code", - "execution_count": 9, + "execution_count": 17, "metadata": {}, "outputs": [], "source": [ "# Adapted from https://www.tensorflow.org/tutorials/structured_data/time_series\n", "class WindowGenerator():\n", - " def __init__(self, data, index: str = \"sleep_id\", input_width: int = INPUT_TIME_STEP, validation_size: int = VALIDATION_SIZE, test_size: int = TEST_SIZE, input_feature_slice: slice = slice(1,100), label_feature_slice: slice = slice(-4,100), generate_data_now: bool = True):\n", + " def __init__(self, data, index: str = \"sleep_id\", input_width: int = INPUT_TIME_STEP, validation_size: int = VALIDATION_SIZE, test_size: int = TEST_SIZE, input_feature_slice: slice = slice(1,-4), label_feature_slice: slice = slice(-4,100), generate_data_now: bool = True):\n", " # Partition data\n", " self.training, self.testing = training_test_split_by_unique_index(data, index, test_size)\n", " self.training, self.validation = training_test_split_by_unique_index(self.training, index, validation_size)\n", @@ -996,8 +1162,9 @@ "\n", " def split_window(self, features):\n", " inputs = features[:, self.input_slice, self.input_feature_slice]\n", - " labels = tf.squeeze(features[:, self.labels_slice, self.label_feature_slice])\n", " inputs.set_shape([None, self.input_width, None])\n", + " \n", + " labels = tf.squeeze(features[:, self.labels_slice, self.label_feature_slice])\n", " # labels.set_shape([None, self.label_width, None])\n", " return inputs, labels\n", "\n", @@ -1027,12 +1194,12 @@ }, { "cell_type": "code", - "execution_count": 10, + "execution_count": 18, "metadata": {}, "outputs": [], "source": [ "# Adapted from https://www.tensorflow.org/tutorials/structured_data/time_series#linear_model\n", - "def compile_and_fit(model, window: WindowGenerator, loss = tf.losses.CategoricalCrossentropy(from_logits=True), optimizer = tf.optimizers.Adam(), metrics = None, early_stop: bool = True, patience:int = 5, baseline = None, epochs: int = MAX_EPOCHS):\n", + "def compile_and_fit(model, window: WindowGenerator, loss = tf.losses.CategoricalCrossentropy(from_logits=True), optimizer = tf.optimizers.Adam(), metrics = None, early_stop: bool = True, patience:int = 2, baseline = None, epochs: int = MAX_EPOCHS):\n", " if metrics is None:\n", " metrics = [tf.keras.metrics.CategoricalCrossentropy(from_logits=True), tf.keras.metrics.CategoricalAccuracy(), tf.keras.metrics.CategoricalHinge()]\n", "\n", @@ -1064,21 +1231,118 @@ }, { "cell_type": "code", - "execution_count": 23, + "execution_count": 19, "metadata": {}, "outputs": [], "source": [ "# USE SUBSET OF DATA FOR EXPERIMENTING\n", - "sleep_data_sub = sleep_data[sleep_data.sleep_id < 2000]" + "sleep_data_sub = sleep_data[sleep_data.sleep_id < 3]" ] }, { "cell_type": "code", - "execution_count": 24, + "execution_count": 20, "metadata": {}, "outputs": [], "source": [ - "wg_sub = WindowGenerator(sleep_data_sub,validation_size=365, test_size=182)" + "wg_sub = WindowGenerator(sleep_data_sub,validation_size=1, test_size=1)" + ] + }, + { + "cell_type": "code", + "execution_count": 24, + "metadata": {}, + "outputs": [ + { + "name": "stdout", + "output_type": "stream", + "text": [ + "ele[0][0] = array([[ 0., 7., 40., 1., 0., 0., 0.],\n", + " [ 1., 7., 41., 1., 0., 0., 0.],\n", + " [ 2., 7., 42., 1., 0., 0., 0.],\n", + " [ 3., 7., 43., 1., 0., 0., 0.],\n", + " [ 4., 7., 44., 1., 0., 0., 0.],\n", + " [ 5., 7., 45., 1., 0., 0., 0.],\n", + " [ 6., 7., 46., 1., 0., 0., 0.],\n", + " [ 7., 7., 47., 1., 0., 0., 0.],\n", + " [ 8., 7., 48., 1., 0., 0., 0.],\n", + " [ 9., 7., 49., 1., 0., 0., 0.]], dtype=float32)\n", + "ele[0][0] = array([[64., 8., 44., 0., 0., 1., 0.],\n", + " [65., 8., 45., 0., 0., 1., 0.],\n", + " [66., 8., 46., 0., 0., 1., 0.],\n", + " [67., 8., 47., 0., 0., 1., 0.],\n", + " [68., 8., 48., 0., 0., 1., 0.],\n", + " [69., 8., 49., 0., 0., 1., 0.],\n", + " [70., 8., 50., 0., 0., 1., 0.],\n", + " [71., 8., 51., 0., 0., 1., 0.],\n", + " [72., 8., 52., 0., 0., 1., 0.],\n", + " [73., 8., 53., 0., 0., 1., 0.]], dtype=float32)\n", + "ele[0][0] = array([[128., 9., 48., 0., 0., 1., 0.],\n", + " [129., 9., 49., 0., 0., 1., 0.],\n", + " [130., 9., 50., 0., 0., 1., 0.],\n", + " [131., 9., 51., 0., 0., 1., 0.],\n", + " [132., 9., 52., 0., 0., 0., 1.],\n", + " [133., 9., 53., 0., 0., 0., 1.],\n", + " [134., 9., 54., 0., 0., 0., 1.],\n", + " [135., 9., 55., 0., 0., 0., 1.],\n", + " [136., 9., 56., 0., 0., 0., 1.],\n", + " [137., 9., 57., 0., 0., 0., 1.]], dtype=float32)\n", + "ele[0][0] = array([[192., 10., 52., 0., 1., 0., 0.],\n", + " [193., 10., 53., 0., 1., 0., 0.],\n", + " [194., 10., 54., 0., 1., 0., 0.],\n", + " [195., 10., 55., 0., 1., 0., 0.],\n", + " [196., 10., 56., 0., 1., 0., 0.],\n", + " [197., 10., 57., 0., 1., 0., 0.],\n", + " [198., 10., 58., 0., 1., 0., 0.],\n", + " [199., 10., 59., 0., 1., 0., 0.],\n", + " [200., 11., 0., 0., 1., 0., 0.],\n", + " [201., 11., 1., 0., 1., 0., 0.]], dtype=float32)\n", + "ele[0][0] = array([[256., 11., 56., 0., 0., 1., 0.],\n", + " [257., 11., 57., 0., 0., 1., 0.],\n", + " [258., 11., 58., 0., 0., 1., 0.],\n", + " [259., 11., 59., 0., 0., 1., 0.],\n", + " [260., 12., 0., 0., 0., 1., 0.],\n", + " [261., 12., 1., 0., 0., 1., 0.],\n", + " [262., 12., 2., 0., 0., 1., 0.],\n", + " [263., 12., 3., 0., 0., 1., 0.],\n", + " [264., 12., 4., 0., 0., 1., 0.],\n", + " [265., 12., 5., 0., 0., 1., 0.]], dtype=float32)\n", + "ele[0][0] = array([[320., 13., 0., 0., 1., 0., 0.],\n", + " [321., 13., 1., 0., 1., 0., 0.],\n", + " [322., 13., 2., 0., 1., 0., 0.],\n", + " [323., 13., 3., 0., 1., 0., 0.],\n", + " [324., 13., 4., 0., 1., 0., 0.],\n", + " [325., 13., 5., 0., 1., 0., 0.],\n", + " [326., 13., 6., 0., 1., 0., 0.],\n", + " [327., 13., 7., 0., 1., 0., 0.],\n", + " [328., 13., 8., 0., 1., 0., 0.],\n", + " [329., 13., 9., 0., 1., 0., 0.]], dtype=float32)\n", + "ele[0][0] = array([[384., 14., 4., 0., 0., 0., 1.],\n", + " [385., 14., 5., 0., 0., 0., 1.],\n", + " [386., 14., 6., 0., 0., 0., 1.],\n", + " [387., 14., 7., 0., 0., 0., 1.],\n", + " [388., 14., 8., 0., 0., 0., 1.],\n", + " [389., 14., 9., 0., 0., 0., 1.],\n", + " [390., 14., 10., 0., 0., 0., 1.],\n", + " [391., 14., 11., 0., 0., 0., 1.],\n", + " [392., 14., 12., 0., 0., 0., 1.],\n", + " [393., 14., 13., 0., 0., 0., 1.]], dtype=float32)\n", + "ele[0][0] = array([[448., 15., 8., 0., 1., 0., 0.],\n", + " [449., 15., 9., 0., 1., 0., 0.],\n", + " [450., 15., 10., 0., 1., 0., 0.],\n", + " [451., 15., 11., 0., 1., 0., 0.],\n", + " [452., 15., 12., 0., 1., 0., 0.],\n", + " [453., 15., 13., 0., 1., 0., 0.],\n", + " [454., 15., 14., 0., 1., 0., 0.],\n", + " [455., 15., 15., 0., 1., 0., 0.],\n", + " [456., 15., 16., 0., 1., 0., 0.],\n", + " [457., 15., 17., 0., 1., 0., 0.]], dtype=float32)\n" + ] + } + ], + "source": [ + "for ele in wg_sub.training_ds.as_numpy_iterator():\n", + " print(f\"{ele[0][0] = }\")" ] }, { @@ -1255,19 +1519,27 @@ }, { "cell_type": "code", - "execution_count": 34, + "execution_count": 19, "metadata": {}, "outputs": [ + { + "name": "stderr", + "output_type": "stream", + "text": [ + "2022-05-12 14:18:02.248350: I tensorflow/core/platform/cpu_feature_guard.cc:151] This TensorFlow binary is optimized with oneAPI Deep Neural Network Library (oneDNN) to use the following CPU instructions in performance-critical operations: AVX2 FMA\n", + "To enable them in other operations, rebuild TensorFlow with the appropriate compiler flags.\n" + ] + }, { "data": { "text/plain": [ "WindowGenerator:\n", - "\tTotal window size: 11\n", - "\tInput indices: [0 1 2 3 4 5 6 7 8 9]\n", - "\tLabel indices: [10]" + "\tTotal window size: 6\n", + "\tInput indices: [0 1 2 3 4]\n", + "\tLabel indices: [5]" ] }, - "execution_count": 34, + "execution_count": 19, "metadata": {}, "output_type": "execute_result" } @@ -1279,16 +1551,16 @@ }, { "cell_type": "code", - "execution_count": 35, + "execution_count": 20, "metadata": {}, "outputs": [ { "data": { "text/plain": [ - "9647" + "4682" ] }, - "execution_count": 35, + "execution_count": 20, "metadata": {}, "output_type": "execute_result" } @@ -1297,6 +1569,31 @@ "len(wg.training_ds)" ] }, + { + "cell_type": "code", + "execution_count": 27, + "metadata": {}, + "outputs": [ + { + "name": "stdout", + "output_type": "stream", + "text": [ + "ele[0].numpy()[0] = array([[ 0. , 8. , 18. , 0.68 , 0.057, 0.2 , 0.063],\n", + " [ 1. , 8. , 19. , 0.652, 0.06 , 0.224, 0.064],\n", + " [ 2. , 8. , 20. , 0.672, 0.059, 0.209, 0.06 ],\n", + " [ 3. , 8. , 21. , 0.645, 0.056, 0.235, 0.064],\n", + " [ 4. , 8. , 22. , 0.644, 0.054, 0.244, 0.058]],\n", + " dtype=float32)\n", + "ele[1].numpy()[0] = array([1., 0., 0., 0.], dtype=float32)\n" + ] + } + ], + "source": [ + "for ele in wg.sample_ds.take(1):\n", + " print(f\"{ele[0].numpy()[0] = }\")\n", + " print(f\"{ele[1].numpy()[0] = }\")" + ] + }, { "cell_type": "markdown", "metadata": {}, @@ -1306,7 +1603,7 @@ }, { "cell_type": "code", - "execution_count": 36, + "execution_count": 34, "metadata": {}, "outputs": [], "source": [ @@ -1317,9 +1614,30 @@ }, { "cell_type": "code", - "execution_count": 37, + "execution_count": 35, "metadata": {}, - "outputs": [], + "outputs": [ + { + "name": "stdout", + "output_type": "stream", + "text": [ + "Model: \"sequential_2\"\n", + "_________________________________________________________________\n", + " Layer (type) Output Shape Param # \n", + "=================================================================\n", + " lstm (LSTM) (None, 8) 512 \n", + " \n", + " dense_2 (Dense) (None, 4) 36 \n", + " \n", + "=================================================================\n", + "Total params: 548\n", + "Trainable params: 548\n", + "Non-trainable params: 0\n", + "_________________________________________________________________\n", + "None\n" + ] + } + ], "source": [ "# Model Definition\n", "lstm_model = keras.Sequential()\n", @@ -1370,7 +1688,7 @@ }, { "cell_type": "code", - "execution_count": 40, + "execution_count": 32, "metadata": {}, "outputs": [], "source": [ @@ -1380,20 +1698,20 @@ }, { "cell_type": "code", - "execution_count": 45, + "execution_count": 33, "metadata": {}, "outputs": [ { "name": "stdout", "output_type": "stream", "text": [ - "Model: \"sequential_8\"\n", + "Model: \"sequential_1\"\n", "_________________________________________________________________\n", " Layer (type) Output Shape Param # \n", "=================================================================\n", - " gru_7 (GRU) (None, 16) 1200 \n", + " gru (GRU) (None, 16) 1200 \n", " \n", - " dense_14 (Dense) (None, 4) 68 \n", + " dense_1 (Dense) (None, 4) 68 \n", " \n", "=================================================================\n", "Total params: 1,268\n", @@ -1439,33 +1757,34 @@ }, { "cell_type": "code", - "execution_count": 47, + "execution_count": 13, "metadata": {}, "outputs": [], "source": [ - "ATTENTION_UNITS = 16" + "ATTENTION_UNITS = 32" ] }, { "cell_type": "code", - "execution_count": 49, + "execution_count": 14, "metadata": {}, "outputs": [ { "name": "stdout", "output_type": "stream", "text": [ - "Model: \"sequential_10\"\n", + "Model: \"sequential\"\n", "_________________________________________________________________\n", " Layer (type) Output Shape Param # \n", "=================================================================\n", - " attention_1 (Attention) (None, 16) 273 \n", + " custom_attention (CustomAtt (None, 32) 497 \n", + " ention) \n", " \n", - " dense_16 (Dense) (None, 4) 68 \n", + " dense (Dense) (None, 4) 132 \n", " \n", "=================================================================\n", - "Total params: 341\n", - "Trainable params: 341\n", + "Total params: 629\n", + "Trainable params: 629\n", "Non-trainable params: 0\n", "_________________________________________________________________\n", "None\n" @@ -1475,7 +1794,7 @@ "source": [ "am_model = keras.Sequential()\n", "am_model.add(layers.Input(shape=(INPUT_TIME_STEP, INPUT_FEATURES_SIZE)))\n", - "am_model.add(Attention(ATTENTION_UNITS))\n", + "am_model.add(CustomAttention(ATTENTION_UNITS))\n", "am_model.add(layers.Dense(SLEEP_STAGES))\n", "am_model.build()\n", "print(am_model.summary())" @@ -1483,19 +1802,217 @@ }, { "cell_type": "code", - "execution_count": 50, + "execution_count": 15, + "metadata": {}, + "outputs": [ + { + "data": { + "text/plain": [ + "<tensorflow.python.training.tracking.util.CheckpointLoadStatus at 0x12aaebe50>" + ] + }, + "execution_count": 15, + "metadata": {}, + "output_type": "execute_result" + } + ], + "source": [ + "am_model.load_weights(\"TEST\")" + ] + }, + { + "cell_type": "code", + "execution_count": 17, + "metadata": {}, + "outputs": [], + "source": [ + "am_history = compile_and_fit(model=am_model, window=wg, epochs=0)" + ] + }, + { + "cell_type": "code", + "execution_count": 18, "metadata": {}, "outputs": [ { "name": "stdout", "output_type": "stream", "text": [ - "9647/9647 [==============================] - 52s 5ms/step - loss: 0.6620 - categorical_crossentropy: 0.6619 - categorical_accuracy: 0.7268 - categorical_hinge: 0.7192 - val_loss: 0.2141 - val_categorical_crossentropy: 0.2140 - val_categorical_accuracy: 0.9589 - val_categorical_hinge: 0.1990\n" + "1442/1442 [==============================] - 14s 4ms/step - loss: 0.1957 - categorical_crossentropy: 0.1957 - categorical_accuracy: 0.9598 - categorical_hinge: 0.1911\n" ] + }, + { + "data": { + "text/plain": [ + "[0.19572481513023376,\n", + " 0.19574123620986938,\n", + " 0.9597873687744141,\n", + " 0.1910863220691681]" + ] + }, + "execution_count": 18, + "metadata": {}, + "output_type": "execute_result" } ], "source": [ - "am_history = compile_and_fit(model=am_model, window=wg, epochs=1)" + "am_model.evaluate(wg.testing_ds)" + ] + }, + { + "cell_type": "code", + "execution_count": 47, + "metadata": {}, + "outputs": [ + { + "data": { + "text/plain": [ + "array([[ 0.59796184, -0.20803624, -0.2916372 , -0.7170148 ]],\n", + " dtype=float32)" + ] + }, + "execution_count": 47, + "metadata": {}, + "output_type": "execute_result" + } + ], + "source": [ + "answer = am_model.predict(np.array(\n", + " [[\n", + " [ 150., 10., 20., 0.5, 0.1, 0., 0.4],\n", + " [ 151., 10., 21., 0.5, 0.2, 0., 0.3],\n", + " [ 152., 10., 22., 0.5, 0.3, 0., 0.2],\n", + " [ 153., 10., 23., 0.5, 0.4, 0., 0.1],\n", + " [ 154., 10., 24., 0.2, 0.1, 0., 0.],\n", + " [ 155., 10., 25., 0.2, 0.2, 0., 0.],\n", + " [ 156., 10., 26., 0.2, 0.2, 0.1, 0.],\n", + " [ 157., 10., 27., 0.2, 0.25, 0.15, 0.],\n", + " [ 158., 10., 28., 0.2, 0.3, 0.2, 0.],\n", + " [ 159., 10., 29., 0.2, 0.3, 0.3, 0.]\n", + " ]]\n", + "))\n", + "norm = np.linalg.norm(answer)\n", + "normalized_answer = answer/norm\n", + "normalized_answer" + ] + }, + { + "cell_type": "code", + "execution_count": 43, + "metadata": {}, + "outputs": [], + "source": [ + "pd.DataFrame.from_dict(am_history.history).to_csv(f\"{HISTORY_DIR}/am_220512.csv\", index=False)" + ] + }, + { + "cell_type": "code", + "execution_count": 46, + "metadata": {}, + "outputs": [ + { + "name": "stdout", + "output_type": "stream", + "text": [ + "Help on method save_weights in module keras.engine.training:\n", + "\n", + "save_weights(filepath, overwrite=True, save_format=None, options=None) method of keras.engine.sequential.Sequential instance\n", + " Saves all layer weights.\n", + " \n", + " Either saves in HDF5 or in TensorFlow format based on the `save_format`\n", + " argument.\n", + " \n", + " When saving in HDF5 format, the weight file has:\n", + " - `layer_names` (attribute), a list of strings\n", + " (ordered names of model layers).\n", + " - For every layer, a `group` named `layer.name`\n", + " - For every such layer group, a group attribute `weight_names`,\n", + " a list of strings\n", + " (ordered names of weights tensor of the layer).\n", + " - For every weight in the layer, a dataset\n", + " storing the weight value, named after the weight tensor.\n", + " \n", + " When saving in TensorFlow format, all objects referenced by the network are\n", + " saved in the same format as `tf.train.Checkpoint`, including any `Layer`\n", + " instances or `Optimizer` instances assigned to object attributes. For\n", + " networks constructed from inputs and outputs using `tf.keras.Model(inputs,\n", + " outputs)`, `Layer` instances used by the network are tracked/saved\n", + " automatically. For user-defined classes which inherit from `tf.keras.Model`,\n", + " `Layer` instances must be assigned to object attributes, typically in the\n", + " constructor. See the documentation of `tf.train.Checkpoint` and\n", + " `tf.keras.Model` for details.\n", + " \n", + " While the formats are the same, do not mix `save_weights` and\n", + " `tf.train.Checkpoint`. Checkpoints saved by `Model.save_weights` should be\n", + " loaded using `Model.load_weights`. Checkpoints saved using\n", + " `tf.train.Checkpoint.save` should be restored using the corresponding\n", + " `tf.train.Checkpoint.restore`. Prefer `tf.train.Checkpoint` over\n", + " `save_weights` for training checkpoints.\n", + " \n", + " The TensorFlow format matches objects and variables by starting at a root\n", + " object, `self` for `save_weights`, and greedily matching attribute\n", + " names. For `Model.save` this is the `Model`, and for `Checkpoint.save` this\n", + " is the `Checkpoint` even if the `Checkpoint` has a model attached. This\n", + " means saving a `tf.keras.Model` using `save_weights` and loading into a\n", + " `tf.train.Checkpoint` with a `Model` attached (or vice versa) will not match\n", + " the `Model`'s variables. See the\n", + " [guide to training checkpoints](https://www.tensorflow.org/guide/checkpoint)\n", + " for details on the TensorFlow format.\n", + " \n", + " Args:\n", + " filepath: String or PathLike, path to the file to save the weights to.\n", + " When saving in TensorFlow format, this is the prefix used for\n", + " checkpoint files (multiple files are generated). Note that the '.h5'\n", + " suffix causes weights to be saved in HDF5 format.\n", + " overwrite: Whether to silently overwrite any existing file at the\n", + " target location, or provide the user with a manual prompt.\n", + " save_format: Either 'tf' or 'h5'. A `filepath` ending in '.h5' or\n", + " '.keras' will default to HDF5 if `save_format` is `None`. Otherwise\n", + " `None` defaults to 'tf'.\n", + " options: Optional `tf.train.CheckpointOptions` object that specifies\n", + " options for saving weights.\n", + " \n", + " Raises:\n", + " ImportError: If `h5py` is not available when attempting to save in HDF5\n", + " format.\n", + "\n" + ] + } + ], + "source": [ + "help(am_model.save_weights)" + ] + }, + { + "cell_type": "code", + "execution_count": 35, + "metadata": {}, + "outputs": [ + { + "name": "stderr", + "output_type": "stream", + "text": [ + "2022-05-12 12:12:02.267722: W tensorflow/python/util/util.cc:368] Sets are not currently considered sequences, but this may change in the future, so consider avoiding using them.\n", + "WARNING:absl:Found untraced functions such as attention_score_vec_layer_call_fn, attention_score_vec_layer_call_and_return_conditional_losses, last_hidden_state_layer_call_fn, last_hidden_state_layer_call_and_return_conditional_losses, attention_score_layer_call_fn while saving (showing 5 of 14). These functions will not be directly callable after loading.\n" + ] + }, + { + "name": "stdout", + "output_type": "stream", + "text": [ + "INFO:tensorflow:Assets written to: .model/attention/assets\n" + ] + }, + { + "name": "stderr", + "output_type": "stream", + "text": [ + "INFO:tensorflow:Assets written to: .model/attention/assets\n" + ] + } + ], + "source": [ + "am_model.save(f\"{MODEL_DIR}/attention\")" ] }, { @@ -1505,12 +2022,143 @@ "### Model Head-to-Head testing" ] }, + { + "cell_type": "code", + "execution_count": 34, + "metadata": {}, + "outputs": [], + "source": [ + "HISTORY_DIR = \".history\"\n", + "MODEL_DIR = \".model\"" + ] + }, + { + "cell_type": "code", + "execution_count": 25, + "metadata": {}, + "outputs": [], + "source": [ + "base_history = pd.read_csv(f\"{HISTORY_DIR}/baseline.csv\")\n", + "lstm_history = pd.read_csv(f\"{HISTORY_DIR}/lstm.csv\")\n", + "gru_history = pd.read_csv(f\"{HISTORY_DIR}/gru.csv\")\n", + "attn_history = pd.read_csv(f\"{HISTORY_DIR}/attention.csv\")\n", + "history_columns = [\"categorical_crossentropy\", \"val_categorical_crossentropy\"] # \"categorical_accuracy\"" + ] + }, + { + "cell_type": "code", + "execution_count": 26, + "metadata": {}, + "outputs": [ + { + "data": { + "text/plain": [ + "<AxesSubplot:>" + ] + }, + "execution_count": 26, + "metadata": {}, + "output_type": "execute_result" + }, + { + "data": { + "image/png": "iVBORw0KGgoAAAANSUhEUgAAAXkAAAD4CAYAAAAJmJb0AAAAOXRFWHRTb2Z0d2FyZQBNYXRwbG90bGliIHZlcnNpb24zLjUuMiwgaHR0cHM6Ly9tYXRwbG90bGliLm9yZy8qNh9FAAAACXBIWXMAAAsTAAALEwEAmpwYAAAwOklEQVR4nO3deXxU5fX48c+ZyUbYQyJrAqIUZQ2yCcoiVnGh4MLiCgiUUnHv9+vyxYW29tW6FK3LD0RZRFERENQWW7VCkSpoQHYQAQHZQ1jDlmXO7487iUOYkEkyyWRmzvv1GnKXZ+49ubmcufPMM+eKqmKMMSYyuUIdgDHGmIpjSd4YYyKYJXljjIlgluSNMSaCWZI3xpgIFhOqHScnJ2uzZs1CtXtjjAlLy5cvP6CqKYG2D1mSb9asGRkZGaHavTHGhCUR2V6a9tZdY4wxEcySvDHGRDBL8sYYE8FC1idvTLDl5uayc+dOTp06FepQjCm3hIQEmjRpQmxsbLm2Y0neRIydO3dSs2ZNmjVrhoiEOhxjykxVycrKYufOnZx//vnl2pZ115iIcerUKerVq2cJ3oQ9EaFevXpBeVdqSd5EFEvwJlIE61wOuyS/ce9RnvnnRo6czA11KMYYU+WFXZLfkXWCiYu2sO3A8VCHYowxVV7YJfm0eokA7Dh4IsSRGFM+ixYt4quvvqqUfV133XUcPny41M+bPn0699xzT/ADqmDbtm3jnXfeCXUYVULASV5E3CLynYj83c+6eBGZJSKbRWSZiDQLapQ+0pIsyZvIUBlJXlXxeDwsWLCAOnXqVOi+zrX/ynauJJ+Xl1fJ0YRWaYZQ3g9sAGr5WTcSOKSqF4rILcAzwJAgxHeWxLgYkmvEsyPLkrwp3u8/Xsf63UeDus1WjWrx1K9al9huxowZPP/884gI7dq1Y/DgwTz99NPk5ORQr149Zs6cycmTJ5k0aRJut5u3336bl19+mYsuuogxY8awY8cOAF588UUuu+wyMjMzue2229i9ezfdunXjs88+Y/ny5SQnJzNhwgSmTp0KwKhRo3jggQfYtm0bffv2pWvXrixfvpwFCxbQq1cvMjIySE5OPiu+t956i48//visGOvXr1/i77pv3z7GjBnD1q1bAZg4cSKNGjU6a/+vvPIKn3zyCSLC448/zpAhQ9izZw9Dhgzh6NGj5OXlMXHiRLp3787IkSPJyMhARBgxYgQPPvggW7ZsYezYsWRmZpKYmMjrr7/ORRddxPDhw6lVqxYZGRns3buXZ599loEDB/Loo4+yYcMG0tPTGTZsGHXr1uWDDz4gOzub/Px85s2bx4gRI9i6dSuJiYlMnjyZdu3aMX78eLZs2cLmzZs5cOAADz/8ML/+9a8ZOnQoN910EzfccAMAt99+O4MHD2bAgAFlPJsqT0BJXkSaANcDfwIe8tNkADDeOz0HeEVERCvoBrJpSdXsSt5USevWrePpp5/mq6++Ijk5mYMHDyIiLF26FBHhjTfe4Nlnn+Wvf/0rY8aMoUaNGvzP//wPALfddhsPPvggl19+OTt27KBv375s2LCB3//+9/Tp04fHHnuMf/7zn0yZMgWA5cuXM23aNJYtW4aq0rVrV3r16kXdunX54YcfePPNN7n00ktLjA/g8ssv9xtjSe677z569erFvHnzyM/PJzs7m0OHDp2x/7lz57Jy5UpWrVrFgQMH6Ny5Mz179uSdd96hb9++jBs3jvz8fE6cOMHKlSvZtWsXa9euBSjsYho9ejSTJk2iRYsWLFu2jLvvvpsvvvgCgD179rBkyRI2btxI//79GThwIH/5y194/vnn+fvfnY6H6dOns2LFClavXk1SUhL33nsvHTp0YP78+XzxxRcMHTqUlStXArB69WqWLl3K8ePH6dChA9dffz0jR47khRde4IYbbuDIkSN89dVXvPnmm+U7WSpJoFfyLwIPAzWLWd8Y+AlAVfNE5AhQDzjg20hERgOjAdLS0soQriMtKZFvtx0q8/NN5AvkirsifPHFFwwaNIjk5GQAkpKSWLNmTeGVa05OTrFfbvn8889Zv3594fzRo0fJzs5myZIlzJs3D4BrrrmGunXrArBkyRJuvPFGqlevDsBNN93El19+Sf/+/WnatOlZCb64+MD5IlkgMfrb3owZMwBwu93Url2bQ4cOnbH/JUuWcOutt+J2u6lfvz69evXi22+/pXPnzowYMYLc3FxuuOEG0tPTad68OVu3buXee+/l+uuv5+qrryY7O5uvvvqKQYMGFe739OnThdM33HADLpeLVq1asW/fvmJjveqqqwp/3yVLljB37lwA+vTpQ1ZWFkePOu/8BgwYQLVq1ahWrRpXXHEF33zzDTfccAN33303mZmZzJ07l5tvvpmYmPD4LmmJffIi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715NTU3V3bt368KFCzUxMVG3bt1auO2C55Q2xnOVDVBV7dKli37wwQeqqnry5Ek9fvz4Wft//vnn9a677lJV1Q0bNmhqaqqePHlS77nnHn377bdVVfX06dN64sQJnTNnjo4aNapw+4cPH9acnBzt1q2b7t+/X1VV33vvvcLt9erVSx966CFVVf3HP/6hV155paqqTps2TceOHVu4naeeekovueQSPXHihKqq9uvXT6dPn66qqlOmTNEBAwYU/k369u2r+fn5umnTJm3cuLGePHlSp0+frvfff7+qqn7//fdaXD6s9LIGVU1qUiLzV+4iJ89DXEzY9jyZilDCFXdF6dChA/v372f37t1kZmZSt25dGjRowIMPPsjixYtxuVzs2rWLffv20aBBg3Nu6/PPP+euu+4qvAIuqIW+du1aHn/8cQ4fPkx2djZ9+/Y967nnqsH+9ddfM3/+fMC5UUnBTUuKq/teq1YtunTp4rfGfHliLOrYsWPs2rWLG2+8EYCEhITCdb77X7JkCffeey8AF110EU2bNmXTpk1069aNP/3pT+zcuZObbrqJFi1a0LZtW373u9/xyCOP0K9fP3r06MHatWtZu3YtV111FeBUz2zYsGHhvm666SYAOnbsyLZt24qNt3///lSrVq3wmH7wwQcA3HnnnTz88MOF7QYPHozL5aJFixY0b96cjRs3MmjQIP74xz/y3HPPMXXqVIYPH17i8SmrsE7yaUmJqMKuwyc5P7l09bONqSiDBg1izpw57N27lyFDhjBz5kwyMzNZvnw5sbGxNGvWrFz12ocPH878+fNp374906dPZ9GiRWe18a3BHgylrU8fSIzB3v9tt91G165d+cc//sF1113Ha6+9Rp8+fVixYgULFizg8ccf58orr+TGG2+kdevWfP311363U1Cf3u12n7O/vTz16RMTE7nqqqv48MMPef/991m+vNy36yhWWF/+2jBKUxUNGTKE9957jzlz5jBo0CCOHDnCeeedR2xsLAsXLgy4BspVV13FtGnTOHHCOb8Lar8fO3aMhg0bkpubW1gTHc6soX6uGuwFt+QDeO+99wqfX1zd92DGeC41a9akSZMmhe8yTp8+XbhdX7614Ddt2sSOHTto2bIlW7dupXnz5tx3330MGDCA1atXs3v3bhITE7njjjv43//9X1asWEHLli3JzMwsTPK5ubmsW7euxNjOVZ++e/fuhcdy5syZZ9T1nz17Nh6Pp7APv2XLloBzT9777ruPzp07F97tqyJYkjcmyFq3bs2xY8do3LgxDRs25PbbbycjI4O2bdsyY8YMLrroooC2c80119C/f386depEenp64dDDP/7xj3Tt2pXLLrvsjG3dcsstPPfcc3To0IEtW7YUW4P9xRdfZMKECbRr147NmzcXVlUsru57MGMsyVtvvcVLL71Eu3bt6N69O3v37j2rzd13343H46Ft27YMGTKE6dOnEx8fz/vvv0+bNm1IT09n7dq1DB06lDVr1tClSxfS09P5/e9/z+OPP05cXBxz5szhkUceoX379qSnp5c4WuiKK65g/fr1pKenM2vWrLPWv/zyy0ybNq3wxuh/+9vfCtelpaXRpUsXrr32WiZNmlTYDdWxY0dq1apV4fXpRUNU+6VTp06akZFRrm14PMrFT/6TYd2b8X/XXRykyEy42rBhAxdfbOdBSU6cOEG1atUQEd577z3efffdEm/CYcpm+PDh9OvXj4EDB561bvfu3fTu3ZuNGzficvm/3vZ3TovIclXtFGgMYd0n73IJqUmJbM86HupQjAkby5cv55577kFVqVOnDlOnTg11SFFnxowZjBs3jgkTJhSb4IOlxCQvIgnAYiDe236Oqj5VpM1w4Dmce70CvKKqbwQ3VP+cksN2r1cTvtasWcOdd955xrL4+HiWLVtWIfvr0aNHifdIrWhjx47lv//97xnL7r///vC7tV4Jpk+f7nf50KFDGTp0aKXEEMiV/Gmgj6pmi0gssEREPlHVpUXazVLVe4If4rmlJSXyzY8HUdWzPsU20Sccz4O2bdsGbRRMuHj11VdDHUKVF6yu9EBu5K2qmu2djfU+qkwR99SkRLJP53HISg5HvYSEBLKysuweAybsqSpZWVlnfFegrALqkxcRN7AcuBB4VVX9vY+8WUR6ApuAB1X1Jz/bGQ2MBucT52DwHWGTVD0uKNs04alJkybs3LmTzMzMUIdiTLklJCTQpEmTcm8noCSvqvlAuojUAeaJSBtVXevT5GPgXVU9LSK/Ad4E+vjZzmRgMjija8obPDj1a8BJ8umpdYKxSROmYmNj/X4r05hoVqqPdVX1MLAQuKbI8ixVPe2dfQPoGJToApBa15vkbYSNMcacpcQkLyIp3it4RKQacBWwsUib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", + "text/plain": [ + "<Figure size 432x288 with 1 Axes>" + ] + }, + "metadata": { + "needs_background": "light" + }, + "output_type": "display_data" + }, + { + "data": { + "image/png": "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", + "text/plain": [ + "<Figure size 432x288 with 1 Axes>" + ] + }, + "metadata": { + "needs_background": "light" + }, + "output_type": "display_data" + }, + { + "data": { + "image/png": "iVBORw0KGgoAAAANSUhEUgAAAXQAAAD4CAYAAAD8Zh1EAAAAOXRFWHRTb2Z0d2FyZQBNYXRwbG90bGliIHZlcnNpb24zLjUuMiwgaHR0cHM6Ly9tYXRwbG90bGliLm9yZy8qNh9FAAAACXBIWXMAAAsTAAALEwEAmpwYAAAwXElEQVR4nO3deXiU9b3//+dnZpLJNiGBJOyIWg6IAkEQ3BDBDZcCLoArIqJfF9TqOUfxhwtt7VWrHqpYv1KtgigWBQRppXWFYyliDTSyi8AXIWxZgOzbzLx/f9yTYRKyDGS/5/24rrnm3uaed26G13zm3j5GRFBKKdX+OVq7AKWUUk1DA10ppWxCA10ppWxCA10ppWxCA10ppWzC1VpvnJKSIr17926tt1dKqXZp/fr1uSKSWtu8Vgv03r17k5GR0Vpvr5RS7ZIx5qe65ukuF6WUsgkNdKWUsgkNdKWUsolW24euVFOrrKwkKyuLsrKy1i5FqUaLiYmhR48eREVFhf0aDXRlG1lZWXg8Hnr37o0xprXLUeqUiQh5eXlkZWVx+umnh/063eWibKOsrIxOnTppmKt2zxhDp06dTvrXpga6shUNc2UXp/JZbneB/t2eI/zu79vR2/4qpVR17S7QN2bl8/rqXeSXVrZ2KUop1aa0u0BP9bgByCksb+VKlGqc1atXs3bt2hZ5r2uuuYZjx46d9Ovmz5/P9OnTm76gZrZnzx7ef//91i6jxbW7QE8LBHq2Brpq51oi0EUEv9/PypUrSUpKatb3qu/9W1p9ge71elu4mpbT7k5b1Ba6Cscv/7KFrQcKmnSd/bsl8uzPz25wuQULFvDSSy9hjGHgwIFMnDiR5557joqKCjp16sTChQspLS1l7ty5OJ1O3nvvPV599VX69evHfffdx969ewF4+eWXueiii8jJyeHWW2/lwIEDXHDBBXz++eesX7+elJQUZs+ezdtvvw3AtGnT+MUvfsGePXu46qqrGD58OOvXr2flypWMHDmSjIwMUlJSTqjv3Xff5S9/+csJNXbu3LnBv/Xw4cPcd9997N69G4DXX3+dbt26nfD+f/jDH/jb3/6GMYannnqKSZMmcfDgQSZNmkRBQQFer5fXX3+dCy+8kLvvvpuMjAyMMUydOpVHH32UXbt28eCDD5KTk0NcXBxvvvkm/fr1Y8qUKSQmJpKRkcGhQ4d44YUXuOmmm5gxYwbbtm0jPT2dO++8k+TkZD766COKiorw+XwsW7aMqVOnsnv3buLi4njjjTcYOHAgs2bNYteuXezcuZPc3Fwef/xx7rnnHiZPnswNN9zA+PHjAbjtttuYOHEi48aNO8VPU/Nod4F+vIWuF4+otmfLli0899xzrF27lpSUFI4cOYIxhnXr1mGM4U9/+hMvvPAC//M//8N9991HQkIC//Vf/wXArbfeyqOPPsrFF1/M3r17ueqqq9i2bRu//OUvGT16NE8++SR///vfeeuttwBYv3498+bN49tvv0VEGD58OCNHjiQ5OZkff/yRd955h/PPP7/B+gAuvvjiWmtsyMMPP8zIkSNZtmwZPp+PoqIijh49Wu39ly5dSmZmJt9//z25ubmcd955XHLJJbz//vtcddVVzJw5E5/PR0lJCZmZmezfv5/NmzcDBHcT3XvvvcydO5c+ffrw7bff8sADD/DVV18BcPDgQdasWcP27dsZO3YsN910E88//zwvvfQSf/3rXwFr19GGDRvYuHEjHTt25KGHHmLw4MEsX76cr776ismTJ5OZmQnAxo0bWbduHcXFxQwePJhrr72Wu+++m9///veMHz+e/Px81q5dyzvvvNO4D0szCCvQjTFjgFcAJ/AnEXm+xvzfA6MCo3FAmogkNWGdQQluFzFRDm2hq3qF05JuDl999RUTJkwgJSUFgI4dO7Jp06Zgi7SioqLOC0W++OILtm7dGhwvKCigqKiINWvWsGzZMgDGjBlDcnIyAGvWrOH6668nPj4egBtuuIF//OMfjB07ltNOO+2EMK+rPrAuygqnxtrWt2DBAgCcTicdOnTg6NGj1d5/zZo13HLLLTidTjp37szIkSP57rvvOO+885g6dSqVlZWMHz+e9PR0zjjjDHbv3s1DDz3Etddey5VXXklRURFr165lwoQJwfctLz/+/3/8+PE4HA769+/P4cOH66z1iiuuCP69a9asYenSpQCMHj2avLw8CgqsX3Tjxo0jNjaW2NhYRo0axb/+9S/Gjx/PAw88QE5ODkuXLuXGG2/E5Wp77eEG96EbY5zAa8DVQH/gFmNM/9BlRORREUkXkXTgVeCjZqi1qh7SPDEa6KrdeOihh5g+fTqbNm3ij3/8Y50Xi/j9ftatW0dmZmawpZqQkHBK71kV8k1dY1O+/yWXXMLXX39N9+7dmTJlCgsWLCA5OZnvv/+eSy+9lLlz5zJt2jT8fj9JSUnB7ZKZmcm2bduC63G73cHh+k5nDneb1Dz/u2p88uTJvPfee8ybN4+pU6eGta6WFs5B0WHAThHZLSIVwCKgvh1HtwB/bori6pLqcetBUdUmjR49msWLF5OXlwfAkSNHyM/Pp3v37gDVfqZ7PB4KCwuD41deeSWvvvpqcLxqF8BFF13Ehx9+CMBnn33G0aNHARgxYgTLly+npKSE4uJili1bxogRI066PqDOGhty2WWX8frrrwPg8/nIz88/YZkRI0bwwQcf4PP5yMnJ4euvv2bYsGH89NNPdO7cmXvuuYdp06axYcMGcnNz8fv93HjjjTz33HNs2LCBxMRETj/9dBYvXgxYof3999/XW1fNbVtbTQsXLgSsg9MpKSkkJiYC8PHHH1NWVkZeXh6rV6/mvPPOA2DKlCm8/PLLAPTv37/W9ba2cAK9O7AvZDwrMO0ExpjTgNOBrxpfWt1SE9zaQldt0tlnn83MmTMZOXIkgwYN4rHHHmPWrFlMmDCBIUOGBHd1APz85z9n2bJlpKen849//IM5c+aQkZHBwIED6d+/P3PnzgXg2Wef5bPPPuOcc85h8eLFdOnSBY/Hw7nnnsuUKVMYNmwYw4cPZ9q0aQwePPik6wPqrLEhr7zyCqtWrWLAgAEMGTKk2i6jKtdffz0DBw5k0KBBjB49mhdeeIEuXbqwevVqBg0axODBg/nggw945JFH2L9/P5deeinp6encfvvt/Pa3vwVg4cKFvPXWWwwaNIizzz6bjz/+uN66Bg4ciNPpZNCgQfz+978/Yf6sWbNYv349AwcOZMaMGdW+xAYOHMioUaM4//zzefrpp+nWrRsAnTt35qyzzuKuu+4Ke/u0NNPQFZfGmJuAMSIyLTB+BzBcRE44OdUY8wTQQ0QeqmNd9wL3AvTq1WvITz/V2fFGvZ75eDMfZx7g+2evPKXXK3vatm0bZ511VmuX0eTKy8txOp24XC6++eYb7r///mDrXTWtWbNmVTtQHaqkpIQBAwawYcMGOnTo0CL11PaZNsasF5GhtS0fzl79/UDPkPEegWm1uRl4sK4VicgbwBsAQ4cOPeVr91MT3OSXVlLu9eF2OU91NUq1C3v37mXixIn4/X6io6N58803W7ukiPPFF19w99138+ijj7ZYmJ+KcAL9O6CPMeZ0rCC/Gbi15kLGmH5AMvBNk1ZYi7RE6yBIblEF3ZNim/vtlGpVffr04d///ner1vCb3/wmuA+7yoQJE5g5c2YrVdQ8Zs2aVev0yy+/nFPdo9CSGgx0EfEaY6YDn2Kdtvi2iGwxxvwKyBCRFYFFbwYWSQvcNavq4qLsgjINdKVawMyZM20X3nYU1omUIrISWFlj2jM1xmc1XVn1S02IAfRqUaWUCtXu7uUCx3e56KmLSil1XLsM9E7x0RijLXSllArVLgPd5XTQKT6anCINdKWUqtIuAx0gJcFNdoEGumrfTvXS/tosX7681gt7msOFF154Sq+bNWsWL730UhNX0/wyMzNZuXJlwwu2snYb6Kket7bQlQrREoFedS/xluqYo673b2n1BXpbur9627tdWJjSPDHsys5t7TJUW/W3GXBoU9Ous8sAuPr5eheZMWMGPXv25MEHrevrZs2ahcvlYtWqVRw9epTKykqee+65sO+j/bvf/Y733nsPh8PB1VdfzfPPP8+bb77JG2+8QUVFBT/72c949913yczMZMWKFfzv//4vzz33XPBOgrXdQ3zXrl3cdtttFBcXM27cOF5++WWKiooQER5//PET7lu+evVqnn76aZKTk9m+fTs7duwgISGBoqKik6oxLi6uwb93586d3HfffeTk5OB0Olm8eDH79u2r9v4bN27k/vvvJyMjA5fLxezZsxk1ahRbtmzhrrvuoqKiAr/fz9KlS+nWrRsTJ04kKysLn8/H008/zaRJk1i/fj2PPfYYRUVFpKSkMH/+fLp27cqll17K8OHDWbVqFceOHeOtt95i+PDhPPPMM5SWlrJmzRqefPJJtm3bxq5du9i9eze9evXit7/9LVOnTiU3N5fU1FTmzZtHr169mDJlCjExMWRkZFBQUMDs2bO57rrruOSSS5gzZw7p6emAdfvi1157jUGDBoX1uaiTiLTKY8iQIdIYv125TX72/30ifr+/UetR9rF169bjIyufEHn7mqZ9rHyiwRo2bNggl1xySXD8rLPOkr1790p+fr6IiOTk5MiZZ54Z/NzGx8fXua6VK1fKBRdcIMXFxSIikpeXJyIiubm5wWVmzpwpc+bMERGRO++8UxYvXhycN3r0aNmxY4eIiKxbt05GjRolIiLXXnutvP/++yIi8vrrrwdrWLJkiVx++eXi9Xrl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", + "text/plain": [ + "<Figure size 432x288 with 1 Axes>" + ] + }, + "metadata": { + "needs_background": "light" + }, + "output_type": "display_data" + }, + { + "data": { + "image/png": "iVBORw0KGgoAAAANSUhEUgAAAXQAAAD4CAYAAAD8Zh1EAAAAOXRFWHRTb2Z0d2FyZQBNYXRwbG90bGliIHZlcnNpb24zLjUuMiwgaHR0cHM6Ly9tYXRwbG90bGliLm9yZy8qNh9FAAAACXBIWXMAAAsTAAALEwEAmpwYAAA0h0lEQVR4nO3dd3hUZd7/8fc9M0kmIYVAIAkJVREECaELSFdBZQELYEVE1h8q1t21PFiw7LOuuqx1wQaI4oMCgujGLqioIElEWiCESEkgFdL7zP37YyZDCGkkmUwy831d11xz5szJub85OfnMmfs0pbVGCCFE22dwdQFCCCGahwS6EEK4CQl0IYRwExLoQgjhJiTQhRDCTZhc1XBISIju0aOHq5oXQog2KS4uLktr3amm91wW6D169CA2NtZVzQshRJuklDpS23vS5SKEEG5CAl0IIdyEBLoQQrgJl/WhC9HcysvLSUlJoaSkxNWlCNFkZrOZyMhIvLy8GvwzEujCbaSkpBAQEECPHj1QSrm6HCEaTWtNdnY2KSkp9OzZs8E/J10uwm2UlJTQsWNHCXPR5iml6Nix4zl/25RAF25Fwly4i8asy20u0HccPsk/v9iPXPZXCCHO1OYCfVdKLku3HCKnqNzVpQghRKvS5gI9PMgMQFqeHMkg2rYtW7bw888/t0hbV155JTk5Oef8cytXrmThwoXNX5CTHT58mA8++MDVZbS4NhfoYZWBniuBLtq2lgh0rTVWq5WYmBjat2/v1Lbqar+l1RXoFRUVLVxNy2lzhy2GBdoC/YQEuqjDU5/uZd/xvGadZ78ugTz5p/71Trdq1SpefPFFlFJERUUxa9Ysnn32WcrKyujYsSOrV6+muLiYZcuWYTQaef/993n11Vfp27cvCxYs4OjRowC89NJLjB49mszMTG688UaOHz/OyJEj+frrr4mLiyMkJIQlS5awfPlyAObPn8/999/P4cOHmTx5MiNGjCAuLo6YmBjGjRtHbGwsISEhZ9X33nvv8emnn55VY2hoaL2/a3p6OgsWLCA5ORmApUuX0qVLl7Paf+211/j8889RSvHYY48xe/ZsTpw4wezZs8nLy6OiooKlS5cyatQobr/9dmJjY1FKMW/ePB544AEOHTrE3XffTWZmJn5+frz11lv07duXuXPnEhgYSGxsLGlpaTz//PNcd911PPLIIyQkJBAdHc2tt95KcHAwH3/8MQUFBVgsFjZs2MC8efNITk7Gz8+PN998k6ioKBYvXsyhQ4dISkoiKyuLhx56iD//+c/MmTOHa665hhkzZgBw0003MWvWLKZPn97Itck52lygdwrwwaAgLbfY1aUIcZa9e/fy7LPP8vPPPxMSEsLJkydRSrFt2zaUUrz99ts8//zz/Otf/2LBggX4+/vz17/+FYAbb7yRBx54gEsuuYSjR48yefJkEhISeOqpp5g4cSKPPvooX3zxBe+88w4AcXFxrFixgu3bt6O1ZsSIEYwbN47g4GAOHjzIu+++y8UXX1xvfQCXXHJJjTXW595772XcuHFs2LABi8VCQUEBp06dOqP99evXs3PnTn7//XeysrIYNmwYY8eO5YMPPmDy5MksWrQIi8VCUVERO3fuJDU1lT179gA4uonuuOMOli1bRu/evdm+fTt33XUX3333HQAnTpxg69at7N+/n2nTpnHdddfx3HPP8eKLL/LZZ58Btq6j+Ph4du3aRYcOHbjnnnsYNGgQGzdu5LvvvmPOnDns3LkTgF27drFt2zYKCwsZNGgQV111Fbfffjv//ve/mTFjBrm5ufz888+8++67TVtZnKDNBbqX0UCnAB/ZQhd1asiWtDN89913zJw5k5CQEAA6dOjA7t27HVukZWVltZ4o8s0337Bv3z7H67y8PAoKCti6dSsbNmwAYMqUKQQHBwOwdetWrr76atq1awfANddcw48//si0adPo3r37WWFeW31gOymrITXWNL9Vq1YBYDQaCQoK4tSpU2e0v3XrVm644QaMRiOhoaGMGzeOHTt2MGzYMObNm0d5eTkzZswgOjqaXr16kZyczD333MNVV13F5ZdfTkFBAT///DMzZ850tFtaWuoYnjFjBgaDgX79+pGenl5rrZdddpnj9926dSvr168HYOLEiWRnZ5OXZ/tGN336dHx9ffH19WXChAn8+uuvzJgxg7vuuovMzEzWr1/Ptddei8nU+uKzzfWhA4QF+cpOUdFm3HPPPSxcuJDdu3fzxhtv1HqyiNVqZdu2bezcudOxperv79+oNitDvrlrbM72x44dyw8//EBERARz585l1apVBAcH8/vvvzN+/HiWLVvG/PnzsVqttG/f3rFcdu7cSUJCgmM+Pj4+juG6Dmdu6DKpfvx35es5c+bw/vvvs2LF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", + "text/plain": [ + "<Figure size 432x288 with 1 Axes>" + ] + }, + "metadata": { + "needs_background": "light" + }, + "output_type": "display_data" + } + ], + "source": [ + "base_history[history_columns].plot()\n", + "lstm_history[history_columns].plot()\n", + "gru_history[history_columns].plot()\n", + "attn_history[history_columns].plot()" + ] + }, + { + "cell_type": "code", + "execution_count": 28, + "metadata": {}, + "outputs": [], + "source": [ + "base_model = tf.keras.models.load_model(f\"{MODEL_DIR}/baseline\")\n", + "lstm_model = tf.keras.models.load_model(f\"{MODEL_DIR}/lstm\")\n", + "gru_model = tf.keras.models.load_model(f\"{MODEL_DIR}/gru\")" + ] + }, + { + "cell_type": "code", + "execution_count": 29, + "metadata": {}, + "outputs": [ + { + "ename": "RuntimeError", + "evalue": "Unable to restore object of class 'Attention' likely due to name conflict with built-in Keras class '<class 'keras.layers.dense_attention.Attention'>'. To override the built-in Keras definition of the object, decorate your class with `@keras.utils.register_keras_serializable` and include that file in your program, or pass your class in a `keras.utils.CustomObjectScope` that wraps this load call.", + "output_type": "error", + "traceback": [ + "\u001b[0;31m---------------------------------------------------------------------------\u001b[0m", + "\u001b[0;31mRuntimeError\u001b[0m Traceback (most recent call last)", + "\u001b[1;32m/Users/nowadmin/Documents/School Folder/CS 437/Lab/Final Project/tf_model.ipynb Cell 65'\u001b[0m in \u001b[0;36m<cell line: 1>\u001b[0;34m()\u001b[0m\n\u001b[0;32m----> <a href='vscode-notebook-cell:/Users/nowadmin/Documents/School%20Folder/CS%20437/Lab/Final%20Project/tf_model.ipynb#ch0000068?line=0'>1</a>\u001b[0m attn_model \u001b[39m=\u001b[39m tf\u001b[39m.\u001b[39;49mkeras\u001b[39m.\u001b[39;49mmodels\u001b[39m.\u001b[39;49mload_model(\u001b[39mf\u001b[39;49m\u001b[39m\"\u001b[39;49m\u001b[39m{\u001b[39;49;00mMODEL_DIR\u001b[39m}\u001b[39;49;00m\u001b[39m/attention\u001b[39;49m\u001b[39m\"\u001b[39;49m)\n", + "File \u001b[0;32m~/Documents/School Folder/CS 437/Lab/Final Project/venv/lib/python3.10/site-packages/keras/utils/traceback_utils.py:67\u001b[0m, in \u001b[0;36mfilter_traceback.<locals>.error_handler\u001b[0;34m(*args, **kwargs)\u001b[0m\n\u001b[1;32m <a href='file:///Users/nowadmin/Documents/School%20Folder/CS%20437/Lab/Final%20Project/venv/lib/python3.10/site-packages/keras/utils/traceback_utils.py?line=64'>65</a>\u001b[0m \u001b[39mexcept\u001b[39;00m \u001b[39mException\u001b[39;00m \u001b[39mas\u001b[39;00m e: \u001b[39m# pylint: disable=broad-except\u001b[39;00m\n\u001b[1;32m <a href='file:///Users/nowadmin/Documents/School%20Folder/CS%20437/Lab/Final%20Project/venv/lib/python3.10/site-packages/keras/utils/traceback_utils.py?line=65'>66</a>\u001b[0m filtered_tb \u001b[39m=\u001b[39m _process_traceback_frames(e\u001b[39m.\u001b[39m__traceback__)\n\u001b[0;32m---> <a href='file:///Users/nowadmin/Documents/School%20Folder/CS%20437/Lab/Final%20Project/venv/lib/python3.10/site-packages/keras/utils/traceback_utils.py?line=66'>67</a>\u001b[0m \u001b[39mraise\u001b[39;00m e\u001b[39m.\u001b[39mwith_traceback(filtered_tb) \u001b[39mfrom\u001b[39;00m \u001b[39mNone\u001b[39m\n\u001b[1;32m <a href='file:///Users/nowadmin/Documents/School%20Folder/CS%20437/Lab/Final%20Project/venv/lib/python3.10/site-packages/keras/utils/traceback_utils.py?line=67'>68</a>\u001b[0m \u001b[39mfinally\u001b[39;00m:\n\u001b[1;32m <a href='file:///Users/nowadmin/Documents/School%20Folder/CS%20437/Lab/Final%20Project/venv/lib/python3.10/site-packages/keras/utils/traceback_utils.py?line=68'>69</a>\u001b[0m \u001b[39mdel\u001b[39;00m filtered_tb\n", + "File \u001b[0;32m~/Documents/School Folder/CS 437/Lab/Final Project/venv/lib/python3.10/site-packages/keras/saving/saved_model/load.py:532\u001b[0m, in \u001b[0;36mKerasObjectLoader._revive_layer_or_model_from_config\u001b[0;34m(self, metadata, node_id)\u001b[0m\n\u001b[1;32m <a href='file:///Users/nowadmin/Documents/School%20Folder/CS%20437/Lab/Final%20Project/venv/lib/python3.10/site-packages/keras/saving/saved_model/load.py?line=529'>530</a>\u001b[0m builtin_layer \u001b[39m=\u001b[39m layers_module\u001b[39m.\u001b[39mget_builtin_layer(class_name)\n\u001b[1;32m <a href='file:///Users/nowadmin/Documents/School%20Folder/CS%20437/Lab/Final%20Project/venv/lib/python3.10/site-packages/keras/saving/saved_model/load.py?line=530'>531</a>\u001b[0m \u001b[39mif\u001b[39;00m builtin_layer:\n\u001b[0;32m--> <a href='file:///Users/nowadmin/Documents/School%20Folder/CS%20437/Lab/Final%20Project/venv/lib/python3.10/site-packages/keras/saving/saved_model/load.py?line=531'>532</a>\u001b[0m \u001b[39mraise\u001b[39;00m \u001b[39mRuntimeError\u001b[39;00m(\n\u001b[1;32m <a href='file:///Users/nowadmin/Documents/School%20Folder/CS%20437/Lab/Final%20Project/venv/lib/python3.10/site-packages/keras/saving/saved_model/load.py?line=532'>533</a>\u001b[0m \u001b[39mf\u001b[39m\u001b[39m'\u001b[39m\u001b[39mUnable to restore object of class \u001b[39m\u001b[39m\\'\u001b[39;00m\u001b[39m{\u001b[39;00mclass_name\u001b[39m}\u001b[39;00m\u001b[39m\\'\u001b[39;00m\u001b[39m likely due to \u001b[39m\u001b[39m'\u001b[39m\n\u001b[1;32m <a href='file:///Users/nowadmin/Documents/School%20Folder/CS%20437/Lab/Final%20Project/venv/lib/python3.10/site-packages/keras/saving/saved_model/load.py?line=533'>534</a>\u001b[0m \u001b[39mf\u001b[39m\u001b[39m'\u001b[39m\u001b[39mname conflict with built-in Keras class \u001b[39m\u001b[39m\\'\u001b[39;00m\u001b[39m{\u001b[39;00mbuiltin_layer\u001b[39m}\u001b[39;00m\u001b[39m\\'\u001b[39;00m\u001b[39m. To \u001b[39m\u001b[39m'\u001b[39m\n\u001b[1;32m <a href='file:///Users/nowadmin/Documents/School%20Folder/CS%20437/Lab/Final%20Project/venv/lib/python3.10/site-packages/keras/saving/saved_model/load.py?line=534'>535</a>\u001b[0m \u001b[39m'\u001b[39m\u001b[39moverride the built-in Keras definition of the object, decorate \u001b[39m\u001b[39m'\u001b[39m\n\u001b[1;32m <a href='file:///Users/nowadmin/Documents/School%20Folder/CS%20437/Lab/Final%20Project/venv/lib/python3.10/site-packages/keras/saving/saved_model/load.py?line=535'>536</a>\u001b[0m \u001b[39m'\u001b[39m\u001b[39myour class with `@keras.utils.register_keras_serializable` and \u001b[39m\u001b[39m'\u001b[39m\n\u001b[1;32m <a href='file:///Users/nowadmin/Documents/School%20Folder/CS%20437/Lab/Final%20Project/venv/lib/python3.10/site-packages/keras/saving/saved_model/load.py?line=536'>537</a>\u001b[0m \u001b[39m'\u001b[39m\u001b[39minclude that file in your program, or pass your class in a \u001b[39m\u001b[39m'\u001b[39m\n\u001b[1;32m <a href='file:///Users/nowadmin/Documents/School%20Folder/CS%20437/Lab/Final%20Project/venv/lib/python3.10/site-packages/keras/saving/saved_model/load.py?line=537'>538</a>\u001b[0m \u001b[39m'\u001b[39m\u001b[39m`keras.utils.CustomObjectScope` that wraps this load call.\u001b[39m\u001b[39m'\u001b[39m) \u001b[39mfrom\u001b[39;00m \u001b[39me\u001b[39;00m\n\u001b[1;32m <a href='file:///Users/nowadmin/Documents/School%20Folder/CS%20437/Lab/Final%20Project/venv/lib/python3.10/site-packages/keras/saving/saved_model/load.py?line=538'>539</a>\u001b[0m \u001b[39melse\u001b[39;00m:\n\u001b[1;32m <a href='file:///Users/nowadmin/Documents/School%20Folder/CS%20437/Lab/Final%20Project/venv/lib/python3.10/site-packages/keras/saving/saved_model/load.py?line=539'>540</a>\u001b[0m \u001b[39mraise\u001b[39;00m\n", + "\u001b[0;31mRuntimeError\u001b[0m: Unable to restore object of class 'Attention' likely due to name conflict with built-in Keras class '<class 'keras.layers.dense_attention.Attention'>'. To override the built-in Keras definition of the object, decorate your class with `@keras.utils.register_keras_serializable` and include that file in your program, or pass your class in a `keras.utils.CustomObjectScope` that wraps this load call." + ] + } + ], + "source": [ + "attn_model = tf.keras.models.load_model(f\"{MODEL_DIR}/attention\")" + ] + }, { "cell_type": "code", "execution_count": null, "metadata": {}, "outputs": [], - "source": [] + "source": [ + "def model_time():\n", + " pass" + ] }, { "cell_type": "markdown",