# Scientific Computing with Python Projects - Probability Calculator

### Tell us what’s happening:

Hi,
I’ve managed to get my code to pass the first two tests but not the third. However, it seems to me that it does what the description asks. When I run the numbers given in the example in the description it gives a similar number (normally around 0.368).
Any explanation as to why it’s failing the last test would be appreciated.

import copy
import random

drawn_dict = {}

class Hat():
def __init__(self, **colours):
self.total = 0
vals = []
self.contents = []
index = 0
for value in colours.values():
vals.append(value)
self.total += value
for colour in colours:
count = 0
index += 1
while count < vals[index - 1]:
self.contents.append(colour)
count += 1
def draw(self, no):
count1 = 0
balls_drawn = []
remaining_balls = []
if no > self.total:
return self.contents
else:
while count1 < no:
balls_drawn.append(self.contents.pop(random.randrange(len(self.contents))))
count1 += 1
for ball in self.contents:
remaining_balls.append(ball)
for ball in balls_drawn:
if ball not in drawn_dict:
drawn_dict[ball] = [ball]
self.contents.append(ball)
else:
drawn_dict[ball].append(ball)
self.contents.append(ball)
return remaining_balls

def experiment(hat, expected_balls, num_balls_drawn, num_experiments):
count2 = 0
M = 0
while count2 < num_experiments:
drawn_dict.clear()
hat.draw(num_balls_drawn)
count3 = 0
for key in expected_balls.keys():
if key in drawn_dict.keys():
check = len(drawn_dict[key])
if expected_balls[key] == check:
count3 += 1
else:
count3 -= 10000
else:
count3 -= 10000
if count3 > 0:
M += 1
else:
pass
count2 += 1
probs = M / num_experiments
print(probs)

User Agent is: Mozilla/5.0 (X11; CrOS x86_64 14541.0.0) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/122.0.0.0 Safari/537.36

### Challenge Information:

Scientific Computing with Python Projects - Probability Calculator

Consider a following case:

• Expected balls are: ‘blue’: 2, ‘green’: 1
• Drawn are: [‘green’, ‘blue’, ‘blue’, ‘blue’]

Does this count as successful experiment or not? What code does for such case?

There’s one more issue with how draw method handles case when there’s more balls to draw than the number of balls in hat. The peculiar way of handling the result standard case (number of balls to draw < number of balls in hat) is quite different.

Hi Sanity,
Thank you for your response. However, I’m afraid I don’t quite understand what I’m doing wrong. For the example above with the blue and green balls the answer would be yes as the project specifies the probability of obtaining “at least” 2 red balls and one green ball. And as for the second part the way I’ve gone about it may be peculiar but it does what it’s meant to do.
If you could expand further that would be appreciated.

Does the code do that?

Is drawn_dict used for a case when number of the balls to draw is higher than number of balls in hat?

I think I see what you mean.
When I started this I thought that attempting to draw more balls than was in the hat would result in a null experiment and we would just take no action.
Are you saying that when the balls to draw is greater than the balls in the hat, we perform the experiment like we are taking the maximum number of balls possible to take?

I have updated my code so that when balls to draw is larger than balls in hat it draws all balls but still doesn’t pass the final test. I have also checked and when the draw has more than desired it does count this as a successful draw. Further help would be appreciated.

Could you share updated code?

Hi Sanity,
thanks for taking a look.
My updated code:

import copy
import random

drawn_dict = {}

class Hat():
def __init__(self, **colours):
self.total = 0
vals = []
self.contents = []
index = 0
for value in colours.values():
vals.append(value)
self.total += value
for colour in colours:
count = 0
index += 1
while count < vals[index - 1]:
self.contents.append(colour)
count += 1
def draw(self, no):
count1 = 0
balls_drawn = []
remaining_balls = []
if no > self.total:
no = self.total
else:
pass
while count1 < no:
balls_drawn.append(self.contents.pop(random.randrange(len(self.contents))))
count1 += 1
for ball in self.contents:
remaining_balls.append(ball)
for ball in balls_drawn:
if ball not in drawn_dict:
drawn_dict[ball] = [ball]
self.contents.append(ball)
else:
drawn_dict[ball].append(ball)
self.contents.append(ball)
return balls_drawn

def experiment(hat, expected_balls, num_balls_drawn, num_experiments):
count2 = 0
M = 0
while count2 < num_experiments:
drawn_dict.clear()
hat.draw(num_balls_drawn)
count3 = 0
for key in expected_balls.keys():
if key in drawn_dict.keys():
check = len(drawn_dict[key])
if expected_balls[key] <= check:
count3 += 1
else:
count3 -= 10000
else:
count3 -= 10000
if count3 > 0:
M += 1
else:
pass
count2 += 1
probs = M / num_experiments
print(probs)

Only small detail left - experiment function should return the probability, it’s not expected to print anything on it own.