我知道如何获得数字之间的平均值,但是当我尝试使用相同的方法(通过设置变量的属性)来获得数字和字符串的混合值的平均值时,它总是返回异常(我知道原因)。
如何使用数字和字符串的混合值获取 column_1 的平均值?
column_1
3
4
N/A
3
N/A
意思是说,在第1列中,平均值必须为3.33.
应该应用(3+4+3)/3
公式,必须忽略/排除计算中的两个N/A
值。怎么做?
答案 0 :(得分:2)
此任务可以分解为几个简单的子任务:
为了解决第一个子任务,我们可以使用Apache commons-lang 库。 StringUtils.isNumeric(java.lang.CharSequence)方法可帮助我们检查值是否为数字。
为了解决第二个子任务,我们可以使用两个变量 - 第一个用于存储数值,第二个用于计算平均值。
我在此示例中使用了csv数据源:
numValue
3
4
N/A
3
N/A
以下示例中此数据源的数据适配器名称为 str_num.csv 。跳过文件的第一行 - 它包含列的名称。
我使用 Jaspersoft Studio (JSS)来设计报告模板。 Detail 频段用于显示数据,摘要频段用于显示平均值。
包含值(数字和非数字)的字段将属于 java.lang.String 类型。
第一个变量仅用于存储数值。如果值
,我们正在使用 null 初始化变量表达式为:
StringUtils.isNumeric($F{numValue}) ? Integer.valueOf($F{numValue}) : null
Java 库正在此表达式中使用,这就是为什么我们需要将报表的语言设置为 java 并为类 StringUtils 添加导入
平均值计算类型的第二个变量:
<variable name="averageValue" class="java.lang.Double" calculation="Average">
<variableExpression><![CDATA[$V{number}]]></variableExpression>
<initialValueExpression><![CDATA[0]]></initialValueExpression>
</variable>
完整模板:
<?xml version="1.0" encoding="UTF-8"?>
<jasperReport xmlns="http://jasperreports.sourceforge.net/jasperreports" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://jasperreports.sourceforge.net/jasperreports http://jasperreports.sourceforge.net/xsd/jasperreport.xsd" name="Average value" pageWidth="595" pageHeight="842" columnWidth="555" leftMargin="20" rightMargin="20" topMargin="20" bottomMargin="20" uuid="bee405b0-c35a-442a-841d-f51423c1c797">
<property name="com.jaspersoft.studio.data.defaultdataadapter" value="str_num.csv"/>
<import value="org.apache.commons.lang3.StringUtils"/>
<queryString>
<![CDATA[]]>
</queryString>
<field name="numValue" class="java.lang.String"/>
<variable name="number" class="java.lang.Integer">
<variableExpression><![CDATA[StringUtils.isNumeric($F{numValue}) ? Integer.valueOf($F{numValue}) : null]]></variableExpression>
</variable>
<variable name="averageValue" class="java.lang.Double" calculation="Average">
<variableExpression><![CDATA[$V{number}]]></variableExpression>
<initialValueExpression><![CDATA[0]]></initialValueExpression>
</variable>
<detail>
<band height="30" splitType="Stretch">
<textField>
<reportElement x="0" y="0" width="230" height="30" uuid="9d00d7e3-b9bc-404d-8842-728326a5d2df"/>
<textFieldExpression><![CDATA["Original value: " + $F{numValue}]]></textFieldExpression>
</textField>
<textField>
<reportElement x="230" y="0" width="250" height="30" uuid="4509cae9-3b89-4860-838a-36aa4466fb37"/>
<textFieldExpression><![CDATA["Only numeric value: " + $V{number}]]></textFieldExpression>
</textField>
</band>
</detail>
<summary>
<band height="53">
<staticText>
<reportElement x="0" y="0" width="230" height="30" uuid="937af139-259c-49da-a0d9-191bcf801cca"/>
<text><![CDATA[Average value (non numeric values are skipped):]]></text>
</staticText>
<textField pattern="0.00">
<reportElement x="230" y="0" width="140" height="30" uuid="9abd786b-32ee-4ab1-91dc-851e8bfef0db"/>
<textFieldExpression><![CDATA[$V{averageValue}]]></textFieldExpression>
</textField>
</band>
</summary>
</jasperReport>
JSS 中生成的resut如下所示:
如果我们将第一个变量(用于存储数值)的表达式更改为:
StringUtils.isNumeric($F{numValue}) ? Integer.valueOf($F{numValue}) : 0
结果将是:
- 这是5条记录的平均值,而不是上述第一种情况中的3条记录。