Java 如何优化该for循环的计算速度?

Java 如何优化该for循环的计算速度?,java,algorithm,optimization,parallel-processing,scientific-computing,Java,Algorithm,Optimization,Parallel Processing,Scientific Computing,我被一个难题困住了(至少对我来说是这样)。我在分析代码时注意到,几乎所有(单核)计算时间都被下面的单个嵌套循环(图像上的二重积分)占用了。你认为加速计算的最佳方式是什么 我试图将其映射到嵌套流,但我不知道如何映射多个if块。。。使用OpenCL在GPU上尝试这样做会更适合这个问题吗 ip是一个ImageJImageProcessor,它的方法。getPixelValue(x,y)也非常耗时。但由于它属于一个已建立的库,如果可以的话,我希望避免修改它 变量声明: 功能: private双重对比(

我被一个难题困住了(至少对我来说是这样)。我在分析代码时注意到,几乎所有(单核)计算时间都被下面的单个嵌套循环(图像上的二重积分)占用了。你认为加速计算的最佳方式是什么

我试图将其映射到嵌套流,但我不知道如何映射多个
if
块。。。使用OpenCL在GPU上尝试这样做会更适合这个问题吗

ip
是一个ImageJ
ImageProcessor
,它的方法
。getPixelValue(x,y)
也非常耗时。但由于它属于一个已建立的库,如果可以的话,我希望避免修改它

变量声明:
功能:
private双重对比(
) {
如果(面积<1.0){
回报率(1.0/平方米);
}
双c=0.0;
最终整数xmin=最大((整数)楼层(u1),0);
最终int xmax=最小值((int)ceil(v1),宽度-1);
最终int ymin=最大((int)楼层(u2),0);
最终内部ymax=最小((内部)天花板(v2),高度-1);
if((u1如果((xmax您没有给出太多关于循环中发生了什么的信息,例如,变量“ip”是什么。但一般来说,我建议在for循环范围之外实例化变量,因为使用局部变量会增加内存使用量

您可以尝试一种分而治之的方法

将图像分为多个并行处理的部分。 但您必须处理边界(两个部分相交处)上出现的边缘情况

或者你也可以开始寻找数值算法,它计算(离散)积分,并且是为并行设计的

更新

由于您的方法称为
对比度
,因此我假定您正在更改图像的对比度


对图像的操作可以通过卷积(如果对2D图像执行,则基本上是离散二重积分)和特定的(图像滤波器)来执行。这些操作可以在GPU上计算,并以数量级的速度提高。您可以使用编写在多个GPU上执行的程序。

是的,您是对的。我在问题中添加了变量声明。不知道如何帮助您加快代码速度,但您的代码可以减少一些额外的括号。不需要额外的括号括号请参见运算符优先级
if(u1
。请参见Java编码约定(第7.3节),在
返回c/区域中不应使用括号;
祝您好运!:)
private ImageProcessor ip = null; //This type comes from ImageJ
private double area;
private double a11, a22;
private double u1, u2;
private double v1, v2;
private double y1, y2;
private static final double HALF_SQRT2 = sqrt(2.0) / 2.0;
private static final double SQRT_TINY =
    sqrt((double)Float.intBitsToFloat((int)0x33FFFFFF));
private double contrast (
) {
    if (area < 1.0) {
        return(1.0 / SQRT_TINY);
    }
    double c = 0.0;
    final int xmin = max((int)floor(u1), 0);
    final int xmax = min((int)ceil(v1), width - 1);
    final int ymin = max((int)floor(u2), 0);
    final int ymax = min((int)ceil(v2), height - 1);
    if ((u1 < xmin) || (xmax < v1) || (u2 < ymin) || (ymax < v2)){
        return(1.0 / SQRT_TINY);
    }
    if ((xmax <= xmin) || (ymax <= ymin)) {
        return(1.0 / SQRT_TINY);
    }
    for (int y = ymin; (y <= ymax); y++) {
        final double dy = y2 - (double)y;
        final double dy2 = dy * dy;
        for (int x = xmin; (x <= xmax); x++) {
            final double dx = y1 - (double)x;
            final double dx2 = dx * dx;
            final double d = sqrt(dx2 + dy2);
            double z = a11 * dx2 + a12 * dx * dy + a22 * dy2;
            if (z < SQRT_TINY) {
                c -= ip.getPixelValue(x, y);
                continue;
            }
            z = a3 / sqrt(z);
            double d0 = (1.0 - z / SQRT2) * d;
            if (d0 < -HALF_SQRT2) {
                c -= ip.getPixelValue(x, y);
                continue;
            }
            if (d0 < HALF_SQRT2) {
                c += SQRT2 * d0 * ip.getPixelValue(x, y);
                continue;
            }
            d0 = (1.0 - z) * d;
            if (d0 < -1.0) {
                c += ip.getPixelValue(x, y);
                continue;
            }
            if (d0 < 1.0) {
                c += (1.0 - d0) * ip.getPixelValue(x, y) / 2.0;
                continue;
            }
        }
    }
    return(c / area);