00001 from ROOT import TFile
00002 import sets
00003 import sys
00004
00005 histos = ['TH1D', 'TH2D', 'TProfile']
00006 ser = 'SERIAL'
00007 par = 'PARALL'
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020 def rec( o, path=None, lst=None ) :
00021 if not path : path = '/stat' ; lst = []
00022 else : path = path + '/' + o.GetName()
00023 lst.append( (path,o) )
00024 if 'GetListOfKeys' in dir(o) :
00025 keys = o.GetListOfKeys()
00026 for k in keys :
00027 name = k.GetName()
00028 rec( o.Get(name), path, lst )
00029 else :
00030 pass
00031 return lst
00032
00033
00034
00035
00036
00037
00038
00039
00040
00041
00042 def composition( t ) :
00043 typ, d = t
00044 hists = 0 ; objs = 0
00045 for k in d.keys() :
00046 if d[k].__class__.__name__ in histos : hists += 1
00047 else : objs += 1
00048 return objs, hists
00049
00050
00051
00052
00053
00054
00055
00056
00057
00058
00059
00060
00061
00062
00063
00064 def comparePaths( t1, t2 ) :
00065 if t1[0] == ser : ds = t1[1] ; dp = t2[1]
00066 elif t2[0] == ser : ds = t2[1] ; dp = t1[1]
00067 else : print 'Neither tuple is Serial Root file reference?' ; return
00068
00069 dsks = ds.keys() ; dpks = dp.keys()
00070 dsks.sort() ; dpks.sort()
00071
00072 sset = sets.Set( dsks )
00073 pset = sets.Set( dpks )
00074 os, hs = composition( (ser, ds) )
00075 op, hp = composition( (par, dp) )
00076 print '\n' + '='*80
00077 print 'Comparison of Paths : Serial vs Parallel ROOT files'
00078 print '-'*80
00079 print 'Number of paths in Serial file : %i (objects, histos) = ( %i, %i )'%( len(dsks), os, hs )
00080 print 'Number of paths in Parall file : %i (objects, histos) = ( %i, %i )'%( len(dpks), op, hp )
00081 matching = sset.intersection(pset)
00082 matchingHistos = 0
00083 for n in matching :
00084 if ds[n].__class__.__name__ in histos : matchingHistos += 1
00085 print '\nMatching paths : %i'%( len(matching) )
00086 uSer = sset - pset
00087
00088 uniqueSerialHistos = 0
00089 for n in uSer :
00090 if ds[n].__class__.__name__ in histos : uniqueSerialHistos += 1
00091 print 'Paths unique to Serial file : %i ( %i Histos )'%( len(uSer), uniqueSerialHistos )
00092 if uSer :
00093 for n in uSer : print '\t%s : \t%s'%( ds[n], n )
00094 uPar = pset - sset
00095 uniqueParallHistos = 0
00096 for n in uPar :
00097 if dp[n].__class__.__name__ in histos : uniqueParallHistos += 1
00098 print 'Paths unique to Parall file : %i ( %i Histos )'%( len(uPar), uniqueParallHistos )
00099 if uPar :
00100 for n in uPar : print '\t%s : \t%s'%( dp[n], n )
00101 print 'Matching Histos to test : %i'%( matchingHistos )
00102 print '='*80 + '\n'
00103 return ( ((os,hs),(op,hp)), (uSer, uniqueSerialHistos), (uPar, uniqueParallHistos), matchingHistos )
00104
00105
00106
00107
00108
00109
00110
00111
00112
00113
00114
00115
00116
00117
00118
00119
00120
00121 def compareHistos(t1, t2, state) :
00122
00123 ( ((serialObjects,serialHistos),(parallObjects, parallHistos)), (uniqueSerPaths,uniqueSerHistos), (uniqueParPaths,uniqueParHistos), mh ) = state
00124
00125
00126 if t1[0] == ser : ds = t1[1] ; dp = t2[1]
00127 elif t2[0] == ser : ds = t2[1] ; dp = t1[1]
00128 else : print 'Neither tuple is Serial Root file reference?' ; return
00129
00130
00131 hcp = 0 ; pHistos = []
00132 hcs = 0 ; sHistos = []
00133
00134 omit = ['/stat/Brunel/MemoryTool/Virtual mem, all entries',
00135 '/stat/Brunel/MemoryTool/Virtual mem, downscaled']
00136 omit = []
00137
00138
00139 for k in ds.keys() :
00140 if k not in omit :
00141 if ds[k].__class__.__name__ in histos : hcs += 1 ; sHistos.append( k )
00142
00143 for k in dp.keys() :
00144 if k not in omit :
00145 if dp[k].__class__.__name__ in histos : hcp += 1 ; pHistos.append( k )
00146
00147
00148 cEntries = 0 ; xEntries = 0 ; diffEntries = []
00149 cIntegrals = 0 ; xIntegrals = 0 ; diffIntegrals = []
00150 passedKol = 0 ; failedKol = 0 ; diffKols = [] ; zeroIntegrals = 0
00151 kTested = 0
00152 notfound = 0 ; integralMatch = 0 ; otherTest = 0 ; zeroIntegralMatch = 0
00153 for h in sHistos :
00154 if h in pHistos :
00155
00156 cEntries += 1
00157 sh = ds[h] ; ph = dp[h]
00158
00159 if sh.GetEntries() != ph.GetEntries() : diffEntries.append(h) ; xEntries += 1 ; continue
00160
00161 sBinError = 0.0 ; pBinError = 0.0
00162 for i in xrange(sh.GetNbinsX()) : sBinError += sh.GetBinError(i)
00163 for i in xrange(ph.GetNbinsX()) : pBinError += ph.GetBinError(i)
00164 sint = sh.Integral() ; pint = ph.Integral()
00165 if (bool(sint) and bool(pint)) and ( sBinError>0 and pBinError>0 ) :
00166 kTested += 1
00167 kTest = sh.KolmogorovTest(ph)
00168 if int(kTest) : passedKol += 1
00169 else : failedKol += 1 ; diffKols.append(h)
00170 else :
00171
00172 otherTest += 1
00173 if all((sint, pint)) and (sint==pint) :
00174 integralMatch += 1
00175 elif (sint==pint) :
00176 zeroIntegralMatch += 1
00177 else :
00178 diffIntegrals.append( h )
00179 xIntegrals += 1
00180 else :
00181 notfound += 1 ; print 'not found? ', h
00182
00183
00184 print '\n\n'+'-'*80
00185 print 'Summary of histos with different Entries'
00186 print '-'*80
00187 if diffEntries :
00188 diffEntries.sort()
00189 for e in diffEntries : print '\t\t\t%s:\t%i != %i'%( e, int(ds[e].GetEntries()), int(dp[e].GetEntries()) )
00190 print '-'*80
00191
00192
00193 print '\n\n'+'-'*60
00194 print 'Summary of histos which failed Kolmogorov Test'
00195 print '-'*60
00196 if diffKols :
00197 diffKols.sort()
00198 for e in diffKols :
00199 result = ds[e].KolmogorovTest(dp[e])
00200 print '%s\t\t%s :\tK-Test Result :\t %5.16f'%( type(ds[e]), e, result )
00201 print '-'*60
00202
00203
00204 print '\n\n'+'-'*60
00205 print 'Summary of histos which failed Integral Check'
00206 print '-'*60
00207 if diffIntegrals :
00208 diffIntegrals.sort()
00209 for e in diffIntegrals :
00210 diff = dp[e].Integral()-ds[e].Integral()
00211 pc = (diff*100)/ds[e].Integral()
00212 print '%s\t\t%s:\t Diff = %5.6f\tPercent Diff to Serial : %5.6f '%( type(ds[e]), e, diff, pc )
00213 print '-'*60 + '\n'
00214 print '='*80 + '\n'
00215
00216 print '\n' + '='*80
00217 print 'Comparison : Serial/Parallel ROOT Histo files'
00218 print '\n\t\tSerial\tParall'
00219 print '\tObjects : %i\t%i\t\t( p-s = %i )'%( serialObjects, parallObjects, parallObjects-serialObjects )
00220 print '\tHistos : %i\t%i\t\t( p-s = %i )'%( serialHistos, parallHistos, parallHistos-serialHistos )
00221 print '\t __________'
00222 print '\tTotal : %i\t%i\n'%( serialHistos+serialObjects, parallHistos+parallObjects )
00223 print 'Objects/Histos unique to Serial File : %i / %i'%( len(uniqueSerPaths)-uniqueSerHistos, uniqueSerHistos )
00224 print 'Objects/Histos unique to Parall File : %i / %i'%( len(uniqueParPaths)-uniqueParHistos, uniqueParHistos )
00225 print '\nMatching Histograms valid for Comparison : %i'%( mh )
00226 print '\nOmissions : '
00227 for entry in omit : print '\t%s'%( entry )
00228 print '\nHistograms for Comparison (after Omissions) : %i'%( mh-len(omit) )
00229 print '\n\tHISTOGRAM TESTS : '
00230 print '\t\tKOLMOGOROV TEST : %i'%( kTested )
00231 print '\t\tINTEGRAL TEST : %i'%( otherTest )
00232 print '\t\tENTRIES TEST : %i'%( xEntries )
00233 print '\t\t ____'
00234 print '\t\tTested : %i'%( cEntries )
00235
00236 print '\n\tDISCREPANCIES : '
00237 print '\t\tK-Test : %i'%( failedKol )
00238 print '\t\tIntegrals : %i'%( xIntegrals )
00239 print '\t\tEntries : %i'%( xEntries )
00240 print '\n'+'='*80
00241
00242
00243
00244 if __name__ == '__main__' :
00245 sys.argv.pop(0)
00246 if len(sys.argv) == 2 :
00247 pFile = sys.argv[0]
00248 sFile = sys.argv[1]
00249 else :
00250 print '*'*80
00251 print 'Wrong count of arguments? > python compareRootHistos.py someParallelFile.root someSerialFile.root'
00252 print '*'*80
00253 sys.exit(0)
00254 tfs = TFile( sFile, 'REC' ) ; print 'opening Serial File : %s'%( sFile )
00255 tfp = TFile( pFile, 'REC' ) ; print 'opening Parall File : %s'%( pFile )
00256
00257
00258 lser = rec(tfs) ; lpar = rec(tfp)
00259
00260 dserial = dict( [(n, o) for n, o in lser] )
00261 dparall = dict( [(n, o) for n, o in lpar] )
00262
00263 ts = ( ser, dserial ) ; tp = ( par, dparall )
00264
00265
00266
00267
00268
00269 state = comparePaths( ts, tp )
00270
00271
00272 compareHistos( ts, tp, state )
00273
00274
00275
00276
00277