Skip to content

Commit

Permalink
moar metrix
Browse files Browse the repository at this point in the history
git-svn-id: https://slps.svn.sourceforge.net/svnroot/slps@932 ab42f6e0-554d-0410-b580-99e487e6eeb2
  • Loading branch information
grammarware committed Feb 2, 2011
1 parent 0cae537 commit 56b5722
Show file tree
Hide file tree
Showing 48 changed files with 371 additions and 52 deletions.
7 changes: 7 additions & 0 deletions topics/investigation/complexity/Makefile
@@ -0,0 +1,7 @@
test:
cp ../../convergence/fl/snapshot/*.bgf tests/
cp ../../convergence/java/snapshot/*.bgf tests/
ls -1 tests/*.bgf | xargs -n1 ./testperform

clean:
rm -f tests/*.bgf tests/*.out
40 changes: 40 additions & 0 deletions topics/investigation/complexity/avs.py
@@ -0,0 +1,40 @@
#!/usr/local/bin/python
# -*- coding: utf-8 -*-
import sys
sys.path.append('../../../shared/python')
import BGF
sys.path.append('../size')
import var

def rhssize(node):
if node.__class__.__name__ == 'Grammar':
return sum(map(rhssize,node.prods))/(0.0+len(var.var(node)))
elif node.__class__.__name__ in ('Production','Selectable'):
return rhssize(node.expr)
elif node.__class__.__name__ == 'Expression':
return rhssize(node.wrapped)
elif node.__class__.__name__ == 'Marked':
return rhssize(node.data)
elif node.__class__.__name__ in ('Plus','Star','Optional'):
return rhssize(node.data)
elif node.__class__.__name__ in ('Terminal','Nonterminal','Value'):
return 1
elif node.__class__.__name__ in ('Epsilon','Any','Empty'):
return 0
elif node.__class__.__name__ in ('Choice','Sequence'):
return sum(map(rhssize,node.data))
else:
print 'How to deal with',node.__class__.__name__,'?'
return 0

if __name__ == "__main__":
if len(sys.argv) != 2:
print 'This tool calculates an AVS metric for any given BGF grammar.'
print 'Usage:'
print ' '+sys.argv[0]+' <bgf-input>'
sys.exit(1)
bgf = BGF.Grammar()
bgf.parse(sys.argv[1])
#print 'AVS =',rhssize(bgf)
print '%.2f' % rhssize(bgf)
sys.exit(0)
104 changes: 104 additions & 0 deletions topics/investigation/complexity/hal.py
@@ -0,0 +1,104 @@
#!/usr/local/bin/python
# -*- coding: utf-8 -*-
import sys
import math
sys.path.append('../../../shared/python')
import BGF
sys.path.append('../size')
import var
import term

def values(g):
# returns the number of values used in the grammar
vals = []
for v in g.getXml().findall('.//value'):
if v.text not in vals:
vals.append(v.text)
return vals

def labels(g):
# returns the number of production labels used in the grammar
labs = []
for v in g.prods:
if v.label and v.label not in labs:
labs.append(v.label)
return labs

def selectors(g):
# returns the number of expression selectors used in the grammar
sels = []
for v in g.getXml().findall('.//selectable'):
if v.findtext('selector') not in sels:
sels.append(v.findtext('selector'))
return sels

def opr(node):
# number of occurrences of operators
if node.__class__.__name__ == 'Grammar':
return sum(map(opr,node.prods))
elif node.__class__.__name__ == 'Production':
return opr(node.expr)
elif node.__class__.__name__ == 'Selectable':
return 1+opr(node.expr)
elif node.__class__.__name__ == 'Expression':
return opr(node.wrapped)
elif node.__class__.__name__ == 'Marked':
return 1+opr(node.data)
elif node.__class__.__name__ in ('Plus','Star','Optional'):
return 1+opr(node.data)
elif node.__class__.__name__ in ('Terminal','Nonterminal','Value'):
return 0
elif node.__class__.__name__ in ('Epsilon','Any','Empty'):
return 1
elif node.__class__.__name__ in ('Choice','Sequence'):
return sum(map(opr,node.data))
else:
print 'How to deal with',node.__class__.__name__,'?'
return 0

def opd(node):
# number of occurrences of operands
if node.__class__.__name__ == 'Grammar':
return sum(map(opd,node.prods))
elif node.__class__.__name__ == 'Production':
if node.label:
return 2+opd(node.expr)
else:
return 1+opd(node.expr)
elif node.__class__.__name__ == 'Selectable':
return 1+opd(node.expr)
elif node.__class__.__name__ == 'Expression':
return opd(node.wrapped)
elif node.__class__.__name__ == 'Marked':
return opd(node.data)
elif node.__class__.__name__ in ('Plus','Star','Optional'):
return opd(node.data)
elif node.__class__.__name__ in ('Terminal','Nonterminal','Value'):
return 1
elif node.__class__.__name__ in ('Epsilon','Any','Empty'):
return 0
elif node.__class__.__name__ in ('Choice','Sequence'):
return sum(map(opd,node.data))
else:
print 'How to deal with',node.__class__.__name__,'?'
return 0

if __name__ == "__main__":
if len(sys.argv) != 2:
print 'This tool calculates a HAL metric for any given BGF grammar.'
print 'Usage:'
print ' '+sys.argv[0]+' <bgf-input>'
sys.exit(1)
bgf = BGF.Grammar()
bgf.parse(sys.argv[1])

# Selectable, Marked, Plus, Star, Optional, Epsilon, Empty, Any, Choice, Sequence
mu1 = 10
mu2 = len(var.var(bgf)) + len(term.term(bgf)) + len(values(bgf)) + len(labels(bgf)) + len(selectors(bgf))
eta1 = opr(bgf)
eta2 = opd(bgf)
hal = (mu1*eta2*(eta1+eta2)*math.log(mu1+mu2,2)) / (2*mu2)
#print 'µ₁ =',mu1,', µ₂ =',mu2,', η₁ =',eta1,', η₂ =',eta2
#print 'HAL =',hal
print '%.2f' % hal
sys.exit(0)
38 changes: 38 additions & 0 deletions topics/investigation/complexity/mcc.py
@@ -0,0 +1,38 @@
#!/usr/local/bin/python
# -*- coding: utf-8 -*-
import sys
sys.path.append('../../../shared/python')
import BGF

def mccabe(node):
if node.__class__.__name__ == 'Grammar':
return sum(map(mccabe,node.prods))
elif node.__class__.__name__ in ('Production','Selectable'):
return mccabe(node.expr)
elif node.__class__.__name__ == 'Expression':
return mccabe(node.wrapped)
elif node.__class__.__name__ == 'Marked':
return mccabe(node.data)
elif node.__class__.__name__ in ('Plus','Star','Optional'):
return 1+mccabe(node.data)
elif node.__class__.__name__ in ('Terminal','Nonterminal','Epsilon','Any','Empty','Value'):
return 0
elif node.__class__.__name__ == 'Choice':
return len(node.data)-1 + max(map(mccabe,node.data))
elif node.__class__.__name__ == 'Sequence':
return sum(map(mccabe,node.data))
else:
print 'How to deal with',node.__class__.__name__,'?'
return 0

if __name__ == "__main__":
if len(sys.argv) != 2:
print 'This tool calculates an MCC metric for any given BGF grammar.'
print 'Usage:'
print ' '+sys.argv[0]+' <bgf-input>'
sys.exit(1)
bgf = BGF.Grammar()
bgf.parse(sys.argv[1])
#print 'MCC =',mccabe(bgf)
print mccabe(bgf)
sys.exit(0)
7 changes: 7 additions & 0 deletions topics/investigation/complexity/testperform
@@ -0,0 +1,7 @@
#!/bin/sh

echo [Test Case] `basename $1`
./mcc.py $1 > $1.out || exit -1
./avs.py $1 >> $1.out || exit -1
./hal.py $1 >> $1.out || exit -1
diff $1.out $1.baseline || exit -1
3 changes: 3 additions & 0 deletions topics/investigation/complexity/tests/antlr.bgf.baseline
@@ -0,0 +1,3 @@
11
2.55
1810.64
3 changes: 3 additions & 0 deletions topics/investigation/complexity/tests/dcg.bgf.baseline
@@ -0,0 +1,3 @@
5
3.12
2211.75
3 changes: 3 additions & 0 deletions topics/investigation/complexity/tests/ecore.bgf.baseline
@@ -0,0 +1,3 @@
9
2.17
4570.24
3 changes: 3 additions & 0 deletions topics/investigation/complexity/tests/ecore2.bgf.baseline
@@ -0,0 +1,3 @@
9
2.11
3139.12
3 changes: 3 additions & 0 deletions topics/investigation/complexity/tests/fl_ldf.bgf.baseline
@@ -0,0 +1,3 @@
3
1.40
360.00
3 changes: 3 additions & 0 deletions topics/investigation/complexity/tests/impl1.bgf.baseline
@@ -0,0 +1,3 @@
45
4.07
132357.97
3 changes: 3 additions & 0 deletions topics/investigation/complexity/tests/impl2.bgf.baseline
@@ -0,0 +1,3 @@
73
4.47
80315.75
3 changes: 3 additions & 0 deletions topics/investigation/complexity/tests/impl3.bgf.baseline
@@ -0,0 +1,3 @@
130
4.48
132603.43
3 changes: 3 additions & 0 deletions topics/investigation/complexity/tests/jaxb.bgf.baseline
@@ -0,0 +1,3 @@
9
1.45
3056.21
3 changes: 3 additions & 0 deletions topics/investigation/complexity/tests/ldf.bgf.baseline
@@ -0,0 +1,3 @@
3
1.40
360.00
3 changes: 3 additions & 0 deletions topics/investigation/complexity/tests/om.bgf.baseline
@@ -0,0 +1,3 @@
9
1.60
2992.59
3 changes: 3 additions & 0 deletions topics/investigation/complexity/tests/read1.bgf.baseline
@@ -0,0 +1,3 @@
45
3.96
148307.20
3 changes: 3 additions & 0 deletions topics/investigation/complexity/tests/read2.bgf.baseline
@@ -0,0 +1,3 @@
58
4.22
176882.01
3 changes: 3 additions & 0 deletions topics/investigation/complexity/tests/read3.bgf.baseline
@@ -0,0 +1,3 @@
92
4.28
258577.76
3 changes: 3 additions & 0 deletions topics/investigation/complexity/tests/sdf.bgf.baseline
@@ -0,0 +1,3 @@
4
3.57
2238.48
3 changes: 3 additions & 0 deletions topics/investigation/complexity/tests/txl.bgf.baseline
@@ -0,0 +1,3 @@
10
3.57
1363.13
3 changes: 3 additions & 0 deletions topics/investigation/complexity/tests/xml.bgf.baseline
@@ -0,0 +1,3 @@
9
2.00
3270.97
3 changes: 3 additions & 0 deletions topics/investigation/complexity/tests/xsd.bgf.baseline
@@ -0,0 +1,3 @@
9
2.00
3270.97
24 changes: 24 additions & 0 deletions topics/investigation/size/bottom.py
@@ -0,0 +1,24 @@
#!/usr/local/bin/python
# -*- coding: utf-8 -*-
import sys
sys.path.append('../../../shared/python')
import BGF
import defined
import used

if __name__ == "__main__":
if len(sys.argv) != 2:
print 'This tool calculates a BOTTOM metric for any given BGF grammar.'
print 'Usage:'
print ' '+sys.argv[0]+' <bgf-input>'
sys.exit(1)
bgf = BGF.Grammar()
bgf.parse(sys.argv[1])
bottoms = []
definednts = defined.defined(bgf)
for nt in used.used(bgf):
if nt not in definednts:
bottoms.append(nt)
#print 'BOTTOM =',len(bottoms)
print len(bottoms)
sys.exit(0)
24 changes: 24 additions & 0 deletions topics/investigation/size/defined.py
@@ -0,0 +1,24 @@
#!/usr/local/bin/python
# -*- coding: utf-8 -*-
import sys
sys.path.append('../../../shared/python')
import BGF

def defined(g):
nts = []
for p in g.prods:
if p.nt not in nts:
nts.append(p.nt)
return nts

if __name__ == "__main__":
if len(sys.argv) != 2:
print 'This tool calculates a DEFINED metric for any given BGF grammar.'
print 'Usage:'
print ' '+sys.argv[0]+' <bgf-input>'
sys.exit(1)
bgf = BGF.Grammar()
bgf.parse(sys.argv[1])
#print 'DEFINED =',len(defined(bgf))
print len(defined(bgf))
sys.exit(0)
15 changes: 9 additions & 6 deletions topics/investigation/size/term.py
Expand Up @@ -4,6 +4,14 @@
sys.path.append('../../../shared/python')
import BGF

def term(g):
ts = []
for p in g.prods:
for n in p.expr.wrapped.getXml().findall('.//terminal'):
if n.text not in ts:
ts.append(n.text)
return ts

if __name__ == "__main__":
if len(sys.argv) != 2:
print 'This tool calculates a TERM metric for any given BGF grammar.'
Expand All @@ -12,11 +20,6 @@
sys.exit(1)
bgf = BGF.Grammar()
bgf.parse(sys.argv[1])
term = []
for p in bgf.prods:
for n in p.expr.wrapped.getXml().findall('.//terminal'):
if n.text not in term:
term.append(n.text)
#print 'TERM =',len(term)
print len(term)
print len(term(bgf))
sys.exit(0)
6 changes: 4 additions & 2 deletions topics/investigation/size/testperform
@@ -1,8 +1,10 @@
#!/bin/sh

echo [Test Case] `basename $1`
./term.py $1 >> $1.out || exit -1
./var.py $1 >> $1.out || exit -1
./top.py $1 >> $1.out || exit -1
./bottom.py $1 >> $1.out || exit -1
./prod.py $1 > $1.out || exit -1
./bprod.py $1 >> $1.out || exit -1
./var.py $1 >> $1.out || exit -1
./term.py $1 >> $1.out || exit -1
diff $1.out $1.baseline || exit -1
2 changes: 0 additions & 2 deletions topics/investigation/size/tests/antlr.bgf.baseline
@@ -1,4 +1,2 @@
14
8
11
9
2 changes: 0 additions & 2 deletions topics/investigation/size/tests/dcg.bgf.baseline
@@ -1,4 +1,2 @@
11
11
8
9
2 changes: 0 additions & 2 deletions topics/investigation/size/tests/ecore.bgf.baseline
@@ -1,4 +1,2 @@
18
12
12
0
2 changes: 0 additions & 2 deletions topics/investigation/size/tests/ecore2.bgf.baseline
@@ -1,4 +1,2 @@
15
9
9
0
2 changes: 0 additions & 2 deletions topics/investigation/size/tests/fl_ldf.bgf.baseline
@@ -1,4 +1,2 @@
2
2
5
1
2 changes: 0 additions & 2 deletions topics/investigation/size/tests/impl1.bgf.baseline
@@ -1,4 +1,2 @@
282
282
142
91
2 changes: 0 additions & 2 deletions topics/investigation/size/tests/impl2.bgf.baseline
@@ -1,4 +1,2 @@
185
185
91
92

0 comments on commit 56b5722

Please sign in to comment.