2013-04-23 9 views
18

में फ्लोट करने के लिए कन्वर्ट करने के लिए बड़े मैं नीचे के रूप में अजगर में प्वाइजन वितरण की गणना करने की कोशिश की int:OverflowError: लंबे भी अजगर

p = math.pow(3,idx) 
depart = math.exp(-3) * p 
depart = depart/math.factorial(idx) 

IDX से 0

पर्वतमाला लेकिन मुझे मिल गया OverflowError: long int too large to convert to float

मैं प्रस्थान को float में बदलने की कोशिश की लेकिन कोई परिणाम नहीं।

+0

क्रमगुणित हो जाता है * वास्तव में * बड़े, * वास्तव में * तेज –

+1

क्या है IDX का मूल्य जब आपको यह त्रुटि मारा? – Pyrce

+0

जब आप एक भाज्य की गणना करना चाहते हैं, की गणना यह लघुगणक है बजाय – zehelvion

उत्तर

3

दशमलव लाइब्रेरी का उपयोग करने का प्रयास करें। यह मनमाने ढंग से सटीकता का समर्थन करने का दावा करता है।
from decimal import Decimal

इसके अलावा, आपको math.pow का उपयोग करने की आवश्यकता नहीं है। pow इन-बिल्ट है।

+0

हाय लोग मैं दशमलव या scipy का उपयोग करने की कोशिश की, लेकिन मैं ImportError मिला: नहीं मॉड्यूल नामित scipy.stats दशमलव – user2312186

+0

के लिए एक ही त्रुटि कौन-सा संस्करण आप कर रहे हैं चल रहा है? 'दशमलव' लाइब्रेरी सभी के लिए मानक माना जाता है। शायद आपने इसे हटा दिया है। पायथन पुनः स्थापित करें और यह इसे ठीक करेगा। scipy के लिए, यह एक तृतीय पक्ष पैकेज है, इसलिए आपको इसे scipy.org से डाउनलोड करना होगा – xylon97

+0

मैंने scipy स्थापित किया है और यह अच्छी तरह से काम करता है – user2312186

21

factorials मिल बड़े असली तेजी से:

>>> math.factorial(170) 
7257415615307998967396728211129263114716991681296451376543577798900561843401706157852350749242617459511490991237838520776666022565442753025328900773207510902400430280058295603966612599658257104398558294257568966313439612262571094946806711205568880457193340212661452800000000000000000000000000000000000000000L 

नोट L; 170 के भाज्य अभी भी एक नाव को convertable है:

>>> float(math.factorial(170)) 
7.257415615307999e+306 

लेकिन अगले भाज्य बहुत बड़ी है:

>>> float(math.factorial(171)) 
Traceback (most recent call last): 
    File "<stdin>", line 1, in <module> 
OverflowError: long int too large to convert to float 

आप decimal module इस्तेमाल कर सकते हैं; गणना धीमी हो जाएगी, लेकिन Decimal() वर्ग factorials इस आकार संभाल कर सकते हैं:

>>> from decimal import Decimal 
>>> Decimal(math.factorial(171)) 
Decimal('1241018070217667823424840524103103992616605577501693185388951803611996075221691752992751978120487585576464959501670387052809889858690710767331242032218484364310473577889968548278290754541561964852153468318044293239598173696899657235903947616152278558180061176365108428800000000000000000000000000000000000000000') 

आप भर Decimal() मूल्यों का उपयोग करना होगा:

from decimal import * 

with localcontext() as ctx: 
    ctx.prec = 32 # desired precision 
    p = ctx.power(3, idx) 
    depart = ctx.exp(-3) * p 
    depart /= math.factorial(idx) 
+0

पायथन में बड़ी संख्या में वर्ग क्या कहा जाता है? क्योंकि '170! '64-बिट पूर्णांक की सीमा से ऊपर है। मुझे लगता है कि उस प्रकार के लिए मजबूर किया गया है? यदि हां, तो 'एल' अभी भी अंत में क्यों जुड़ा हुआ है? –

+1

@HunterMcMillen: पायथन लंबे पूर्णांक केवल ओएस मेमोरी आवंटन द्वारा ही सीमित हैं। 'एल' का संकेत है कि हम मंच के लिए अधिकतम सी पूर्णांक आकार (मेरे मामले में 64-बिट) से आगे बढ़ने के लिए लंबे पूर्णांक का उपयोग किया जा रहा है; संक्रमण स्वचालित है। Http://docs.python.org/2/library/stdtypes.html#numeric-types-int-float-long-complex –

+0

अहह, मैं देखता हूं। अधिकांश अन्य भाषाओं में 'बिगइंटर' या कुछ समान होता है। धन्यवाद। –

4

जब IDX बड़े या तो math.pow और/या हो जाता है math.factorial बेहद बड़ा हो जाएगा और एक फ़्लोटिंग वैल्यू में परिवर्तित करने में असमर्थ होगा (idx=1000 मेरी 64 बिट मशीन पर त्रुटि को ट्रिगर करता है)। आप math.pow फ़ंक्शन का उपयोग नहीं करना चाहेंगे क्योंकि यह ** ऑपरेटर में निर्मित की तुलना में पहले बहती है क्योंकि यह पहले फ़्लोट कनवर्ट करके उच्च परिशुद्धता रखने की कोशिश करता है। इसके अतिरिक्त आप उच्च परिशुद्धता के लिए Decimal ऑब्जेक्ट में प्रत्येक फ़ंक्शन कॉल को लपेट सकते हैं।

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

3 ** idx => math.log(3) * idx 
math.exp(-3) * p => -3 + math.log(p) 
math.factorial(idx) => sum(math.log(ii) for ii in range(1, idx)) 
... 
math.exp(result) 

यह जब तक लॉग डोमेन रहता है बहुत तो अंत अपने संख्या बहुत, बहुत बड़ी प्राप्त कर सकते हैं इससे पहले कि आप अतिप्रवाह समस्याओं मारा जाएगा।

+0

मुझे लगता है कि '3 ** idx => math.log (3) * math.log (idx)' 3 ** idx => math.log (3) * idx' –

+0

ऑप्स होना चाहिए, हाँ आप सही हैं। 'Scipy.stats' के लिए – Pyrce

0

scipy मॉड्यूल आपकी मदद कर सकता है।

scipy.misc.factorial एक फैक्टोरियल फ़ंक्शन है जो फैक्टोरियल की गणना करने के लिए गामा फ़ंक्शन सन्निकटन का उपयोग कर सकता है, और फ्लोटिंग पॉइंट्स का उपयोग करके परिणाम देता है।

import numpy 
from scipy.misc import factorial 

i = numpy.arange(10) 
print(numpy.exp(-3) * 3**i/factorial(i)) 

देता है:

[ 0.04978707 0.14936121 0.22404181 0.22404181 0.16803136 0.10081881 
    0.05040941 0.02160403 0.00810151 0.0027005 ] 

भी एक module to calculate Poisson distributions नहीं है। उदाहरण के लिए:

import numpy 
from scipy.stats import poisson 

i = numpy.arange(10) 
p = poisson(3) 
print(p.pmf(i)) 

देता है:

[ 0.04978707 0.14936121 0.22404181 0.22404181 0.16803136 0.10081881 
    0.05040941 0.02160403 0.00810151 0.0027005 ] 
+0

+1, लेकिन फैक्टोरियल फ़ंक्शन scipy ऑफ़र अभी भी बड़े तर्क पर 'inf' बाहर होगा। – DSM

+0

धन्यवाद। मैं नेटवर्क में पैकेट समय उत्पन्न करने के रूप में पोइसन संख्या उत्पन्न करने जा रहा हूं। मैं लगातार प्रत्येक पोइसन संख्या उत्पन्न करने के लिए इस फ़ंक्शन का उपयोग कैसे कर सकता हूं? – user2312186

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