Re: [Tutor] very odd math problem
Am 11.03.2011 06:05, schrieb Steven D'Aprano: Alex Hall wrote: Hi all, I am trying to get a list of ordered pairs from the below function. In my code, evaluate is more exciting, but the evaluate here will at least let this run. The below runs fine, with one exception: somehow, it is saying that -2+2.0 is 4.x, where x is a huge decimal involving E-16 (in other words, a really tiny number). Does anyone have any idea what is going on here? Let's reword the description of the problem... "2.0 - 2 is a really tiny number close to 4e-16" Welcome to the wonders of floating point maths! Repeat after me: Floats are not real numbers... floats are not real numbers... floats are not real numbers... everything you learned about arithmetic in school only *approximately* applies to floats. Half :) and half :( First off, anything involving e-16 isn't a "huge decimal", it's a tiny decimal, very close to zero, no matter what the x is: 0.0004x Also, although you say "-2 + 2.0" in a comment, that's not actually what you calculate. I know this even though I don't know what you calculate, because I can test -2 + 2.0 and see that it is exactly zero: >>> -2 + 2.0 == 0 True Somewhere in your calculation you're probably calculating something which *looks* like 2.0 but isn't. Here's an example: >>> x = 2 + 1e-14 >>> print(x) 2.0 >>> x == 2.0 False but you can see the difference by printing the float with more decimal places than shown by the default view: >>> repr(x) '2.01' Another problem: you calculate your values by repeated addition. This is the wrong way to do it, because each addition has a tiny little error, and repeating them just compounds error upon error. Here's an example: >>> x = 0.0 >>> for i in range(10): ... x += 0.1 ... >>> x == 1.0 False >>> print(x) 1.0 >>> repr(x) '0.99989' The right way is to do it like this: >>> x = 0.0 >>> for i in range(1, 11): ... x = i*0.1 ... >>> x == 1.0 True This ensures that errors don't compound. Some further resources: http://floating-point-gui.de/ http://introcs.cs.princeton.edu/91float/ David Goldberg used to have a fantastic (although quite technical) discussion of floating point issues, "What Every Computer Scientist Should Know About Floating-Point Arithmetic": http://docs.sun.com/source/806-3568/ncg_goldberg.html Unfortunately, since Oracle bought Sun, they've removed the article. Bastards. If you can find a copy of Apple's old "Apple Numeric Manual" (2nd Edition), it has a fantastic introduction by William Kahan. Even though the book is about Apple's SANE, a lot will apply to other floating point systems as well. Google on William Kahan and read his stuff :) Damn, you're fast!! ;-)) ___ Tutor maillist - Tutor@python.org To unsubscribe or change subscription options: http://mail.python.org/mailman/listinfo/tutor
Re: [Tutor] very odd math problem
Am 11.03.2011 04:23, schrieb Alex Hall: Hi all, I am trying to get a list of ordered pairs from the below function. In my code, evaluate is more exciting, but the evaluate here will at least let this run. The below runs fine, with one exception: somehow, it is saying that -2+2.0 is 4.x, where x is a huge decimal involving E-16 (in other words, a really tiny number). Does anyone have any idea what is going on here? You can find some great posts at a thread about decimal floating point numbers some weeks ago for background reading. Or (and) look at this: http://docs.python.org/tutorial/floatingpoint.html#floating-point-arithmetic-issues-and-limitations Now my guess is: i is calculated as a sum of floats of step 0.1. That means you have in the base 2 representation an approximation of 0.1, not "exactly" 0.1, but something like 0.10123123. When i reaches approximately 2.0, it is actually 2.0342374 (or what ever). On the other hand, e1 can be represented precisely if it's 2.0 in the base 2 representation. But the sum of e1 and i is actually your tiny number. That's why 2.0 - 2.0 is exactly 0.0, but (20*0.1 - 2.0 is not). To elaborate, you could add some lines to your code: def getCoords(f, e1, e2, step=.1): time=0 i=0 coords=[] while time<=e2: print "time="+str(e1)+"+"+str(i)+"=" print type(e1) print type(i) time=e1+i time_2 = e1 + e2 print "%s, %.24f" % (time, time) # app 0.0 print "%s, %.24f" % (time_2, time_2) # exact 0.0 coords.append((time, evaluate(f, time))) i=i+1*step return coords The reason why Python prints i as 2.0 in the first print statement is probably due to some internal auto-rounding when using str(). See the last paragraph of the link above. No idea, what's exactly going on under the hood. HTH, Jan def getCoords(f, e1, e2, step=.1): #returns a list of (x,y) tuples from e1 to e2 at the given accuracy (step) time=0 i=0 coords=[] while time<=e2: print "time="+str(e1)+"+"+str(i)+"=" time=e1+i print time #watch this line when above is -2+2.0 coords.append((time, evaluate(f, time))) i=i+1*step return coords def evaluate(x,y): return x*y ___ Tutor maillist - Tutor@python.org To unsubscribe or change subscription options: http://mail.python.org/mailman/listinfo/tutor
Re: [Tutor] very odd math problem
Alex Hall wrote: Hi all, I am trying to get a list of ordered pairs from the below function. In my code, evaluate is more exciting, but the evaluate here will at least let this run. The below runs fine, with one exception: somehow, it is saying that -2+2.0 is 4.x, where x is a huge decimal involving E-16 (in other words, a really tiny number). Does anyone have any idea what is going on here? Let's reword the description of the problem... "2.0 - 2 is a really tiny number close to 4e-16" Welcome to the wonders of floating point maths! Repeat after me: Floats are not real numbers... floats are not real numbers... floats are not real numbers... everything you learned about arithmetic in school only *approximately* applies to floats. Half :) and half :( First off, anything involving e-16 isn't a "huge decimal", it's a tiny decimal, very close to zero, no matter what the x is: 0.0004x Also, although you say "-2 + 2.0" in a comment, that's not actually what you calculate. I know this even though I don't know what you calculate, because I can test -2 + 2.0 and see that it is exactly zero: >>> -2 + 2.0 == 0 True Somewhere in your calculation you're probably calculating something which *looks* like 2.0 but isn't. Here's an example: >>> x = 2 + 1e-14 >>> print(x) 2.0 >>> x == 2.0 False but you can see the difference by printing the float with more decimal places than shown by the default view: >>> repr(x) '2.01' Another problem: you calculate your values by repeated addition. This is the wrong way to do it, because each addition has a tiny little error, and repeating them just compounds error upon error. Here's an example: >>> x = 0.0 >>> for i in range(10): ... x += 0.1 ... >>> x == 1.0 False >>> print(x) 1.0 >>> repr(x) '0.99989' The right way is to do it like this: >>> x = 0.0 >>> for i in range(1, 11): ... x = i*0.1 ... >>> x == 1.0 True This ensures that errors don't compound. Some further resources: http://floating-point-gui.de/ http://introcs.cs.princeton.edu/91float/ David Goldberg used to have a fantastic (although quite technical) discussion of floating point issues, "What Every Computer Scientist Should Know About Floating-Point Arithmetic": http://docs.sun.com/source/806-3568/ncg_goldberg.html Unfortunately, since Oracle bought Sun, they've removed the article. Bastards. If you can find a copy of Apple's old "Apple Numeric Manual" (2nd Edition), it has a fantastic introduction by William Kahan. Even though the book is about Apple's SANE, a lot will apply to other floating point systems as well. Google on William Kahan and read his stuff :) -- Steven ___ Tutor maillist - Tutor@python.org To unsubscribe or change subscription options: http://mail.python.org/mailman/listinfo/tutor
[Tutor] very odd math problem
Hi all, I am trying to get a list of ordered pairs from the below function. In my code, evaluate is more exciting, but the evaluate here will at least let this run. The below runs fine, with one exception: somehow, it is saying that -2+2.0 is 4.x, where x is a huge decimal involving E-16 (in other words, a really tiny number). Does anyone have any idea what is going on here? def getCoords(f, e1, e2, step=.1): #returns a list of (x,y) tuples from e1 to e2 at the given accuracy (step) time=0 i=0 coords=[] while time<=e2: print "time="+str(e1)+"+"+str(i)+"=" time=e1+i print time #watch this line when above is -2+2.0 coords.append((time, evaluate(f, time))) i=i+1*step return coords def evaluate(x,y): return x*y -- Have a great day, Alex (msg sent from GMail website) mehg...@gmail.com; http://www.facebook.com/mehgcap ___ Tutor maillist - Tutor@python.org To unsubscribe or change subscription options: http://mail.python.org/mailman/listinfo/tutor
Re: [Tutor] Need help with dates in Python
Hi All: Thanks for all of your answers. I could solve this problem using strptime (datetime.datetime.strptime(dt1, '%Y-%m-%d') and correct indentation. As I am new to python programming, I don't know how to use classes yet, still learning. Thanks, Sree. --- On Thu, 3/10/11, James Reynolds wrote: From: James Reynolds Subject: Re: [Tutor] Need help with dates in Python To: "nookasree ponamala" Cc: "Andre Engels" , tutor@python.org Date: Thursday, March 10, 2011, 2:26 AM On Wed, Mar 9, 2011 at 1:34 PM, nookasree ponamala wrote: Hi, I'm new to Python programming. I've changed the code to below, but still it is not working, Could you pls. make the corrections in my code. import datetime t = () tot = [] min = datetime.date(2008, 1, 1) max = datetime.date(2012, 12, 31) for line in open ('test2.txt','r'): data = line.rstrip().split() a = data[9] b = data[4] (year, month, day) = b.split('-') year = int(year) month = int(month) day = int(day) t = (year,month,day) if t < max: maxyr = max if t > min: minyr = min t = (a,b,maxyr,minyr) tot.append(t) print t Thanks Sree. --- On Wed, 3/9/11, Andre Engels wrote: > From: Andre Engels > Subject: Re: [Tutor] Need help with dates in Python > To: "nookasree ponamala" > Cc: tutor@python.org > Date: Wednesday, March 9, 2011, 2:16 PM > On Wed, Mar 9, 2011 at 9:21 AM, > nookasree ponamala > wrote: > > Hi, > > > > I need help in finding the minimum date and maximum > date in a file. > > Here is my test file: > > s.no: dt1 amt id1 id2 > > 452 2010-02-20 $23.26 059542 > 06107 > > 452 2010-02-05 $20.78 059542 > 06107 > > 451 2010-02-24 $5.99 059542 > 20151 > > 452 2010-02-12 $114.25 839745 > 98101 > > 452 2010-02-06 $28.00 839745 > 06032 > > 451 2010-02-12 $57.00 839745 > 06269 > > > > I want to get the minimum and maximum dt1 for each > id1 > > > > Required result: > > > > id1 mindate maxdate > > 059542 2010-02-24 2010-02-20 > > 839745 2010-02-06 2010-02-12 > > > > Code: The code I tried. It doesn't work though. > > > > import sys > > import os > > t = () > > tot = [] > > maxyr = 2012 > > minyr = 2008 > > maxday = 31 > > minday = 1 > > maxmon = 12 > > minmon = 1 > > > > for line in open ('test2.txt','r'): > > data = line.rstrip().split() > > a = data[3] > > b = data[1] > > (year, month, day) = b.split('-') > > year = int(year) > > month = int(month) > > day = int(day) > > if year > maxyr: > > maxyr = year > > elif year < minyr: > > minyr = year > > if month > maxmon: > > maxmon = month > > elif month < minmon: > > minmon = month > > if day > maxday: > > maxday = day > > elif day < minday: > > minday = day > > max = (maxyr,maxmon,maxday) > > min = (minyr,minmon,minday) > > t = (a,b,max,min) > > tot.append(t) > > print t > > > > Could you pls. help me with this. > > I see several things go wrong. Here a list, which may well > not be complete: > > * You want the mindate and maxdate for each id1, but you > remember only > a single minyr, maxyr etcetera. There's no way that that is > going to > work. > * You initialize minyr etcetera to a date before the first > date you > will see, nd maxyr etcetera to a date after the last date. > This means > that you will never find an earlier respectively later one, > so they > would never be changed. You should do it exactly the other > way around > - minyr etcetera should be _later_ than any date that may > occur, maxyr > etcetera _earlier_. > * You move "if year > maxyr" back to the left. This > means that it is > not part of the loop, but is executed (only) once _after_ > the loop has > been gone through > * year < minyear should be "if", not "elif": it is > possible that the > new date is both the first _and_ the last date that has > been found > (this will be the case with the first date) > * You change maxyear, maxmonth and maxday independently. > That is not > what you are trying to do - you want the last date, not the > highest > year, highest month and highest day (if the dates were > 2001-12-01, > 2011-11-03 and 2005-05-30, you want the maximum date to be > 2011-11-03, > not 2011-12-30). You should thus find a way to compare the > *complete > date* and then if it is later than the maxdate or earlier > than the > mindate change the *complete date* > * At the end you show (well, in this case you don't because > it is > under "if month > maxmon") a quadruple consisting of > id1, current > date, lowest date and highest date - EACH time. You want > only the > triple and only after the last date of some value of id1 > has been > parsed (best to do that
Re: [Tutor] Need help with dates in Python
On 09/03/2011 9.21, nookasree ponamala wrote: Hi, I need help in finding the minimum date and maximum date in a file. Here is my test file: s.no: dt1 amt id1 id2 452 2010-02-20 $23.26 05954206107 452 2010-02-05 $20.78 05954206107 451 2010-02-24 $5.99 05954220151 452 2010-02-12 $114.25 83974598101 452 2010-02-06 $28.00 83974506032 451 2010-02-12 $57.00 83974506269 I want to get the minimum and maximum dt1 for each id1 Required result: id1 mindate maxdate 059542 2010-02-24 2010-02-20 839745 2010-02-06 2010-02-12 Code: The code I tried. It doesn't work though. I noticed that your dates are formatted in a way that makes it easy to compare them as strings. This allows you not only to do without splitting dates into year, month and day, but also to do without the datetime module: I'm also, AFAIK, the first one to address your need for the min and max date FOR EACH ID1, not in the whole file. .ids = {} # create an empty dictionary to store results .for L in open("test.txt", "r"): . S = L.split() # allow direct access to fields . if S[3] in ids: .mindate, maxdate = ids[S[3]] # current stored minimum and maximum date .if S[1] < mindate: . mindate = S[1] .if S[1] > maxdate: . maxdate = S[1] .ids[S[3]] = (mindate, maxdate) # new stored min and max . else: .ids[S[3]] = (S[1], S[1]) # initialize storage for the current id1, with min and max in a tuple .#leave print formatting as an exercise to the reader (but you can do without it!) .print ids Hope this helps... Francesco - Nessun virus nel messaggio. Controllato da AVG - www.avg.com Versione: 10.0.1204 / Database dei virus: 1497/3495 - Data di rilascio: 09/03/2011 ___ Tutor maillist - Tutor@python.org To unsubscribe or change subscription options: http://mail.python.org/mailman/listinfo/tutor
Re: [Tutor] How to sum weighted matrices
Numpy apart, you can use lists and loops: >>> matrix = [[1, 2, 3], [4, 5, 6], [7, 8, 9]] >>> matrix2 = [[3, 2, 1], [6, 5, 4], [9, 8, 7]] >>> result = [] >>> w = [1, 2] >>> for x in range(len(matrix)): row = [] for y in range(len(matrix[x])): row.append((w[0]*matrix[x][y])+(w[1]*matrix2[x][y])) result.append(row) >>> result [[7, 6, 5], [16, 15, 14], [25, 24, 23]] >>> But I think this isn't pythonic way, so maybe someone else can help you 2011/3/7 shu wei > Hello all, > > I am new to python and numpy. > My question is how to sum up N weighted matrices. > For example w=[1,2] (N=2 case) > m1=[1 2 3, >3 4 5] > > m2=[3 4 5, >4 5 6] > I want to get a matrix Y=w[1]*m1+w[2]*m2 by using a loop. > > My original problem is like this > X=[1 2 3, > 3 4 5, > 4 5 6] > > a1=[1 2 3] 1st row of X > m1=a1'*a1 a matirx > a2=[3 4 5] 2nd row of X > m2=a2'*a2 > a3=[ 4 5 6] 3rd row of X > m3=a3'*a3 > > I want to get Y1=w[1]*m1+w[2]*m2 > Y2=w[1]*m2+w[2]*m3 > So basically it is rolling and to sum up the weighted matries > I have a big X, the rolling window is relatively small. > > I tried to use > > sq=np.array([x[i].reshape(-1,1)*x[i] for i in np.arange(0,len(x)]) # > s=len(x) > m=np.array([sq[i:i+t] for i in np.arange(0,s-t+1)]) # t is the len(w) > > then I was stuck, I tried to use a loop somethig like > Y=np.array([np.sum(w[i]*m[j,i],axis=0) for i in np.arange(0,t)] ) > Any suggestion is welcome. > > sue > ___ > Tutor maillist - Tutor@python.org > To unsubscribe or change subscription options: > http://mail.python.org/mailman/listinfo/tutor > > ___ Tutor maillist - Tutor@python.org To unsubscribe or change subscription options: http://mail.python.org/mailman/listinfo/tutor
Re: [Tutor] PyQuery
pseudo: for line in file: query = {} columnheader = line[0] headercontent = line[1] query[columnheader] = [header1content] ___ Tutor maillist - Tutor@python.org To unsubscribe or change subscription options: http://mail.python.org/mailman/listinfo/tutor