4
4
import numpy as np
5
5
from numpy .testing import assert_almost_equal
6
6
7
- if np .__version__ > "1.19 " :
8
- raise RuntimeError (f"This test requires NumPy version 1.19 or lower " )
7
+ if np .__version__ >= "1.20" and np . __version__ < "1.24 " :
8
+ raise RuntimeError (f"This test requires NumPy version <= 1.19 or >=1.24 " )
9
9
10
10
import graph_nets as gn
11
11
from graph_nets import utils_tf
12
12
import sonnet as snt
13
+ import os
13
14
14
15
15
16
@@ -21,9 +22,22 @@ def get_graph_data_dict(num_nodes, num_edges, GLOBAL_FEATURE_SIZE=2, NODE_FEATUR
21
22
"nodes" : np .random .rand (num_nodes , NODE_FEATURE_SIZE ).astype (np .float32 ),
22
23
"edges" : np .random .rand (num_edges , EDGE_FEATURE_SIZE ).astype (np .float32 ),
23
24
"senders" : np .random .randint (num_nodes , size = num_edges , dtype = np .int32 ),
24
- "receivers" : np .random .randint (num_nodes , size = num_edges , dtype = np .int32 ),
25
+ "receivers" : np .random .randint (num_nodes , size = num_edges , dtype = np .int32 )
25
26
}
26
27
28
+ def resize_graph_data (input_data , GLOBAL_FEATURE_SIZE = 2 , NODE_FEATURE_SIZE = 2 , EDGE_FEATURE_SIZE = 2 ) :
29
+ n = input_data ["nodes" ]
30
+ e = input_data ["edges" ]
31
+ s = input_data ["senders" ]
32
+ r = input_data ["receivers" ]
33
+ return {
34
+ "globals" : np .zeros ((GLOBAL_FEATURE_SIZE )),
35
+ "nodes" : np .zeros ((n .shape [0 ],NODE_FEATURE_SIZE )),
36
+ "edges" : np .zeros ((e .shape [0 ],EDGE_FEATURE_SIZE )),
37
+ "senders" : s , "receivers" : r
38
+ }
39
+
40
+ LATENT_SIZE = 2
27
41
def make_mlp_model ():
28
42
"""Instantiates a new MLP, followed by LayerNorm.
29
43
@@ -34,7 +48,7 @@ def make_mlp_model():
34
48
A Sonnet module which contains the MLP and LayerNorm.
35
49
"""
36
50
return snt .Sequential ([
37
- snt .nets .MLP ([2 , 2 ] , activate_final = True ),
51
+ snt .nets .MLP ([LATENT_SIZE ] * 2 , activate_final = True ),
38
52
snt .LayerNorm (axis = - 1 , create_offset = True , create_scale = True )
39
53
])
40
54
@@ -48,9 +62,9 @@ class MLPGraphIndependent(snt.Module):
48
62
def __init__ (self , name = "MLPGraphIndependent" ):
49
63
super (MLPGraphIndependent , self ).__init__ (name = name )
50
64
self ._network = gn .modules .GraphIndependent (
51
- edge_model_fn = lambda : snt .nets .MLP ([2 , 2 ] , activate_final = True ),
52
- node_model_fn = lambda : snt .nets .MLP ([2 , 2 ] , activate_final = True ),
53
- global_model_fn = lambda : snt .nets .MLP ([2 , 2 ] , activate_final = True ))
65
+ edge_model_fn = lambda : snt .nets .MLP ([LATENT_SIZE ] * 2 , activate_final = True ),
66
+ node_model_fn = lambda : snt .nets .MLP ([LATENT_SIZE ] * 2 , activate_final = True ),
67
+ global_model_fn = lambda : snt .nets .MLP ([LATENT_SIZE ] * 2 , activate_final = True ))
54
68
55
69
def __call__ (self , inputs ):
56
70
return self ._network (inputs )
@@ -69,12 +83,19 @@ def __init__(self, name="MLPGraphNetwork"):
69
83
def __call__ (self , inputs ):
70
84
return self ._network (inputs )
71
85
86
+ def PrintGData (data , printShape = True ):
87
+ n = data .nodes .numpy ()
88
+ e = data .edges .numpy ()
89
+ g = data .globals .numpy ()
90
+ if (printShape ) :
91
+ print ("GNet data ... shapes" ,n .shape ,e .shape ,g .shape )
92
+ print (" node data" , n .reshape (n .size ,))
93
+ print (" edge data" , e .reshape (e .size ,))
94
+ print (" global data" ,g .reshape (g .size ,))
95
+
72
96
class EncodeProcessDecode (snt .Module ):
73
97
74
98
def __init__ (self ,
75
- edge_output_size = None ,
76
- node_output_size = None ,
77
- global_output_size = None ,
78
99
name = "EncodeProcessDecode" ):
79
100
super (EncodeProcessDecode , self ).__init__ (name = name )
80
101
self ._encoder = MLPGraphIndependent ()
@@ -103,12 +124,15 @@ def test_parse_gnn(self):
103
124
Test that parsed GNN model from a graphnets model generates correct
104
125
inference code
105
126
'''
127
+
128
+ print ('\n Run Graph parsing test' )
129
+
106
130
GraphModule = gn .modules .GraphNetwork (
107
131
edge_model_fn = lambda : snt .nets .MLP ([2 ,2 ], activate_final = True ),
108
132
node_model_fn = lambda : snt .nets .MLP ([2 ,2 ], activate_final = True ),
109
133
global_model_fn = lambda : snt .nets .MLP ([2 ,2 ], activate_final = True ))
110
134
111
- GraphData = get_graph_data_dict (2 ,1 )
135
+ GraphData = get_graph_data_dict (2 ,1 , 2 , 2 , 2 )
112
136
input_graphs = utils_tf .data_dicts_to_graphs_tuple ([GraphData ])
113
137
output = GraphModule (input_graphs )
114
138
@@ -135,18 +159,26 @@ def test_parse_gnn(self):
135
159
assert_almost_equal (output_edge_data , np .asarray (input_data .edge_data ))
136
160
assert_almost_equal (output_global_data , np .asarray (input_data .global_data ))
137
161
162
+ fname = "gnn_network"
163
+ os .remove (fname + '.dat' )
164
+ os .remove (fname + '.hxx' )
165
+
138
166
139
167
def test_parse_graph_independent (self ):
140
168
'''
141
169
Test that parsed GraphIndependent model from a graphnets model generates correct
142
170
inference code
143
171
'''
172
+
173
+ print ('\n Run Graph Independent parsing test' )
174
+
175
+
144
176
GraphModule = gn .modules .GraphIndependent (
145
177
edge_model_fn = lambda : snt .nets .MLP ([2 ,2 ], activate_final = True ),
146
178
node_model_fn = lambda : snt .nets .MLP ([2 ,2 ], activate_final = True ),
147
179
global_model_fn = lambda : snt .nets .MLP ([2 ,2 ], activate_final = True ))
148
180
149
- GraphData = get_graph_data_dict (2 ,1 )
181
+ GraphData = get_graph_data_dict (2 ,1 , 2 , 2 , 2 )
150
182
input_graphs = utils_tf .data_dicts_to_graphs_tuple ([GraphData ])
151
183
output = GraphModule (input_graphs )
152
184
@@ -173,39 +205,58 @@ def test_parse_graph_independent(self):
173
205
assert_almost_equal (output_edge_data , np .asarray (input_data .edge_data ))
174
206
assert_almost_equal (output_global_data , np .asarray (input_data .global_data ))
175
207
208
+ fname = "graph_independent_network"
209
+ os .remove (fname + '.dat' )
210
+ os .remove (fname + '.hxx' )
211
+
176
212
def test_lhcb_toy_inference (self ):
177
213
'''
178
214
Test that parsed stack of SOFIE GNN and GraphIndependent modules generate the correct
179
215
inference code
180
216
'''
217
+
218
+ print ('Run LHCb test' )
219
+
181
220
# Instantiating EncodeProcessDecode Model
182
- ep_model = EncodeProcessDecode (2 ,2 ,2 )
221
+
222
+ #number of features for node. edge, globals
223
+ nsize = 3
224
+ esize = 3
225
+ gsize = 2
226
+ lsize = LATENT_SIZE #hard-coded latent size in definition of GNET model (for node edge and globals)
227
+
228
+ ep_model = EncodeProcessDecode ()
183
229
184
230
# Initializing randomized input data
185
- GraphData = get_graph_data_dict (2 ,1 )
186
- input_graphs = utils_tf .data_dicts_to_graphs_tuple ([GraphData ])
231
+ InputGraphData = get_graph_data_dict (2 ,1 , gsize , nsize , esize )
232
+ input_graphs = utils_tf .data_dicts_to_graphs_tuple ([InputGraphData ])
233
+
234
+ # Make data for core networks (number of features for node/edge global is 2 * lsize)
235
+ CoreGraphData = resize_graph_data (InputGraphData , 2 * lsize , 2 * lsize , 2 * lsize )
236
+
237
+
238
+ OutputGraphData = resize_graph_data (InputGraphData , lsize , lsize , lsize )
187
239
188
- # Initializing randomized input data for core
189
- CoreGraphData = get_graph_data_dict (2 , 1 , 4 , 4 , 4 )
190
- input_graphs_2 = utils_tf .data_dicts_to_graphs_tuple ([CoreGraphData ])
191
240
192
241
# Collecting output from GraphNets model stack
193
242
output_gn = ep_model (input_graphs , 2 )
194
243
244
+ print ("senders and receivers " ,InputGraphData ['senders' ],InputGraphData ['receivers' ])
245
+
195
246
# Declaring sofie models
196
- encoder = ROOT .TMVA .Experimental .SOFIE .RModel_GraphIndependent .ParseFromMemory (ep_model ._encoder ._network , GraphData , filename = "encoder" )
247
+ encoder = ROOT .TMVA .Experimental .SOFIE .RModel_GraphIndependent .ParseFromMemory (ep_model ._encoder ._network , InputGraphData , filename = "encoder" )
197
248
encoder .Generate ()
198
249
encoder .OutputGenerated ()
199
250
200
251
core = ROOT .TMVA .Experimental .SOFIE .RModel_GNN .ParseFromMemory (ep_model ._core ._network , CoreGraphData , filename = "core" )
201
252
core .Generate ()
202
253
core .OutputGenerated ()
203
254
204
- decoder = ROOT .TMVA .Experimental .SOFIE .RModel_GraphIndependent .ParseFromMemory (ep_model ._decoder ._network , GraphData , filename = "decoder" )
255
+ decoder = ROOT .TMVA .Experimental .SOFIE .RModel_GraphIndependent .ParseFromMemory (ep_model ._decoder ._network , OutputGraphData , filename = "decoder" )
205
256
decoder .Generate ()
206
257
decoder .OutputGenerated ()
207
258
208
- output_transform = ROOT .TMVA .Experimental .SOFIE .RModel_GraphIndependent .ParseFromMemory (ep_model ._output_transform ._network , GraphData , filename = "output_transform" )
259
+ output_transform = ROOT .TMVA .Experimental .SOFIE .RModel_GraphIndependent .ParseFromMemory (ep_model ._output_transform ._network , OutputGraphData , filename = "output_transform" )
209
260
output_transform .Generate ()
210
261
output_transform .OutputGenerated ()
211
262
@@ -222,14 +273,18 @@ def test_lhcb_toy_inference(self):
222
273
223
274
# Preparing the input data for running inference on sofie
224
275
input_data = ROOT .TMVA .Experimental .SOFIE .GNN_Data ()
225
- input_data .node_data = ROOT .TMVA .Experimental .AsRTensor (GraphData ['nodes' ])
226
- input_data .edge_data = ROOT .TMVA .Experimental .AsRTensor (GraphData ['edges' ])
227
- input_data .global_data = ROOT .TMVA .Experimental .AsRTensor (GraphData ['globals' ])
276
+ input_data .node_data = ROOT .TMVA .Experimental .AsRTensor (InputGraphData ['nodes' ])
277
+ input_data .edge_data = ROOT .TMVA .Experimental .AsRTensor (InputGraphData ['edges' ])
278
+ input_data .global_data = ROOT .TMVA .Experimental .AsRTensor (InputGraphData ['globals' ])
279
+
280
+ output_gn = ep_model (input_graphs , 2 )
228
281
229
282
# running inference on sofie
230
- encoder_session .infer (input_data )
231
- latent0 = CopyData (input_data )
232
- latent = input_data
283
+ data = CopyData (input_data )
284
+
285
+ encoder_session .infer (data )
286
+ latent0 = CopyData (data )
287
+ latent = data
233
288
output_ops = []
234
289
for _ in range (2 ):
235
290
core_input = ROOT .TMVA .Experimental .SOFIE .Concatenate (latent0 , latent , axis = 1 )
@@ -246,10 +301,16 @@ def test_lhcb_toy_inference(self):
246
301
output_global_data = output_gn [i ].globals .numpy ().flatten ()
247
302
248
303
assert_almost_equal (output_node_data , np .asarray (output_ops [i ].node_data ))
304
+
249
305
assert_almost_equal (output_edge_data , np .asarray (output_ops [i ].edge_data ))
250
- assert_almost_equal (output_global_data , np .asarray (output_ops [i ].global_data ))
251
306
307
+ assert_almost_equal (output_global_data , np .asarray (output_ops [i ].global_data ))
252
308
309
+ #remove header files after being used
310
+ filesToRemove = ['core' ,'encoder' ,'decoder' ,'output_transform' ]
311
+ for fname in filesToRemove :
312
+ os .remove (fname + '.hxx' )
313
+ os .remove (fname + '.dat' )
253
314
254
315
255
316
if __name__ == '__main__' :
0 commit comments