मैंने अभी इस स्क्रिप्ट को पायथन 3.3 के साथ चलाने की कोशिश की है। दुर्भाग्य से यह पाइथन 2.7 के मुकाबले धीमी गति से दोगुना है।पायथन 3.3 में इतना धीमा प्रिंट क्यों है और मैं इसे कैसे ठीक कर सकता हूं?
#!/usr/bin/env python
from sys import stdin
def main():
for line in stdin:
try:
fields = line.split('"', 6)
print(fields[5])
except:
pass
if __name__ == '__main__':
main()
यहाँ परिणाम हैं:
$ time zcat access.log.gz | python3 -m cProfile ./ua.py > /dev/null
real 0m13.276s
user 0m18.977s
sys 0m0.484s
$ time zcat access.log.gz | python2 -m cProfile ./ua.py > /dev/null
real 0m6.139s
user 0m11.693s
sys 0m0.408s
रूपरेखा से पता चलता अतिरिक्त समय प्रिंट में खर्च है कि:
$ zcat access.log.gz | python3 -m cProfile ./ua.py | tail -15
Ordered by: standard name
ncalls tottime percall cumtime percall filename:lineno(function)
1 0.000 0.000 0.000 0.000 <frozen importlib._bootstrap>:1594(_handle_fromlist)
196806 0.234 0.000 0.545 0.000 codecs.py:298(decode)
1 0.000 0.000 13.598 13.598 ua.py:3(<module>)
1 4.838 4.838 13.598 13.598 ua.py:6(main)
1 0.000 0.000 13.598 13.598 {built-in method exec}
1 0.000 0.000 0.000 0.000 {built-in method hasattr}
4300456 4.726 0.000 4.726 0.000 {built-in method print}
196806 0.312 0.000 0.312 0.000 {built-in method utf_8_decode}
1 0.000 0.000 0.000 0.000 {method 'disable' of '_lsprof.Profiler' objects}
4300456 3.489 0.000 3.489 0.000 {method 'split' of 'str' objects}
$ zcat access.log.gz | python2 -m cProfile ./ua.py | tail -10
Ordered by: standard name
ncalls tottime percall cumtime percall filename:lineno(function)
1 0.000 0.000 6.573 6.573 ua.py:3(<module>)
1 3.894 3.894 6.573 6.573 ua.py:6(main)
1 0.000 0.000 0.000 0.000 {method 'disable' of '_lsprof.Profiler' objects}
4300456 2.680 0.000 2.680 0.000 {method 'split' of 'str' objects}
मैं इस भूमि के ऊपर कैसे बच सकते हैं? क्या यूटीएफ -8 के साथ कुछ करना है?
ठीक है, 'प्रिंट' अब python3 में कोई कथन नहीं है, इसलिए कुछ ओवरहेड की उम्मीद है। यह संभवतः 'sys.stdout.write' का उपयोग करके कम किया जा सकता है - या इससे भी बेहतर, पहले अपने स्ट्रिंग्स की एक सूची बनाकर और फिर' sys.stdout.writelines' का उपयोग करके, मान लें कि स्मृति कोई मुद्दा नहीं है। दोनों मामलों में, आपको 'प्रिंट' द्वारा बनाए गए न्यूलाइन को जोड़ना होगा। – l4mpi