Use this XPath one-liner:
sum(((ea|pa)/@type | perf)[number()= number()])
XSLT 1.0 - based verification:
<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
<xsl:output method="text"/>
<xsl:template match="/*">
<xsl:copy-of select="sum(((ea|pa)/@type | perf)[number()= number()]) "/>
</xsl:template>
</xsl:stylesheet>
When this transformation is applied on the following XML document (the provided fragment, wrapped into a single top element):
<t>
<ea type="null"/>
<pa type="null"/>
<perf>4</perf>
</t>
The XPath expression is evaluated (using as initial context node the top element) and the result of this evaluation is copied to the output:
4
If all elements' values are non-numbers, such as in:
<t>
<ea type="null"/>
<pa type="null"/>
<perf>I am a string</perf>
</t>
the result is again correct:
0
Do note:
The currently selected answer doesn't contain a syntactically valid XSLT 1.0 transformation and any XSLT 1.0 processor (not an XSLT 2.0 one) produces error like this (with Saxon 6.5.4):
SAXON 6.5.4 from Michael Kay
Java version 1.6.0_31
Error at xsl:copy-of on line 12 of file:/(Untitled):
Error in expression sum( ( //ea[not(@type eq 'null')], //pa[not(@type eq 'null')], //perf[not(@type eq 'null')] ) ) : expected ")", found "<name>"
Transformation failed: Failed to compile stylesheet. 1 error detected.
Press any key to continue . . .