Codility FrogJmp奇怪的Java得分

时间:2014-08-22 21:39:20

标签: java time-complexity

所以我决定尝试Codility。第一个任务 - FrogJmp很容易,但令我惊讶的是我得了44%。解决方案,即使在性能方面显然是不可接受的。

原始解决方案:

public int solution2(int X, int Y, int D) {
    return (int) Math.ceil((float)(Y -X)/D);
}

所以我决定用不同的代码尝试它,没有浮点运算。

public int solution(int X, int Y, int D) {
    int diff = Y - X;
    if (diff % D == 0)
        return diff /D; 
    else
        return diff/D + 1;

}

这次我得到了100%。所以我想亲自检查一下性能并编写简单的测试:

class Solution {


    public int solution(int X, int Y, int D) {
        int diff = Y - X;
        if (diff % D == 0)
            return diff /D; 
        else
            return diff/D + 1;

    }

    public int solution2(int X, int Y, int D) {
        return (int) Math.ceil((float)(Y -X)/D);
    }


    private static Random ran = new Random(System.currentTimeMillis());

    public static int getRandom(int a, int b){
        return ran.nextInt(b - a + 1) + a; 
    }


    public static void main(String[] args) {

        int size = 1000_000;
        int max = 1000_000_000;

        int[] xs = new int[size];
        int[] ys = new int[size];
        int[] ds = new int[size];

        for (int i = 0; i < size; i++) {
            int y = getRandom(1, max);
            int x = getRandom(1, y);
            int d = getRandom(1, max);
            xs[i] = x;
            ys[i] = y;
            ds[i] = d;
        }

        long start = System.nanoTime();

        Solution sol = new Solution();
        for (int i = 0; i < size; i++) {
            sol.solution2(xs[i], ys[i], ds[i]);
        }

        long diff = System.nanoTime() - start;

        System.out.println("took: " + diff/1000000 + "ms");
    }
}

令我惊讶的是,在我的机器上,解决方案1平均需要13毫秒,解决方案2(报告为绝对无效)10毫秒。

我错过了什么?

也许它必须对任务的预期时间和空间复杂性做一些事情。

  

预期的最坏情况时间复杂度为O(1);预期的最坏情况空间   复杂性是O(1)。

解决方案2是否具有恒定时间&amp;空间复杂性?

此外,我无法理解44%解决方案的结果报告:

enter image description here

这意味着什么?

17 个答案:

答案 0 :(得分:4)

Java 100/100和O(1)时间复杂度的解决方案。

public int solution(int X, int Y, int D) {
    return Double.valueOf(Math.ceil((Y - X) / (double) D)).intValue();
}

答案 1 :(得分:2)

C#中的100/100解决方案我只是

using System;    
class Solution {
    public int solution(int X, int Y, int D) {        
        return ((Y - X) + D - 1)/D;        
    }
}

答案 2 :(得分:2)

Java 100/100中的解决方案:

public int solution(int X, int Y, int D) {
    int diff = Y - X;
    int count = diff / D;
    if (diff % D > 0) {
        count++;
    }
    return count;
}

答案 3 :(得分:2)

两种解决方案都具有O(1)时间复杂度。问题是第一个解决方案是返回错误的答案。性能测试测试答案和时间。您的解决方案失败可能是因为使用浮动的精确问题。

对于x = 1,y = 1000000000,d = 1,你的第一个解决方案给出1000000000作为答案,第二个给出 999999999.从(float)更改为(double)会更正此结果。

在这些算法测试中,尽可能避免浮点运算通常是一个好主意,以便更容易获得所有情况的确切答案。

答案 4 :(得分:1)

C#中的解决方案

double result = (Y - X) / (D * 1.0);
return Convert.ToInt32(Math.Ceiling(result));

答案 5 :(得分:1)

public static int solution(int X, int Y, int D) {
        // write your code in Java SE 8


       return (int)Math.round((Y-X)/(double)D);

    }

这也将获得100%

答案 6 :(得分:1)

Java中的简单O(1)解决方案:

class Solution {
    public int solution(int X, int Y, int D) {
        return (Y-X) % D == 0 ? (Y-X) / D : (Y-X) / D + 1;
    }
}

答案 7 :(得分:1)

目标C解决方案O(1)

Codility提供的结果

任务得分:100%
正确性:100%
效果:100%

时间复杂度

最差的时间复杂度是O(1)

Xcode Solution Here

+(int)solution:(int)x y:(int)y d:(int)d {

    /******** Algorithm Explanation  ********/

    // FACTS
    //      I realized that the formula:    [x+(n*d)] >= y    satisfies the required frog jumps
    //      then, the formula to find the 'n' required jumps is the following:
    //      n = (y-x)/d

    // STEP 1
    //     Implement the formula in code
    //     Be careful dealing with the floating point, it should be double
    //     use the function 'ceil' as a resource to round to the next integer.

    double n = ((double)y - (double)x) / (double)d; // O(1)
    n = ceil(n);
    return (int)n;
}

答案 8 :(得分:1)

尝试这个100/100

public static int frogJmp(int X, int Y, int D) {
    return (int) Math.ceil( (Y-X) / (double)D );
}

答案 9 :(得分:0)

public int solution(int X, int Y, int D) {
    // write your code in C# 6.0 with .NET 4.5 (Mono)
    double divAll = (Y-X) / (D * 1.0);
    double finalRes = (Y-X) % (D * 1.0) > 0 ? (divAll + 1) : divAll;

    return (int) finalRes;
}

答案 10 :(得分:0)

JS 解决方案

任务得分:100% 正确性:100% 性能:100%

function solution(X, Y, D) {
    return Math.ceil((Y - X) / D);
}

答案 11 :(得分:0)

Here is my simple code with detected time complexity of O(1) in Codility.

public int solution(int X, int Y, int D) {
        int dev = (Y - X) % D;
        if (X == Y)
            return 0;
        else if (dev == 0)
            return (Y - X) / D;
        else
            return ((Y - X) / D) + 1;
    }

答案 12 :(得分:0)

我刚刚用满分来解决它,所以这是我的答案(java):

static int solution(int X, int Y, int D){

    double count=((double)Y-(double)X)/(double) D;

    return (int)Math.ceil(count);
 }

我第一次认为通过使用&#34; while循环&#34;但我没有表现......

答案 13 :(得分:0)

这是我的100%/ 100%解决方案

public int solution(int X, int Y, int D) {
    double d = D;
    return (int) Math.ceil( (Y-X) / d );
}

答案 14 :(得分:0)

C中的Frogjump解决方案

int solution(int X, int Y, int D) {
        // write your code in C90
        int r=0;

        if(Y>X)
        {   
            r=(Y-X)/D;
            if((X+(r*D)) < Y) r++;
        }

        return r;
    }

答案 15 :(得分:0)

首先,你应该注意在你的情况下不能为0的除数&#34; diff / D&#34;, D 不能 0

其次,在您的情况下&#34; diff = Y - X&#34;,如果(差异&lt; = 0),那么您就不再跳跃了。

答案 16 :(得分:-1)

用JS解决方案100%

function solution(X, Y, D) {
  const distance = Y - X;
  if (distance % D === 0) {
    return Math.round(distance/D);
  } 
  return Math.floor(distance/D +1);
}