2012-09-18 14 views
12

मेरे जावा कोड का मूल्यांकन करते समय मुझे एक बड़ी समस्या है। समस्या को सरल बनाने के लिए मैंने निम्नलिखित कोड लिखा जो समान उत्सुक व्यवहार उत्पन्न करता है। महत्वपूर्ण तरीका है() और डबल वैल्यू रेट दिया गया है। मेरे रनटाइम टेस्ट (मुख्य विधि में) के लिए मैंने दर को 0.5 बार एक बार और 1.0 बार सेट किया। मान 1.0 के साथ यदि प्रत्येक लूप पुनरावृत्ति में if-statement निष्पादित किया जाएगा और मान 0.5 के साथ if-statement को आधे से अधिक निष्पादित किया जाएगा। इस कारण से मुझे पहले मामले से लंबे समय तक रनटाइम की उम्मीद थी लेकिन विपरीत सच है। क्या कोई मुझे इस घटना की व्याख्या कर सकता है ??जावा उत्सुक लूप प्रदर्शन

मुख्य का परिणाम:

Test mit rate = 0.5 
Length: 50000000, IF executions: 25000856 
Execution time was 4329 ms. 
Length: 50000000, IF executions: 24999141 
Execution time was 4307 ms. 
Length: 50000000, IF executions: 25001582 
Execution time was 4223 ms. 
Length: 50000000, IF executions: 25000694 
Execution time was 4328 ms. 
Length: 50000000, IF executions: 25004766 
Execution time was 4346 ms. 
================================= 
Test mit rate = 1.0 
Length: 50000000, IF executions: 50000000 
Execution time was 3482 ms. 
Length: 50000000, IF executions: 50000000 
Execution time was 3572 ms. 
Length: 50000000, IF executions: 50000000 
Execution time was 3529 ms. 
Length: 50000000, IF executions: 50000000 
Execution time was 3479 ms. 
Length: 50000000, IF executions: 50000000 
Execution time was 3473 ms. 

कोड

public ArrayList<Byte> list = new ArrayList<Byte>(); 
public final int LENGTH = 50000000; 

public PerformanceTest(){ 
    byte[]arr = new byte[LENGTH]; 
    Random random = new Random(); 
    random.nextBytes(arr); 
    for(byte b : arr) 
     list.add(b); 
} 

public void run(double rate){ 

    byte b = 0; 
    int count = 0; 

    for (int i = 0; i < LENGTH; i++) { 

     if(getRate(rate)){ 
      list.set(i, b); 
      count++; 
     } 
    } 
    System.out.println("Length: " + LENGTH + ", IF executions: " + count); 
} 

public boolean getRate(double rate){ 
    return Math.random() < rate; 
} 

public static void main(String[] args) throws InterruptedException { 
    PerformanceTest test = new PerformanceTest(); 

    long start, end; 
    System.out.println("Test mit rate = 0.5"); 
    for (int i = 0; i < 5; i++) { 
     start=System.currentTimeMillis(); 
     test.run(0.5); 
     end = System.currentTimeMillis(); 
     System.out.println("Execution time was "+(end-start)+" ms."); 

     Thread.sleep(500); 
    }  
    System.out.println("================================="); 
    System.out.println("Test mit rate = 1.0");  
    for (int i = 0; i < 5; i++) { 
     start=System.currentTimeMillis(); 
     test.run(1.0); 
     end = System.currentTimeMillis(); 
     System.out.println("Execution time was "+(end-start)+" ms."); 
     Thread.sleep(500); 
    } 
} 
+3

http://stackoverflow.com/questions/11227809/why- है प्रसंस्करण एक हल कर सरणी-तेजी-से-एक-अवर्गीकृत सरणी)। – assylias

+1

यादृच्छिक यहां बहुत धीमी है। मेरा सुझाव है कि आप एक सरल प्रगति का पालन करें और आप अपने अधिकांश समय यादृच्छिक संख्या उत्पन्न नहीं करेंगे। मैं आपको कई बार चलाने और दूसरी बार कई बार चलाने के बजाय वैकल्पिक परीक्षण का सुझाव देता हूं। (आपको उनके बीच सोने की जरूरत नहीं है) –

+0

गर्म करने में सोच रहा है कि क्या आप पहले 1.0 निष्पादित करते हैं? – ssedano

उत्तर

10

शाखा misprediction पहले मामले में प्रदर्शन को मारता है। हालांकि दूसरा मामला कुछ काम करता है, यह कुछ हद तक सीधे आगे है, इसलिए प्रोसेसर आसानी से अगले चरण की भविष्यवाणी कर सकता है। अधिक जानकारी के लिए कृपया यह Wikipedia page देखें।

0.7 के साथ परीक्षण करने का प्रयास करें। यदि मैं सही हूं तो प्रदर्शन 0.5 और 1.0 के बीच कहीं होगा।

+1

दूसरा मामला तेज़ है, और शाखा गलत भविष्यवाणी दूसरे मामले की तुलना में पहले मामले को प्रभावित कर रही है। – NominSim

+0

@NominSim आप सही हैं मैंने पहले के बजाय दूसरा लिखा है, यह अभी तय है। –

+1

ठीक है ... ऐसा लगता है कि ऐसा कारण है। तुम बहुत अच्छे हो, बहुत बहुत धन्यवाद। –

9

यह पुष्टि करने के लिए कि आप शाखा गलतफहमी as indicated in my comment के प्रभाव देख रहे हैं, मैंने कुछ परीक्षण चलाए हैं। तालिका दर (आपके रन विधि में इनपुट) दिखाती है, if की संख्या निष्पादित और चलाने के लिए समय।

0.0 0    1162 
0.1 5,000,892  1204.25 
0.2 10,002,410 1236.8 
0.3 14,998,226 1264 
0.4 19,996,983 1278 
0.5 24,998,455 1305.5 
0.6 29,998,879 1263.25 
0.7 34,999,821 1232.25 
0.8 39,999,414 1203.5 
0.9 44,998,674 1202 
1.0 50,000,000 1176.75 

करीब 0.5 तक पहुंचने के बाद, आपको जितनी अधिक शाखा गलत भविष्यवाणियां मिलती हैं (लगभग हर दौड़)। जितना करीब आप 0 या 1 तक पहुंचते हैं, उतनी सटीक शाखा भविष्यवाणियां आपको मिलती हैं (जब कोई दर 0 या 1 होती है तो कोई गलतफहमी नहीं होती है)।

और क्योंकि एक तस्वीर एक हजार शब्दों के बराबर है:

enter image description here

शायद के साथ [शाखा (अ-) भविष्यवाणी] कुछ करने के लिए (
+2

वाह अच्छा काम ... बहुत कुछ था –

संबंधित मुद्दे