BigDecimal 符号/括号

发布于 2024-12-17 06:06:35 字数 619 浏览 3 评论 0原文

我正在尝试强制 BigDecimal 使用符号(例如,不使用 Decimal.multiply,而是执行 Decimal *),因为此问题涉及大量括号。

你们能告诉我是否有一种方法可以在 BigDecimal 上使用符号而不将其转换为 Double 或其他东西?或者可以将 t 转换成 term 之类的格式吗?

double t = ((1.00 / f1) * ((((4.00 / (ak1 + 1.00)) - (2.00 / (ak1 + 4.00))) - (1.00 / (ak1 + 5.00))) - (1 / (ak1 + 6.00))));

对于像这样的格式,

term = ((one.divide(f,mc)).multiply(((((four.divide((ak.add(one)),mc)).subtract((two.divide((ak.add(four)),mc)))).subtract((one.divide((ak.add(five)),mc)))).subtract((one.divide((ak.add(six)),mc))))));

我已经多次尝试记录它,并花了近 6 个小时试图找出 BigDecimal 的错误所在。

I'm trying force BigDecimal to use symbols (Ex. Instead of Decimal.multiply, do Decimal *), because of the mass parenthesis being involved in this problem.

Can you guys tell me if there's a way to use symbols on BigDecimal without converting it to Double or something? Or can you convert t into a format like term?

double t = ((1.00 / f1) * ((((4.00 / (ak1 + 1.00)) - (2.00 / (ak1 + 4.00))) - (1.00 / (ak1 + 5.00))) - (1 / (ak1 + 6.00))));

To a format like

term = ((one.divide(f,mc)).multiply(((((four.divide((ak.add(one)),mc)).subtract((two.divide((ak.add(four)),mc)))).subtract((one.divide((ak.add(five)),mc)))).subtract((one.divide((ak.add(six)),mc))))));

I've tried recording it lots of times, and spent almost 6 hours trying to figure out where I'm getting wrong with the BigDecimal.

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(4

不弃不离 2024-12-24 06:06:35

不可以。不幸的是 Java 不支持运算符重载。您别无选择,只能在 BigDecimal 上使用这些方法。

No. Unfortunately Java does not support operator overloading. You have no choice but to use those methods on BigDecimal.

沒落の蓅哖 2024-12-24 06:06:35

没有。因为Java中没有运算符重载。

为了让事情变得更简单,将方程分成几部分写出来,并找出复杂或重复多次的部分。将计算分解为这些部分,甚至编写辅助方法来帮助您计算总和。如果您将整个计算分成几个部分,那么每个部分都更容易测试。

例如。

import static java.math.BigDecimal.ONE;

public class Sum {

    private static final TWO = new BigDecimal("2");
    private static final FOUR = new BigDecimal("4");
    private static final FIVE = new BigDecimal("5");
    private static final SIX = new BigDecimal("6");

    private BigDecimal f;
    private BigDecimal ak;

    private MathContext mc;

    public Sum(BigDecimal f, BigDecimal ak, MathContext mc) {
        this.f = f;
        this.ak = ak;
        this.mc = mc;
    }

    public BigDecimal calculate() {

        return inverse(f).multiply(
            firstSubtractRest(
                xOverYPlusZ(FOUR, ak, ONE),
                xOverYPlusZ(TWO, ak, FOUR),
                xOverYPlusZ(ONE, ak, FIVE),
                xOverYPlusZ(ONE, ak, SIX),

            ));

    }

    private BigDecimal inverse(BigDecimal x) {
        return ONE.divide(x, mc);
    }

    /* returns x / (y + z) */
    private BigDecimal xOverYPlusZ(BigDecimal x, BigDecimal y, BigDecimal z) {
        BigDecimal divisor = y.add(z);
        return x.divide(divisor, mc);
    }

    private BigDecimal firstSubtractRest(BigDecimal... values) {
        BigDecimal value = values[0];
        for (int i = 1; i < values.length; i++) {
            value = value.subtract(values[i]);
        }
        return value;
    }

}

Nope. Since there is no operator overloading in Java.

To make things simpler for yourself write the equation out in parts and identity the bits that are complicated or repeated several times. Break up your computation into these parts and even write helper methods to help you get the sum computed. If you write the whole computation in parts then each part is easier to test.

eg.

import static java.math.BigDecimal.ONE;

public class Sum {

    private static final TWO = new BigDecimal("2");
    private static final FOUR = new BigDecimal("4");
    private static final FIVE = new BigDecimal("5");
    private static final SIX = new BigDecimal("6");

    private BigDecimal f;
    private BigDecimal ak;

    private MathContext mc;

    public Sum(BigDecimal f, BigDecimal ak, MathContext mc) {
        this.f = f;
        this.ak = ak;
        this.mc = mc;
    }

    public BigDecimal calculate() {

        return inverse(f).multiply(
            firstSubtractRest(
                xOverYPlusZ(FOUR, ak, ONE),
                xOverYPlusZ(TWO, ak, FOUR),
                xOverYPlusZ(ONE, ak, FIVE),
                xOverYPlusZ(ONE, ak, SIX),

            ));

    }

    private BigDecimal inverse(BigDecimal x) {
        return ONE.divide(x, mc);
    }

    /* returns x / (y + z) */
    private BigDecimal xOverYPlusZ(BigDecimal x, BigDecimal y, BigDecimal z) {
        BigDecimal divisor = y.add(z);
        return x.divide(divisor, mc);
    }

    private BigDecimal firstSubtractRest(BigDecimal... values) {
        BigDecimal value = values[0];
        for (int i = 1; i < values.length; i++) {
            value = value.subtract(values[i]);
        }
        return value;
    }

}
如梦 2024-12-24 06:06:35

您可以编写一个简单的解析器来构建表达式,然后使用 Rhino 或 Java 中可用的其他脚本引擎对其进行评估代码。

You could write a simple parser to build the expression then evaluate it using Rhino or other scripting engine available inside Java code.

留蓝 2024-12-24 06:06:35

您可以将表达式放在最后,而不是首先反转 f1。

double t = (4 / (ak1 + 1) - 2 / (ak1 + 4) - 1 / (ak1 + 5) - 1 / (ak1 + 6)) / f1;

您确定需要 BigDecimal 提供的精度吗?即您需要超过 15 位的精度。

double f1 = 1;
double ak1 = 1;

double t = (4 / (ak1 + 1) - 2 / (ak1 + 4) - 1 / (ak1 + 5) - 1 / (ak1 + 6)) / f1;

System.out.println(t);

System.out.println(new Sum(BigDecimal.ONE, BigDecimal.ONE, MathContext.DECIMAL64).calculate());
System.out.println(new Sum(BigDecimal.ONE, BigDecimal.ONE, MathContext.DECIMAL128).calculate());

prints

1.2904761904761906
1.2904761904761904
1.2904761904761904761904761904761904

如果需要超过 15 位的精度,则需要 BigDecimal。但如果您想简化代码并且不需要那么高的精度,我会使用double

Instead of inverting f1 first, you could simply the expression by placing it last.

double t = (4 / (ak1 + 1) - 2 / (ak1 + 4) - 1 / (ak1 + 5) - 1 / (ak1 + 6)) / f1;

Are you sure you need the accuracy BigDecimal provides. i.e. you need more than 15 digits of precision.

double f1 = 1;
double ak1 = 1;

double t = (4 / (ak1 + 1) - 2 / (ak1 + 4) - 1 / (ak1 + 5) - 1 / (ak1 + 6)) / f1;

System.out.println(t);

System.out.println(new Sum(BigDecimal.ONE, BigDecimal.ONE, MathContext.DECIMAL64).calculate());
System.out.println(new Sum(BigDecimal.ONE, BigDecimal.ONE, MathContext.DECIMAL128).calculate());

prints

1.2904761904761906
1.2904761904761904
1.2904761904761904761904761904761904

If you need more than 15 digits of accuracy, you need BigDecimal. But if you are trying to simplify your code and don't need so much precision, I would just use double.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文