fixed functions
This commit is contained in:
parent
a52c578ecd
commit
72f26d9fe2
@ -25,7 +25,6 @@ import org.thingsboard.script.api.tbel.TbelCfTsDoubleVal;
|
||||
import org.thingsboard.script.api.tbel.TbelCfTsRollingArg;
|
||||
import org.thingsboard.server.common.data.kv.KvEntry;
|
||||
import org.thingsboard.server.common.data.kv.TsKvEntry;
|
||||
import org.thingsboard.server.exception.CalculatedFieldStateException;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.List;
|
||||
@ -116,10 +115,11 @@ public class TsRollingArgumentEntry implements ArgumentEntry {
|
||||
case STRING -> value.getStrValue().ifPresent(aString -> tsRecords.put(ts, Double.parseDouble(aString)));
|
||||
case JSON -> value.getJsonValue().ifPresent(aString -> tsRecords.put(ts, Double.parseDouble(aString)));
|
||||
}
|
||||
cleanupExpiredRecords();
|
||||
} catch (Exception e) {
|
||||
tsRecords.put(ts, Double.NaN);
|
||||
log.debug("Invalid value '{}' for time series rolling arguments. Only numeric values are supported.", value.getValue());
|
||||
} finally {
|
||||
cleanupExpiredRecords();
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@ -61,14 +61,18 @@ public class TbelCfTsRollingArg implements TbelCfArg, Iterable<TbelCfTsDoubleVal
|
||||
}
|
||||
|
||||
public double max() {
|
||||
return max(true);
|
||||
}
|
||||
|
||||
public double max(boolean ignoreNaN) {
|
||||
if (values.isEmpty()) {
|
||||
return 0;
|
||||
throw new IllegalArgumentException("Rolling argument values are empty.");
|
||||
}
|
||||
|
||||
double max = Double.MIN_VALUE;
|
||||
for (TbelCfTsDoubleVal value : values) {
|
||||
double val = value.getValue();
|
||||
if (Double.isNaN(val)) {
|
||||
if (!ignoreNaN && Double.isNaN(val)) {
|
||||
return val;
|
||||
}
|
||||
if (max < val) {
|
||||
@ -79,14 +83,18 @@ public class TbelCfTsRollingArg implements TbelCfArg, Iterable<TbelCfTsDoubleVal
|
||||
}
|
||||
|
||||
public double min() {
|
||||
return min(true);
|
||||
}
|
||||
|
||||
public double min(boolean ignoreNaN) {
|
||||
if (values.isEmpty()) {
|
||||
return 0;
|
||||
throw new IllegalArgumentException("Rolling argument values are empty.");
|
||||
}
|
||||
|
||||
double min = Double.MAX_VALUE;
|
||||
for (TbelCfTsDoubleVal value : values) {
|
||||
double val = value.getValue();
|
||||
if (Double.isNaN(val)) {
|
||||
if (!ignoreNaN && Double.isNaN(val)) {
|
||||
return Double.NaN;
|
||||
}
|
||||
if (min > val) {
|
||||
@ -97,21 +105,28 @@ public class TbelCfTsRollingArg implements TbelCfArg, Iterable<TbelCfTsDoubleVal
|
||||
}
|
||||
|
||||
public double mean() {
|
||||
if (values.isEmpty()) {
|
||||
return 0;
|
||||
return mean(true);
|
||||
}
|
||||
|
||||
double sum = sum();
|
||||
return Double.isNaN(sum) ? Double.NaN : sum / values.size();
|
||||
public double mean(boolean ignoreNaN) {
|
||||
if (values.isEmpty()) {
|
||||
throw new IllegalArgumentException("Rolling argument values are empty.");
|
||||
}
|
||||
|
||||
return sum(ignoreNaN) / count(ignoreNaN);
|
||||
}
|
||||
|
||||
public double std() {
|
||||
if (values.isEmpty()) {
|
||||
return 0;
|
||||
return std(true);
|
||||
}
|
||||
|
||||
double mean = mean();
|
||||
if (Double.isNaN(mean)) {
|
||||
public double std(boolean ignoreNaN) {
|
||||
if (values.isEmpty()) {
|
||||
throw new IllegalArgumentException("Rolling argument values are empty.");
|
||||
}
|
||||
|
||||
double mean = mean(ignoreNaN);
|
||||
if (!ignoreNaN && Double.isNaN(mean)) {
|
||||
return Double.NaN;
|
||||
}
|
||||
|
||||
@ -119,26 +134,36 @@ public class TbelCfTsRollingArg implements TbelCfArg, Iterable<TbelCfTsDoubleVal
|
||||
for (TbelCfTsDoubleVal value : values) {
|
||||
double val = value.getValue();
|
||||
if (Double.isNaN(val)) {
|
||||
if (!ignoreNaN) {
|
||||
return Double.NaN;
|
||||
}
|
||||
} else {
|
||||
sum += Math.pow(val - mean, 2);
|
||||
}
|
||||
return Math.sqrt(sum / values.size());
|
||||
}
|
||||
return Math.sqrt(sum / count(ignoreNaN));
|
||||
}
|
||||
|
||||
public double median() {
|
||||
return median(true);
|
||||
}
|
||||
|
||||
public double median(boolean ignoreNaN) {
|
||||
if (values.isEmpty()) {
|
||||
return 0;
|
||||
throw new IllegalArgumentException("Rolling argument values are empty.");
|
||||
}
|
||||
|
||||
List<Double> sortedValues = new ArrayList<>();
|
||||
for (TbelCfTsDoubleVal value : values) {
|
||||
double val = value.getValue();
|
||||
if (Double.isNaN(val)) {
|
||||
if (!ignoreNaN) {
|
||||
return Double.NaN;
|
||||
}
|
||||
} else {
|
||||
sortedValues.add(val);
|
||||
}
|
||||
}
|
||||
Collections.sort(sortedValues);
|
||||
|
||||
int size = sortedValues.size();
|
||||
@ -147,51 +172,90 @@ public class TbelCfTsRollingArg implements TbelCfArg, Iterable<TbelCfTsDoubleVal
|
||||
: (sortedValues.get(size / 2 - 1) + sortedValues.get(size / 2)) / 2.0;
|
||||
}
|
||||
|
||||
public double count() {
|
||||
return hasNaN() ? Double.NaN : values.size();
|
||||
public int count() {
|
||||
return count(true);
|
||||
}
|
||||
|
||||
public int count(boolean ignoreNaN) {
|
||||
int count = 0;
|
||||
if (ignoreNaN) {
|
||||
for (TbelCfTsDoubleVal value : values) {
|
||||
if (!Double.isNaN(value.getValue())) {
|
||||
count++;
|
||||
}
|
||||
}
|
||||
return count;
|
||||
}
|
||||
return values.size();
|
||||
}
|
||||
|
||||
public double last() {
|
||||
if (values.isEmpty()) {
|
||||
return 0;
|
||||
return last(true);
|
||||
}
|
||||
|
||||
return hasNaN() ? Double.NaN : values.get(values.size() - 1).getValue();
|
||||
public double last(boolean ignoreNaN) {
|
||||
if (values.isEmpty()) {
|
||||
throw new IllegalArgumentException("Rolling argument values are empty.");
|
||||
}
|
||||
|
||||
double value = values.get(values.size() - 1).getValue();
|
||||
if (!Double.isNaN(value) || !ignoreNaN) {
|
||||
return value;
|
||||
}
|
||||
for (int i = values.size() - 2; i >= 0; i--) {
|
||||
double prevValue = values.get(i).getValue();
|
||||
if (!Double.isNaN(prevValue)) {
|
||||
return prevValue;
|
||||
}
|
||||
}
|
||||
throw new IllegalArgumentException("Rolling argument values are empty.");
|
||||
}
|
||||
|
||||
public double first() {
|
||||
if (values.isEmpty()) {
|
||||
return 0;
|
||||
return first(true);
|
||||
}
|
||||
|
||||
return hasNaN() ? Double.NaN : values.get(0).getValue();
|
||||
public double first(boolean ignoreNaN) {
|
||||
if (values.isEmpty()) {
|
||||
throw new IllegalArgumentException("Rolling argument values are empty.");
|
||||
}
|
||||
|
||||
double firstValue = values.get(0).getValue();
|
||||
if (!Double.isNaN(firstValue) || !ignoreNaN) {
|
||||
return firstValue;
|
||||
}
|
||||
for (int i = 1; i < values.size(); i++) {
|
||||
double nextValue = values.get(i).getValue();
|
||||
if (!Double.isNaN(nextValue)) {
|
||||
return nextValue;
|
||||
}
|
||||
}
|
||||
throw new IllegalArgumentException("Rolling argument values are empty.");
|
||||
}
|
||||
|
||||
public double sum() {
|
||||
return sum(true);
|
||||
}
|
||||
|
||||
public double sum(boolean ignoreNaN) {
|
||||
if (values.isEmpty()) {
|
||||
return 0;
|
||||
throw new IllegalArgumentException("Rolling argument values are empty.");
|
||||
}
|
||||
|
||||
double sum = 0;
|
||||
for (TbelCfTsDoubleVal value : values) {
|
||||
double val = value.getValue();
|
||||
if (Double.isNaN(val)) {
|
||||
if (!ignoreNaN) {
|
||||
return Double.NaN;
|
||||
}
|
||||
} else {
|
||||
sum += val;
|
||||
}
|
||||
}
|
||||
return sum;
|
||||
}
|
||||
|
||||
private boolean hasNaN() {
|
||||
for (TbelCfTsDoubleVal value : values) {
|
||||
if (Double.isNaN(value.getValue())) {
|
||||
return true;
|
||||
}
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
@JsonIgnore
|
||||
public int getSize() {
|
||||
return values.size();
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user