关于来自维基的加泰罗尼亚数字的表达

时间:2014-06-04 19:47:04

标签: algorithm catalan

根据维基catalan definition from wiki,我看到下面的表达式: enter image description here

我能理解前两个表达式,但对第三个表达式真的很困惑。 pi符号代表乘法。表达式是否代表下面的代码:

for (int i = 2; i < n + 1; i++) {
    sum *= (n + i)/i;
}

我的代码在

下面
public class Test {
public  int getCatalan(int n) {
    //Catalan Number = (2n)!/(n+1)!*n!
    int product = 1;
    if (n == 1)
        return 1;

    for (int i = 2; i < n + 1; i++) {
        product *= (n+i)/i;
    }
    return product;
}

public static void main(String[] args) {
    Test test = new Test();

    for (int i = 1;i < 7; i++) {
        System.out.println("when i=" + i + " its catalan number is "+ test.getCatalan(i));
    }
}

}

我得到的结果完全错误

enter image description here

有人帮助我吗?

3 个答案:

答案 0 :(得分:2)

是。这大致意味着什么(假设您将sum初始化为1)。

但要注意整数除法。如果你写(n + i)/i并且ni都是整数,你可能会发现自己在某些语言中有一些意想不到的输出。

例如,在Java中,如果n = 3i = 2(n + i)/i = 2,而不是2.5,则int / int = int,我们无法存储{{ 1}}在一个整数。

如果你在某处投了2.5或添加double+ 0.0,结果将是* 1.0double)并且应该是正确的

另请注意,double / int = double本身应为sum / double,而不是float(因为,int无法存储{{ 1}},类似于上面提到的)。如果您希望输出为sum,则应2.5

int

(我也将Math.round更改为int n = 3; double product = 1; for (int i = 2; i <= n; i++) { product *= (0.0 + n + i)/i; } System.out.println(product); // 5 - 后者对我来说更清楚,但它在功能上没有改变代码)

有关更多技术细节,请参阅JLS - Division Operator /Binary Numeric Promotion

答案 1 :(得分:1)

是。确保将sum(可能应称为product)初始化为1。

答案 2 :(得分:0)

使用long或BigIntegers(或使用您使用的任何语言的等效物)来避免浮点错误可能更安全。您可以跟踪分子和分母并在末尾划分。 (或在步骤之间保持减少以减少溢出的可能性)

long catalan(long n) {
    long p = 1;
    long q = 1;
    for (long k = 2; k <= n; k++) {
        p *= (n + k);
        q *= k;

        // these 3 lines are optional, and just delay when overflow happens
        long gcd = gcd(p, q);
        p /= gcd; 
        q /= gcd;
    }
    return p / q;
}

在这里查看一个比较:https://coderpad.io/565957使用双打将在n = 30时给你错误的答案,gcd我的只有33到好,但是你可以轻松换掉BigIntegers的长号无限期地去。