XPTY0004: '>' 的第一个操作数所需的项目类型是数字;提供的值具有项目类型 xs:string
XPTY0004: Required item type of first operand of '>' is numeric; supplied value has item type xs:string
toComplie 字符串包含求和、乘法等函数的所有定义,并附加 if ($a > 0) then (iaf:numeric-equal(iaf:numeric-multiply($b, $c), $d)) else (true())
执行此操作的代码段是:
XQueryExecutable queryExecutable = xqueryCompiler.compile(toCompile.toString());
XQueryEvaluator xqueryEvaluator = queryExecutable.load();
//setExternalVariables(): function used to set the variables for the test contains below line
xqueryEvaluator.setExternalVariable(new QName(memberName), value);
setExternalVariables(xqueryEvaluator,assertionExpression);
xqueryResult = xqueryEvaluator.evaluate();
抛出如下异常:
XPTY0004: Required item type of the first operand of '>' is numeric; supplied value has item type xs:string
如果需要更多信息来理解这个问题,请告诉我。这是else部分的原因,还是其他原因?
编辑:
在 setExternalVariables()
中,我使用下面的行添加变量,使用 for-each 循环。 value
变量的类型是 net.sf.saxon.s9api.XdmValue
xqueryEvaluator.setExternalVariable(new QName(memberName), value);
在setExternalVariables()
方法中,
// FACT_VALUE_FORMAT:%s;%s -- where first string is value and second gives information about precision.
//current option
XdmAtomicValue atomicValue = new XdmAtomicValue(String.format(FACT_VALUE_FORMAT, fact.getValue(),getPrecision(fact.getDecimals())));
// alternative 1
atomicValue = new XdmAtomicValue(getDoubleValue(fact));
//alternative 2
atomicValue = new XdmAtomicValue(getStringValue(fact));
在getDoubleValue()
,
String precision = fact.getDecimals();
BigDecimal value = new BigDecimal(fact.getValue());
if((precision != null ) && (precision.equals(INF_STRING) == false )){
if(Integer.parseInt(precision)>0){
NumberFormat nf = NumberFormat.getNumberInstance(Locale.US);
DecimalFormat df = (DecimalFormat)nf;
// If the decimal value is greater than 0, then we need the decimal precision correct to n places of decimal
df.setMaximumFractionDigits(Integer.parseInt(precision) + 1);
double doublePrecision = Math.pow(10,-Integer.parseInt(precision))/2;
df.setMaximumFractionDigits(Integer.parseInt(precision) + 1);
precision = df.format(doublePrecision);
System.out.println("doublePrecision\t:\t"+doublePrecision);
return (double) Math.round(value.doubleValue() * doublePrecision) / doublePrecision;
}else{
int scale = (int) Math.pow(10, -Integer.parseInt(precision));
System.out.println("scale\t:\t"+scale);
return (double) Math.round(value.doubleValue() * scale) / scale;
}
}
return value.doubleValue();
在getStringValue(),
String value = fact.getValue();
String decimal = fact.getDecimals();
String DOT = "\.";
if(value.contains(".")){
final int parseInt = Integer.parseInt(decimal);
if(parseInt>0){
String[]split = value.split(DOT);
value = split[0];
if(parseInt>=value.length()){
return "0";
}
for (int i = 0; i < parseInt; i++) {
char[] array =value.toCharArray();
array[value.length()-i-1]="0".charAt(0);
value = new String(array);
}
}else{
final int parseNegativeInt = -Integer.parseInt(decimal);
String[]split = value.split(DOT);
String tempValue = split[1];
if(tempValue.length()>parseNegativeInt){
tempValue = tempValue.substring(0, parseNegativeInt);
}
value = split[0]+"."+tempValue;
}
}
return value;
当前的实现和 alternative(2) 不适用于上述规则,当我返回 double 时,它将大数字转换为包含 char E 的表达式,因为例如5.12344E12,在其他规则中失败。
Error on line 199 of module with no systemId:
FORG0001: Cannot convert string "1.089563E9" to xs:decimal: invalid character 'E'
at iaf:splitValueThreshold() (module with no systemId#20)
at iaf:numeric-equal() (module with no systemId#343)
请提出任何其他选项。
通常 XPath >
将字符串操作数隐式转换为数字,但您可以使用 number()
XPath 函数强制转换。
if (number($a) > 0) then (iaf:numeric-equal(iaf:numeric-multiply($b, $c), $d)) else (true())
假设您在 Java 端有数值作为字符串,例如String value = "2179.125955";
然后我建议通过使用 new XdmAtomicValue(new BigDecimal(value))
作为传递给 setExternalVariable
的值将它们作为 xs:decimal
传递给 XQuery/XPath 例如
xqueryEvaluator.setExternalVariable(new QName(memberName), new XdmAtomicValue(new BigDecimal(value)));
我支持 Martin 的建议(我首先忽略了 BigDecimal 与 BigDecimalValue)。
根据 Saxon 的文档,我想到了一些替代方案:
atomicValue = new XdmAtomicValue(
new BigDecimalValue(getDoubleValue(fact))
);
或者为了避免经过双打或 BigDecimal,类似于:
atomicValue = new XdmAtomicValue(
(BigDecimalValue)BigDecimalValue.makeDecimalValue(getStringValue(fact), true)
);
// potentially adding an "instance of BigDecimalValue" check in the middle
// or bypassing all checks with 'false' instead of 'true'
注意:如果传递 xs:double
而不是 xs:decimal
,我不确定我是否完全理解其他规则中出现的问题。我怀疑在这些其他规则中可能有一些转换回 xs:string
,因为这是可以引入 E
的地方。任何类型的数值之间的 XPath 比较应该是无缝的。
总的来说(但我只是猜测,因为我不知道所涉及的细节,除了在规则中看到 EBA 的区间算术函数的用法),我认为对齐使用的类型可能是个好主意在或传递给具有原始 XBRL 概念类型的 XBRL 公式规则(使用 xs:decimal
表示 xbrli:decimalItemType
(r) 或 xbrli:monetaryItemType
(m),但 xs:double
表示 xbrli:doubleItemType
, 等), 因为词法空间将与 XBRL 实例中使用的词法空间相匹配。
toComplie 字符串包含求和、乘法等函数的所有定义,并附加 if ($a > 0) then (iaf:numeric-equal(iaf:numeric-multiply($b, $c), $d)) else (true())
执行此操作的代码段是:
XQueryExecutable queryExecutable = xqueryCompiler.compile(toCompile.toString());
XQueryEvaluator xqueryEvaluator = queryExecutable.load();
//setExternalVariables(): function used to set the variables for the test contains below line
xqueryEvaluator.setExternalVariable(new QName(memberName), value);
setExternalVariables(xqueryEvaluator,assertionExpression);
xqueryResult = xqueryEvaluator.evaluate();
抛出如下异常:
XPTY0004: Required item type of the first operand of '>' is numeric; supplied value has item type xs:string
如果需要更多信息来理解这个问题,请告诉我。这是else部分的原因,还是其他原因?
编辑:
在 setExternalVariables()
中,我使用下面的行添加变量,使用 for-each 循环。 value
变量的类型是 net.sf.saxon.s9api.XdmValue
xqueryEvaluator.setExternalVariable(new QName(memberName), value);
在setExternalVariables()
方法中,
// FACT_VALUE_FORMAT:%s;%s -- where first string is value and second gives information about precision.
//current option
XdmAtomicValue atomicValue = new XdmAtomicValue(String.format(FACT_VALUE_FORMAT, fact.getValue(),getPrecision(fact.getDecimals())));
// alternative 1
atomicValue = new XdmAtomicValue(getDoubleValue(fact));
//alternative 2
atomicValue = new XdmAtomicValue(getStringValue(fact));
在getDoubleValue()
,
String precision = fact.getDecimals();
BigDecimal value = new BigDecimal(fact.getValue());
if((precision != null ) && (precision.equals(INF_STRING) == false )){
if(Integer.parseInt(precision)>0){
NumberFormat nf = NumberFormat.getNumberInstance(Locale.US);
DecimalFormat df = (DecimalFormat)nf;
// If the decimal value is greater than 0, then we need the decimal precision correct to n places of decimal
df.setMaximumFractionDigits(Integer.parseInt(precision) + 1);
double doublePrecision = Math.pow(10,-Integer.parseInt(precision))/2;
df.setMaximumFractionDigits(Integer.parseInt(precision) + 1);
precision = df.format(doublePrecision);
System.out.println("doublePrecision\t:\t"+doublePrecision);
return (double) Math.round(value.doubleValue() * doublePrecision) / doublePrecision;
}else{
int scale = (int) Math.pow(10, -Integer.parseInt(precision));
System.out.println("scale\t:\t"+scale);
return (double) Math.round(value.doubleValue() * scale) / scale;
}
}
return value.doubleValue();
在getStringValue(),
String value = fact.getValue();
String decimal = fact.getDecimals();
String DOT = "\.";
if(value.contains(".")){
final int parseInt = Integer.parseInt(decimal);
if(parseInt>0){
String[]split = value.split(DOT);
value = split[0];
if(parseInt>=value.length()){
return "0";
}
for (int i = 0; i < parseInt; i++) {
char[] array =value.toCharArray();
array[value.length()-i-1]="0".charAt(0);
value = new String(array);
}
}else{
final int parseNegativeInt = -Integer.parseInt(decimal);
String[]split = value.split(DOT);
String tempValue = split[1];
if(tempValue.length()>parseNegativeInt){
tempValue = tempValue.substring(0, parseNegativeInt);
}
value = split[0]+"."+tempValue;
}
}
return value;
当前的实现和 alternative(2) 不适用于上述规则,当我返回 double 时,它将大数字转换为包含 char E 的表达式,因为例如5.12344E12,在其他规则中失败。
Error on line 199 of module with no systemId: FORG0001: Cannot convert string "1.089563E9" to xs:decimal: invalid character 'E' at iaf:splitValueThreshold() (module with no systemId#20) at iaf:numeric-equal() (module with no systemId#343)
请提出任何其他选项。
通常 XPath >
将字符串操作数隐式转换为数字,但您可以使用 number()
XPath 函数强制转换。
if (number($a) > 0) then (iaf:numeric-equal(iaf:numeric-multiply($b, $c), $d)) else (true())
假设您在 Java 端有数值作为字符串,例如String value = "2179.125955";
然后我建议通过使用 new XdmAtomicValue(new BigDecimal(value))
作为传递给 setExternalVariable
的值将它们作为 xs:decimal
传递给 XQuery/XPath 例如
xqueryEvaluator.setExternalVariable(new QName(memberName), new XdmAtomicValue(new BigDecimal(value)));
我支持 Martin 的建议(我首先忽略了 BigDecimal 与 BigDecimalValue)。
根据 Saxon 的文档,我想到了一些替代方案:
atomicValue = new XdmAtomicValue(
new BigDecimalValue(getDoubleValue(fact))
);
或者为了避免经过双打或 BigDecimal,类似于:
atomicValue = new XdmAtomicValue(
(BigDecimalValue)BigDecimalValue.makeDecimalValue(getStringValue(fact), true)
);
// potentially adding an "instance of BigDecimalValue" check in the middle
// or bypassing all checks with 'false' instead of 'true'
注意:如果传递 xs:double
而不是 xs:decimal
,我不确定我是否完全理解其他规则中出现的问题。我怀疑在这些其他规则中可能有一些转换回 xs:string
,因为这是可以引入 E
的地方。任何类型的数值之间的 XPath 比较应该是无缝的。
总的来说(但我只是猜测,因为我不知道所涉及的细节,除了在规则中看到 EBA 的区间算术函数的用法),我认为对齐使用的类型可能是个好主意在或传递给具有原始 XBRL 概念类型的 XBRL 公式规则(使用 xs:decimal
表示 xbrli:decimalItemType
(r) 或 xbrli:monetaryItemType
(m),但 xs:double
表示 xbrli:doubleItemType
, 等), 因为词法空间将与 XBRL 实例中使用的词法空间相匹配。