Jump to content

Yay (not really) found a bug in Python

Go to solution Solved by madknight3,

Seems like it's just regular floating point precision that most every language has to deal with.

So to learn python I've been using Think Python. And this one exercise just made it break.

 

The exercise:

Exercise 7.3. To test the square root algorithm in this chapter, you could compare it with
math.sqrt. Write a function named test_square_root that prints a table like this:
1.0 1.0 1.0 0.0
2.0 1.41421356237 1.41421356237 2.22044604925e-16
3.0 1.73205080757 1.73205080757 0.0
4.0 2.0 2.0 0.0
5.0 2.2360679775 2.2360679775 0.0
6.0 2.44948974278 2.44948974278 0.0
7.0 2.64575131106 2.64575131106 0.0
8.0 2.82842712475 2.82842712475 4.4408920985e-16
9.0 3.0 3.0 0.0
The first column is a number, a; the second column is the square root of a computed with the function
from Section 7.5; the third column is the square root computed by math.sqrt; the fourth column is
the absolute value of the difference between the two estimates.
def tsr(a):    from math import sqrt #used later in the function    x = a    y = (x + a / x) / 2    while abs(y - x) > 0.000001: #loop that approximates square roots        x = y        y = (x + a / x) / 2    b = y    c = sqrt(a) #uses built in square root function    d = abs(b-c) #finds difference between approximation and sqrt function    print a, b, c, dtsr(4.0)tsr(5.0)

all numbers besides 4 and 5 work, so those are the only ones I included.

 

For the output, the last number in each line is super broken

 

Output:

4.0 2.0 2.0 2.22044604925e-15
5.0 2.2360679775 2.2360679775 1.88293824976e-13

 

I was going to ask for help as I was stumped but I realized that Python kinda just broke.

CPU: AMD FX-6300 4GHz @ 1.3 volts | CPU Cooler: Cooler Master Hyper 212 EVO | RAM: 8GB DDR3

Motherboard: Gigabyte 970A-DS3P | GPU: EVGA GTX 960 SSC | SSD: 250GB Samsung 850 EVO

HDD: 1TB WD Caviar Green | Case: Fractal Design Core 2500 | OS: Windows 10 Home

Link to comment
https://linustechtips.com/topic/316352-yay-not-really-found-a-bug-in-python/
Share on other sites

Link to post
Share on other sites

In 99% of cases if the output isn't right either you've done something wrong or you're reading the output wrong like in this case. There are very few bugs in the more mainstream programming languages and those bugs that exist will be in the more obscure features.

Link to post
Share on other sites

Seems fine to me. How do you know it broke?

d finds the difference between b and c which have the same values so d should be equal to 0

 

are floating point precision problems like this normal?

CPU: AMD FX-6300 4GHz @ 1.3 volts | CPU Cooler: Cooler Master Hyper 212 EVO | RAM: 8GB DDR3

Motherboard: Gigabyte 970A-DS3P | GPU: EVGA GTX 960 SSC | SSD: 250GB Samsung 850 EVO

HDD: 1TB WD Caviar Green | Case: Fractal Design Core 2500 | OS: Windows 10 Home

Link to post
Share on other sites

Seems like it's just regular floating point precision that most every language has to deal with.

So this is normal?

CPU: AMD FX-6300 4GHz @ 1.3 volts | CPU Cooler: Cooler Master Hyper 212 EVO | RAM: 8GB DDR3

Motherboard: Gigabyte 970A-DS3P | GPU: EVGA GTX 960 SSC | SSD: 250GB Samsung 850 EVO

HDD: 1TB WD Caviar Green | Case: Fractal Design Core 2500 | OS: Windows 10 Home

Link to post
Share on other sites

Yeah, here's some more information on the topic. Many languages will have a specific type that allows for accurate decimal representation at the cost of some speed.

Thanks for the helpful info

CPU: AMD FX-6300 4GHz @ 1.3 volts | CPU Cooler: Cooler Master Hyper 212 EVO | RAM: 8GB DDR3

Motherboard: Gigabyte 970A-DS3P | GPU: EVGA GTX 960 SSC | SSD: 250GB Samsung 850 EVO

HDD: 1TB WD Caviar Green | Case: Fractal Design Core 2500 | OS: Windows 10 Home

Link to post
Share on other sites

Thanks for the helpful info

No problem. And I forgot to link Python's decimal class so here it is.

 

You only need to use this if you want precision though. As mentioned, it's a fair bit slower. Many times regular floating point numbers is fine with a "tolerance" check for equality. A "tolerance" is a value that checks if things are "close enough". Basically what your code did in the while loop.

Link to post
Share on other sites

Create an account or sign in to comment

You need to be a member in order to leave a comment

Create an account

Sign up for a new account in our community. It's easy!

Register a new account

Sign in

Already have an account? Sign in here.

Sign In Now

×