2012-05-16 57 views
0

我正在嘗試對幾個方法進行基準測試,出於某種原因我得到了不可能的結果。顯然,一些操作比整個應用程序運行時間要長得多。我已經搜查了這一切,並由於某種原因,我不能牽制我做錯了什麼,所以我很抱歉,但我張貼整個方法: -/定時操作產生不可能的結果

public static void parseNumber() throws Exception { 
    long numberHelperTotal = 0; 
    long numberUtilsTotal = 0; 
    long regExTotal = 0; 
    long bruteForceTotal = 0; 
    long scannerTotal = 0; 
    int iterations = 10; 
    for (int i = 0; i < iterations; i++) { 
    long numberHelper = 0; 
    long numberUtils = 0; 
    long regEx = 0; 
    long bruteForce = 0; 
    long scanner = 0; 
    for (int j = 0; j < 999999; j++) { // I know 999999 is a bit overkill... I've tried it with smaller values and it still yields impossible results 
     Date start; //I think it may have something to do with the way I'm doing start and end... 
     Date end; 
     Random rand = new Random(); 
     String string = ((rand.nextBoolean()) ? "" : "-") + String.valueOf(rand.nextDouble() * j); 

     //NumberHelper 
     start = new Date(); 
     NumberHelper.isValidNumber(double.class, string); 
     end = new Date(); 
     numberHelper += end.getTime() - start.getTime(); 

     //NumberUtils 
     start = new Date(); 
     NumberUtils.isNumber(string); 
     end = new Date(); 
     numberUtils += end.getTime() - start.getTime(); 

     //RegEx 
     start = new Date(); 
     Pattern p = Pattern.compile("^[-+]?[0-9]*\\.?[0-9]+$"); 
     Matcher m = p.matcher(string); 
     if (m.matches()) { 
     Double.parseDouble(string); 
     } 
     end = new Date(); 
     regEx += end.getTime() - start.getTime(); 

     //Brute Force (not international support) and messy support for E and negatives 
     //This is not the way to do it... 
     start = new Date(); 
     int decimalpoints = 0; 
     for (char c : string.toCharArray()) { 
     if (Character.isDigit(c)) { 
      continue; 
     } 
     if (c != '.') { 
      if (c == '-' || c == 'E') { 
      decimalpoints--; 
      } else { 
      //return false 
      //because it should never return false in this test, I will throw an exception here if it does. 
      throw new Exception("Brute Force returned false! It doesn't work! The character is " + c + " Here's the number: " + string); 
      } 
     } 
     if (decimalpoints > 0) { 
      //return false 
      //because it should never return false in this test, I will throw an exception here if it does. 
      throw new Exception("Brute Force returned false! It doesn't work! The character is " + c + " Here's the number: " + string); 
     } 
     decimalpoints++; 
     } 
     end = new Date(); 
     bruteForce += end.getTime() - start.getTime(); 

     //Scanner 
     start = new Date(); 
     Scanner scanNumber = new Scanner(string); 
     if (scanNumber.hasNextDouble()) {//check if the next chars are integer 
     //return true; 
     } else { 
     //return false; 
     //because it should never return false in this test, I will throw an exception here if it does. 
     throw new Exception("Scanner returned false! It doesn't work! Here's the number: " + string); 
     } 
     end = new Date(); 
     scanner += end.getTime() - start.getTime(); 

     //Increase averages 
     numberHelperTotal += numberHelper; 
     numberUtilsTotal += numberUtils; 
     regExTotal += regEx; 
     bruteForceTotal += bruteForce; 
     scannerTotal += scanner; 
     //For debug: 
     //System.out.println("String: " + string); 
     //System.out.println("NumberHelper: " + numberHelper); 
     //System.out.println("NumberUtils: " + numberUtils); 
     //System.out.println("RegEx: " + regEx); 
     //System.out.println("Brute Force: " + bruteForce); 
     //System.out.println("Scanner: " + scanner); 
    } 
    } 

樣本輸出:

First: NumberUtils - 83748758 milliseconds 
Second: Brute Force - 123797252 milliseconds 
Third: NumberHelper - 667504094 milliseconds 
Fourth: RegEx - 2540545193 milliseconds 
Fifth: Scanner - 23447108911 milliseconds 
+0

你使用System.currentTimeInMillis()得到了相同的結果嗎? – mcfinnigan

+0

嘗試在路易斯下面的答案中建議的'System.nanoTime()'。 – kentcdodds

回答

0

繼5號線似乎是不正確的地方:

//Increase averages 
numberHelperTotal += numberHelper; 
numberUtilsTotal += numberUtils; 
regExTotal += regEx; 
bruteForceTotal += bruteForce; 
scannerTotal += scanner; 

嘗試把他們for (int j ...循環之外。

+0

哇,這很尷尬!謝謝你的收穫。那樣做了。結果是(如果有人感興趣:'NumberHelper:144毫秒'''NumberUtils:25毫秒'''RegEx:406毫秒'''蠻力:35毫秒'''掃描儀:20486毫秒 – kentcdodds

2

使用System.nanoTime(),這實際上是用於像「取兩個時間之間的區別在你運行的中間。」

或者,更好的主意 - 使用已經知道如何熱身JIT和所有你需要做的就是準確的基準測試結果與其他事物的預建的Java基準測試框架。 Caliper可能是最着名的。

+0

感謝您的提示。我正在研究它。現在,這是爲什麼這不起作用的問題!哈哈。這裏是使用System.nanoTime()的輸出:'NumberHelper:73秒.' - 'NumberUtils:18 seconds.' - 'RegEx:185 seconds.' - '蠻力:17秒.' - 'Scanner: 8831秒。「 - 這是事實,整個過程只花了19秒,這讓我想知道...... – kentcdodds

相關問題