2012-06-06 17 views
30

पायथन के मूल sum फ़ंक्शन और NumPy के numpy.sum का उपयोग करने के बीच प्रदर्शन और व्यवहार में अंतर क्या हैं? sum न्यूमपी के सरणी पर काम करता है और numpy.sum पाइथन सूचियों पर काम करता है और वे दोनों एक ही प्रभावी परिणाम (ओवरफ्लो जैसे किनारे के मामलों का परीक्षण नहीं किया है) लेकिन विभिन्न प्रकारों का परीक्षण करते हैं।पायथन का योग बनाम NumPy's numpy.sum

>>> import numpy as np 
>>> np_a = np.array(range(5)) 
>>> np_a 
array([0, 1, 2, 3, 4]) 
>>> type(np_a) 
<class 'numpy.ndarray') 

>>> py_a = list(range(5)) 
>>> py_a 
[0, 1, 2, 3, 4] 
>>> type(py_a) 
<class 'list'> 

# The numerical answer (10) is the same for the following sums: 
>>> type(np.sum(np_a)) 
<class 'numpy.int32'> 
>>> type(sum(np_a)) 
<class 'numpy.int32'> 
>>> type(np.sum(py_a)) 
<class 'numpy.int32'> 
>>> type(sum(py_a)) 
<class 'int'> 

संपादित करें: मैं अपने व्यावहारिक प्रश्न यहाँ लगता है अजगर पूर्णांकों की एक सूची पर numpy.sum का उपयोग करके करते है किसी भी अजगर की अपनी sum का उपयोग कर से अधिक तेजी से हो सकता है?

इसके अतिरिक्त, एक पाइथन पूर्णांक बनाम स्केलर numpy.int32 के उपयोग के प्रभाव (प्रदर्शन सहित) क्या हैं? उदाहरण के लिए, a += 1 के लिए, क्या कोई व्यवहार या प्रदर्शन अंतर है यदि a का प्रकार एक पायथन पूर्णांक या numpy.int32 है? अगर मैं पाइथन कोड में बहुत कुछ जोड़ा या घटाया गया है, तो numpy.int32 जैसे न्यूमपी स्केलर डेटाटाइप का उपयोग करना तेज़ है।

स्पष्टीकरण के लिए, मैं जैव सूचना विज्ञान सिमुलेशन पर काम कर रहा हूं जिसमें आंशिक रूप से बहुआयामी numpy.ndarray एस को एकल स्केलर रकम में गिरने के बाद शामिल किया जाता है जिसे बाद में संसाधित किया जाता है। मैं पाइथन 3.2 और न्यूपी 1.6 का उपयोग कर रहा हूं।

अग्रिम धन्यवाद!

उत्तर

42

मुझे उत्सुकता और समय लगता है। numpy.sum numpy arrays के लिए बहुत तेज लगता है, लेकिन सूचियों पर बहुत धीमी है।

import numpy as np 
import timeit 

x = range(1000) 
# or 
#x = np.random.standard_normal(1000) 

def pure_sum(): 
    return sum(x) 

def numpy_sum(): 
    return np.sum(x) 

n = 10000 

t1 = timeit.timeit(pure_sum, number = n) 
print 'Pure Python Sum:', t1 
t2 = timeit.timeit(numpy_sum, number = n) 
print 'Numpy Sum:', t2 

परिणाम जब x = range(1000):

Pure Python Sum: 0.445913167735 
Numpy Sum: 8.54926219673 

परिणाम जब x = np.random.standard_normal(1000):

Pure Python Sum: 12.1442425643 
Numpy Sum: 0.303303771848 

मैं अजगर 2.7.2 और Numpy 1.6.1

+0

+1, लेकिन क्या आपके पास ये परिणाम पीछे नहीं हैं? – dawg

+0

@ ड्रेक, हाँ, मैंने उन्हें पीछे की तरफ देखा था। इस बारे में बताने के लिए शुक्रिया! फिक्स्ड। – Akavall

+0

'np.array' का उपयोग करते समय आप तेजी से' np.sum' के बारे में सही हैं। लेकिन यदि आप समय 'np.sum (np.array ऑब्जेक्ट)' और 'योग (सूची वस्तु) 'करते हैं, तो दोनों लगभग समान प्रदर्शन करते हैं। – xyres

5

नम्पी बहुत तेज होना चाहिए, खासकर जब आपका डेटा पहले से ही एक सुस्त सरणी है।

गूंगा सरणी मानक सी सरणी पर एक पतली परत होती है। जब numpy sum इस पर पुनरावृत्त करता है, यह टाइपिंग नहीं कर रहा है और यह बहुत तेज़ है। मानक सी

तुलनात्मक रूप से ऑपरेशन करने के लिए तुलना की तुलना की जा सकती है तुलनात्मक रूप से, पाइथन की राशि का उपयोग करके इसे पहले नमस्ते सरणी को एक पायथन सरणी में परिवर्तित करना होगा, और फिर उस सरणी पर फिर से चालू करना होगा। इसे कुछ प्रकार की जांच करना है और आम तौर पर धीमा होने वाला है।

सटीक राशि जो कि पाइथन योग numpy sum से धीमी है, अच्छी तरह से परिभाषित नहीं है क्योंकि पायथन योग कुछ हद तक अनुकूलित फ़ंक्शन होने जा रहा है जैसा कि आपके स्वयं के योग फ़ंक्शन को पाइथन में लिखने की तुलना में किया जाता है।

+5

यह numpy सरणी 'कन्वर्ट' नहीं करता है - एक numpy सरणी पहले से ही Python में पुन: प्रयोज्य है। दूसरी ओर, 'numpy.sum' को एक सूची को एक numpy सरणी में परिवर्तित करना पड़ सकता है, जो @ Akavall के समय के परिणामों की व्याख्या करेगा। –

+1

भले ही रूपांतरण सरणी के सरणी के रूप में होता है या अलग-अलग आइटम टाइप करके, आप कुछ स्तर पर आइटम (मूल प्रकार से/मूल प्रकार) को परिवर्तित कर सकते हैं, और यही वह बिंदु था जिसे मैं बनाने की कोशिश कर रहा था। – Claris

3

नोट का उपयोग कर रहा है कि अजगर पर योग बहुआयामी numpy arrays केवल पहली धुरी के साथ एक योग करेगा:

sum(np.array([[[2,3,4],[4,5,6]],[[7,8,9],[10,11,12]]])) 
Out[47]: 
array([[ 9, 11, 13], 
     [14, 16, 18]]) 

np.sum(np.array([[[2,3,4],[4,5,6]],[[7,8,9],[10,11,12]]]), axis=0) 
Out[48]: 
array([[ 9, 11, 13], 
     [14, 16, 18]]) 

np.sum(np.array([[[2,3,4],[4,5,6]],[[7,8,9],[10,11,12]]])) 
Out[49]: 81 
1

यह answer post above by Akavall का विस्तार है। उस उत्तर से आप देख सकते हैं कि np.sumnp.array ऑब्जेक्ट्स के लिए तेज़ प्रदर्शन करता है, जबकि sumlist ऑब्जेक्ट्स के लिए तेज़ प्रदर्शन करता है।एक np.array वस्तु बनाम के लिए np.sum चल पर

: कि उनका विस्तार करनाsumlist ऑब्जेक्ट के लिए, ऐसा लगता है कि वे गर्दन में गर्दन करते हैं।

# I'm running IPython 

In [1]: x = range(1000) # list object 

In [2]: y = np.array(x) # np.array object 

In [3]: %timeit sum(x) 
100000 loops, best of 3: 14.1 µs per loop 

In [4]: %timeit np.sum(y) 
100000 loops, best of 3: 14.3 µs per loop 

ऊपर, sum हालांकि, कई बार मैंने np.sum समय देखा है 14.1 µs भी हो सकता है, एक छोटे बिट np.array से तेज है। लेकिन ज्यादातर, यह 14.3 µs है।

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