PowerShell प्रदर्शन अंतर फ़िल्टर बनाम फ़ंक्शन


11

मैं वर्तमान में पढ़ रहा हूँ Windows PowerShell 3.0 PowerShell के लिए कुछ अधिक जानकारी प्राप्त करने के लिए Step by Step पुस्तक।

पृष्ठ 201 पर लेखक प्रदर्शित करता है कि एक फिल्टर समान कार्यात्मक रूप से कार्य से तेज है।

इस स्क्रिप्ट में उनके कंप्यूटर पर 2.6 सेकंड लगते हैं:

MeasureAddOneFilter.ps1
Filter AddOne
{ 
 "add one filter"
  $_ + 1
}

Measure-Command { 1..50000 | addOne }

और यह एक 4.6 सेकंड

MeasureAddOneFunction.ps1
Function AddOne
{  
  "Add One Function"
  While ($input.moveNext())
   {
     $input.current + 1
   }
}

Measure-Command { 1..50000 | addOne }

यदि मैं इस कोड को चलाता हूं तो उसके परिणाम के बिल्कुल विपरीत है:

.\MeasureAddOneFilter.ps1
Days              : 0
Hours             : 0
Minutes           : 0
Seconds           : 0
Milliseconds      : 226
Ticks             : 2266171
TotalDays         : 2,62288310185185E-06
TotalHours        : 6,29491944444444E-05
TotalMinutes      : 0,00377695166666667
TotalSeconds      : 0,2266171
TotalMilliseconds : 226,6171

.\MeasureAddOneFunction.ps1

Days              : 0
Hours             : 0
Minutes           : 0
Seconds           : 0
Milliseconds      : 93
Ticks             : 933649
TotalDays         : 1,08061226851852E-06
TotalHours        : 2,59346944444444E-05
TotalMinutes      : 0,00155608166666667
TotalSeconds      : 0,0933649
TotalMilliseconds : 93,3649

क्या कोई मुझे ये समझा सकता है?

जवाबों:


13

जब तक लेखक ने अधिक सहायक सबूत नहीं दिए, शायद वह सिर्फ गर्म हवा से भरा था। आपने परीक्षण चलाया और परिणाम प्राप्त किया और उसे गलत साबित किया।

संपादित करें: जेफरी स्नोवर के ब्लॉग से:

फ़िल्टर एक फ़ंक्शन है जिसमें बस एक प्रक्रिया स्क्रिप्टब्लॉक है

अकेले मुझे यह समझाने के लिए पर्याप्त नहीं है कि एक फिल्टर एक फ़ंक्शन पर गति लाभ होने वाला है, दोनों को समान प्रक्रिया ब्लॉक दिया गया है।

यह भी कि 1950 का उपकरण किस प्रकार का है, जहां एक नंबर को जोड़ने में 4.6 सेकंड लगते हैं?

PS C:\Users\Ryan> Measure-Command { Filter AddOne { $_ + 1 }; AddOne 1 }

TotalMilliseconds : 7.7266


PS C:\Users\Ryan> Measure-Command { Function AddOne { $_ + 1 }; AddOne 1 }    

TotalMilliseconds : 0.4108

4.6 सेकेंड का समय अजीब है। शायद बायनेरिज़ के जन्म से पहले लेखक Powershell के CTP संस्करण के कुछ प्रकार का उपयोग कर रहा था। : पी

अंत में, एक नए पॉवर्सशेल सत्र में अपने परीक्षण का प्रयास करें, लेकिन रिवर्स ऑर्डर में। फ़ंक्शन पहले और फ़िल्टर दूसरे या इसके विपरीत आज़माएँ:

PS C:\Users\Ryan> Measure-Command { Function AddOne { $_ + 1 }; AddOne 1 }    

TotalMilliseconds : 6.597    


PS C:\Users\Ryan> Measure-Command { Filter AddOne { $_ + 1 }; AddOne 1 }

TotalMilliseconds : 0.4055

देख? पहला जो आप चलाते हैं वह हमेशा धीमा रहेगा। यह मेमोरी में पहले से लोड किए गए सामान के .NET इंटर्नल्स के बारे में था जो कि एक फ़ंक्शन या फ़िल्टर की परवाह किए बिना, दूसरे ऑपरेशन को तेज़ बनाता है।

मैं यह स्वीकार करूंगा कि फ़ंक्शन अभी भी फ़िल्टर की तुलना में लगातार तेज़ प्रतीत होता है, भले ही वह कितनी बार चला हो।

Measure-Command { Function AddOne($Num) { Return $Num += 1 }; 1..50000 | AddOne $_ }

TotalMilliseconds : 13.9813

Measure-Command { Filter AddOne($Num) { Return $Num += 1 }; 1..50000 | AddOne $_ }

TotalMilliseconds : 69.5301

तो लेखक गलत था ... और अब मुझे पहले कभी भी फंक्शन के बजाय कभी फिल्टर का इस्तेमाल नहीं करने के लिए बुरा नहीं लगता।


4

यदि आप दोनों परीक्षणों में समान $ _ का उपयोग करते हैं तो वास्तव में अंतर बहुत छोटा है। मैंने कारण की जांच नहीं की है, लेकिन मुझे लगता है कि यह इसलिए है क्योंकि लेखक दोनों परीक्षणों में समान दृष्टिकोण का उपयोग नहीं कर रहा है। इसके अलावा, कंसोल आउटपुट परिणामों में हस्तक्षेप कर सकता है। यदि आप इन भागों को काटते हैं, तो संख्या बहुत समान है। देख:

Function AddOneFunction
{  
    process {
        $_ + 1
    }
}

Filter AddOneFilter
{ 
    $_ + 1
}

write-host "First"
Measure-Command { 1..50000 | AddOneFilter } | select totalMilliseconds
Measure-Command { 1..50000 | AddOneFilter } | select totalMilliseconds
Measure-Command { 1..50000 | AddOneFilter } | select totalMilliseconds
Measure-Command { 1..50000 | AddOneFilter } | select totalMilliseconds
Measure-Command { 1..50000 | AddOneFilter } | select totalMilliseconds

write-host "Second"
Measure-Command { 1..50000 | AddOneFunction } | select totalMilliseconds
Measure-Command { 1..50000 | AddOneFunction } | select totalMilliseconds
Measure-Command { 1..50000 | AddOneFunction } | select totalMilliseconds
Measure-Command { 1..50000 | AddOneFunction } | select totalMilliseconds
Measure-Command { 1..50000 | AddOneFunction } | select totalMilliseconds

परिणाम बहुत करीब होंगे, भले ही आप आदेशों के क्रम को बदल दें।

First

TotalMilliseconds
-----------------
        84.6742
        84.7646
        89.8603
        82.3399
        83.8195
Second
        86.8978
        87.4064
        89.304
        94.4334
        87.0135

प्रलेखन यह भी कहता है कि फिल्टर मूल रूप से केवल प्रक्रिया ब्लॉक वाले कार्यों के शॉर्टकट हैं। फ़ंक्शंस, जब तक कि एक प्रक्रिया ब्लॉक (या कुछ अन्य तकनीक जैसे कि स्वचालित चर का उपयोग करना जैसे कि $ इनपुट) के साथ निर्दिष्ट नहीं किया जाता है, एक बार चलाएं, इनपुट का उपयोग न करें और पाइपलाइन में अगले कमांड पर न जाएं।

Https://technet.microsoft.com/en-us/library/hh847829.aspx और https://technet.microsoft.com/en-us/library/hh847781.aspx पर अधिक जानकारी

हमारी साइट का प्रयोग करके, आप स्वीकार करते हैं कि आपने हमारी Cookie Policy और निजता नीति को पढ़ और समझा लिया है।
Licensed under cc by-sa 3.0 with attribution required.