刘光辉
3 小时以前 06f314545ac3514d7ce28939920866ae8188d31c
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
package jnpf.elnFormula;
 
import java.util.ArrayList;
import java.util.Collections;
import java.util.LinkedHashMap;
import java.util.List;
import java.util.Map;
 
public final class FormulaFunctionRegistry {
 
    private final Map<String, FormulaFunction> functions;
    private final List<FormulaFunction> catalog;
    private final List<String> codes;
 
    public FormulaFunctionRegistry() {
        LinkedHashMap<String, FormulaFunction> values = new LinkedHashMap<>();
        add(values, "ABS", "绝对值", "数学", "ABS(x)", "返回数值的绝对值", "ABS(-2)");
        add(values, "POW", "幂", "数学", "POW(x, n)", "返回 x 的整数次幂", "POW(2, 3)");
        add(values, "SQRT", "平方根", "数学", "SQRT(x)", "返回非负数的平方根", "SQRT(4)");
        add(values, "MIN", "最小值", "数学", "MIN(x, ...)", "返回参数中的最小值", "MIN(1, 2)");
        add(values, "MAX", "最大值", "数学", "MAX(x, ...)", "返回参数中的最大值", "MAX(1, 2)");
        add(values, "IF", "条件", "逻辑", "IF(condition, trueValue, falseValue)",
                "按条件返回一个分支", "IF(true, 1, 0)");
        add(values, "COALESCE", "首个非空值", "逻辑", "COALESCE(value, ...)",
                "返回首个非 NULL 值", "COALESCE(null, 1)");
        add(values, "IS_BLANK", "判空", "逻辑", "IS_BLANK(value)",
                "判断 NULL、空白文本或空列表", "IS_BLANK(null)");
        add(values, "SUM", "求和", "统计", "SUM(values)", "返回数值列表之和", "SUM(values_a1)");
        add(values, "MEAN", "平均值", "统计", "MEAN(values)", "返回数值列表平均值", "MEAN(values_a1)");
        add(values, "STDDEV_S", "样本标准差", "统计", "STDDEV_S(values)",
                "返回数值列表的样本标准差", "STDDEV_S(values_a1)");
        add(values, "RSD", "相对标准偏差", "统计", "RSD(values)",
                "返回百分比相对标准偏差", "RSD(values_a1)");
        add(values, "ROUND", "四舍五入", "修约", "ROUND(x, scale)",
                "按 HALF_UP 模式修约", "ROUND(2.345, 2)");
        add(values, "ROUND_UP", "远离零修约", "修约", "ROUND_UP(x, scale)",
                "按 UP 模式修约", "ROUND_UP(2.341, 2)");
        add(values, "ROUND_DOWN", "向零修约", "修约", "ROUND_DOWN(x, scale)",
                "按 DOWN 模式修约", "ROUND_DOWN(2.349, 2)");
        add(values, "CONVERT", "单位换算", "单位", "CONVERT(value, from, to)",
                "在同维度质量或体积单位间换算", "CONVERT(1000, \"mg\", \"g\")");
        add(values, "LOOKUP_EXACT", "精确查值", "查值", "LOOKUP_EXACT(key, x1, y1, ...)",
                "按数值键精确查找", "LOOKUP_EXACT(2, 1, 10, 2, 20)");
        add(values, "LOOKUP_LINEAR", "线性插值", "查值", "LOOKUP_LINEAR(key, x1, y1, ...)",
                "在严格递增点间线性插值", "LOOKUP_LINEAR(5, 0, 0, 10, 1)");
        add(values, "LN", "自然对数", "数学", "LN(x)", "返回 x 的自然对数", "LN(10)");
        add(values, "LOG10", "常用对数", "数学", "LOG10(x)",
                "返回 x 以 10 为底的对数", "LOG10(100)");
        add(values, "LOG", "指定底数对数", "数学", "LOG(x, base)",
                "返回 x 以 base 为底的对数", "LOG(8, 2)");
        add(values, "EXP", "自然指数", "数学", "EXP(x)", "返回 e 的 x 次幂", "EXP(1)");
        add(values, "NTH_ROOT", "N 次方根", "数学", "NTH_ROOT(x, n)",
                "返回 x 的 n 次方根", "NTH_ROOT(27, 3)");
        add(values, "COUNT", "计数", "统计", "COUNT(values)",
                "返回数值列表的项数", "COUNT(values_a1)");
        add(values, "MEDIAN", "中位数", "统计", "MEDIAN(values)",
                "返回数值列表的中位数", "MEDIAN(values_a1)");
        add(values, "STDDEV_P", "总体标准差", "统计", "STDDEV_P(values)",
                "返回数值列表的总体标准差", "STDDEV_P(values_a1)");
        add(values, "VAR_S", "样本方差", "统计", "VAR_S(values)",
                "返回数值列表的样本方差", "VAR_S(values_a1)");
        add(values, "VAR_P", "总体方差", "统计", "VAR_P(values)",
                "返回数值列表的总体方差", "VAR_P(values_a1)");
        add(values, "GEOMEAN", "几何平均值", "统计", "GEOMEAN(values)",
                "返回非负数值列表的几何平均值", "GEOMEAN(values_a1)");
        add(values, "WEIGHTED_MEAN", "加权平均值", "统计",
                "WEIGHTED_MEAN(values, weights)", "按非负权重计算加权平均值",
                "WEIGHTED_MEAN(values_a1, weights_b2)");
        add(values, "SLOPE", "线性回归斜率", "校准", "SLOPE(xValues, yValues)",
                "返回最小二乘直线斜率", "SLOPE(x_values_a1, y_values_b2)");
        add(values, "INTERCEPT", "线性回归截距", "校准", "INTERCEPT(xValues, yValues)",
                "返回最小二乘直线截距", "INTERCEPT(x_values_a1, y_values_b2)");
        add(values, "CORREL", "相关系数", "校准", "CORREL(xValues, yValues)",
                "返回 Pearson 相关系数", "CORREL(x_values_a1, y_values_b2)");
        add(values, "LINEAR_PREDICT", "线性预测", "校准",
                "LINEAR_PREDICT(x, xValues, yValues)", "按最小二乘直线返回预测值",
                "LINEAR_PREDICT(5, x_values_a1, y_values_b2)");
        add(values, "ROUND_HALF_EVEN", "四舍六入五成双", "修约",
                "ROUND_HALF_EVEN(x, scale)", "按 HALF_EVEN 模式修约中间结果",
                "ROUND_HALF_EVEN(2.345, 2)");
        add(values, "ROUND_SIG", "有效数字修约", "修约", "ROUND_SIG(x, digits)",
                "按 HALF_UP 模式保留有效数字", "ROUND_SIG(12345, 3)");
        add(values, "ROUND_SIG_HALF_EVEN", "有效数字五成双修约", "修约",
                "ROUND_SIG_HALF_EVEN(x, digits)", "按 HALF_EVEN 模式保留有效数字",
                "ROUND_SIG_HALF_EVEN(1.245, 3)");
        functions = Collections.unmodifiableMap(values);
        catalog = Collections.unmodifiableList(new ArrayList<>(values.values()));
        codes = Collections.unmodifiableList(new ArrayList<>(values.keySet()));
    }
 
    public FormulaFunction get(String code) {
        return functions.get(code);
    }
 
    public boolean contains(String code) {
        return functions.containsKey(code);
    }
 
    public List<FormulaFunction> catalog() {
        return catalog;
    }
 
    public List<String> codes() {
        return codes;
    }
 
    private static void add(Map<String, FormulaFunction> functions, String code,
                            String chineseName, String category, String signature,
                            String description, String example) {
        functions.put(code, new FormulaFunction(code, chineseName, category, signature,
                description, example, returnType(code)));
    }
 
    private static String returnType(String code) {
        if ("IF".equals(code) || "COALESCE".equals(code)) {
            return "DYNAMIC";
        }
        return "IS_BLANK".equals(code) ? "BOOLEAN" : "DECIMAL";
    }
}