Hello everybody, im working on the project “Probability Calculator” and I just can’t pass the third test. (“The experiment method should return a different probability”)
My calculations are near to what the probability of the example provided is, but not in the 0,1 range required, and i can’t figure out why.
My only guess is my 2 broad usages of pass and except, but those don’t seem to cause problems.
import copy
import random
class Hat:
contents = []
def __init__(self, **kwargs):
# convert input to contents
color_dict = {}
color_dict.update(**kwargs)
for color in color_dict.keys():
if color_dict.get(color) > 0:
count = 0
while count < color_dict.get(color):
count += 1
self.contents.append(color)
def draw(self, drawn_balls):
draw_number = 0
remove_list = []
# returning the randomly drawn balls and removing them from contents
if drawn_balls <= len(self.contents):
while draw_number < drawn_balls:
draw_number += 1
random_number = random.randrange(0, len(self.contents))
# print("random number:" + str(random_number))
# print(len(copy_contents))
remove_list.append(self.contents[random_number])
self.contents.pop(random_number)
return remove_list
def experiment(from_hat, expected_balls, num_balls_drawn, num_experiments):
run = 0
complete_success_counter = 0
# make copy of contents to restore original of contents (to return all the drawn balls)
copy_contents = copy.copy(from_hat.contents)
# return all the balls when the number of balls to draw exceeds the available quantity
while run <= num_experiments:
if len(from_hat.contents) < num_balls_drawn:
# print("not enough balls left, returning all the balls")
from_hat.contents.clear()
for count in copy_contents:
from_hat.contents.append(count)
# print(len(hat.contents))
run += 1
drawn_balls = from_hat.draw(num_balls_drawn)
drawn_balls_no_dupl = []
# remove duplicates (to not check colors multiple times)
for no_dupl in drawn_balls:
if no_dupl not in drawn_balls_no_dupl:
drawn_balls_no_dupl.append(no_dupl)
# count number of balls per color
draw_dict = {}
for color in drawn_balls:
try:
draw_dict[color] = draw_dict[color] + 1
except:
draw_dict[color] = 1
# print("expected balls: ")
# print(expected_balls)
# print(" ")
# print("drawn balls: ")
# print(draw_dict)
# print("---")
# count how many times expected and drawn balls match (per color)
success_counter = 0
for color in drawn_balls_no_dupl:
try:
if draw_dict[color] >= expected_balls[color]:
# print("Success: " + color)
success_counter += 1
except:
pass
# print("---")
# check if there is a match for all colors, and if so, add 1 to the complete success counter
if success_counter == len(expected_balls):
complete_success_counter += 1
# print(complete_success_counter)
# calculate probability and round it
probability = round(complete_success_counter / num_experiments, 3)
return probability
Your browser information:
User Agent is: Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/124.0.0.0 Safari/537.36
Challenge Information:
Scientific Computing with Python Projects - Probability Calculator
I updated the code on Replit, but here it is (only class):
import copy
import random
class Hat:
contents = []
def __init__(self, **kwargs):
# convert input to contents
color_dict = {}
color_dict.update(**kwargs)
for color in color_dict.keys():
if color_dict.get(color) > 0:
count = 0
while count < color_dict.get(color):
count += 1
self.contents.append(color)
def draw(self, drawn_balls):
draw_number = 0
remove_list = []
# returning the randomly drawn balls and removing them from contents
if drawn_balls <= len(self.contents):
while draw_number < drawn_balls:
draw_number += 1
random_number = random.randrange(0, len(self.contents))
# print("random number:" + str(random_number))
# print(len(copy_contents))
remove_list.append(self.contents[random_number])
self.contents.pop(random_number)
return remove_list
def experiment(hat, expected_balls, num_balls_drawn, num_experiments):
run = 0
complete_success_counter = 0
# make copy of contents to restore original of contents (to return all the drawn balls)
copy_contents = copy.copy(hat.contents)
# return all the balls when the number of balls to draw exceeds the available quantity
while run <= num_experiments:
if len(hat.contents) < num_balls_drawn:
# print("not enough balls left, returning all the balls")
hat.contents.clear()
for count in copy_contents:
hat.contents.append(count)
# print(len(hat.contents))
run += 1
drawn_balls = hat.draw(num_balls_drawn)
drawn_balls_no_dupl = []
# remove duplicates (to not check colors multiple times)
for no_dupl in drawn_balls:
if no_dupl not in drawn_balls_no_dupl:
drawn_balls_no_dupl.append(no_dupl)
# count number of balls per color
draw_dict = {}
for color in drawn_balls:
try:
draw_dict[color] = draw_dict[color] + 1
except:
draw_dict[color] = 1
# print("expected balls: ")
# print(expected_balls)
# print(" ")
# print("drawn balls: ")
# print(draw_dict)
# print("---")
# count how many times expected and drawn balls match (per color)
success_counter = 0
for color in drawn_balls_no_dupl:
try:
if draw_dict[color] >= expected_balls[color]:
# print("Success: " + color)
success_counter += 1
except:
pass
# print("---")
# check if there is a match for all colors, and if so, add 1 to the complete success counter
if success_counter == len(expected_balls):
complete_success_counter += 1
# print(complete_success_counter)
# calculate probability and round it
probability = round(complete_success_counter / num_experiments, 3)
return probability
There is an issue with the tests of this project, the resolution is not live yet but it will be soon. You are also failing this extra test:
Failed:The draw method should behave correctly when the number of ballsto extract is bigger than the number of balls in the hat.
Your function doesn’t work correctly when the balls to extract are more than the content of the hat
pyodide.asm.js:9 Traceback (most recent call last):
pyodide.asm.js:9 File "/home/pyodide/test_module.py", line 15, in test_hat_draw_2
pyodide.asm.js:9 self.assertEqual(actual, expected, 'Expected hat draw to return all items from hat contents.')
pyodide.asm.js:9 AssertionError: None != ['yellow', 'yellow', 'yellow', 'yellow', [118 chars]est'] : Expected hat draw to return all items from hat contents.
Because the I already addressed the assignment “If the number of balls to draw exceeds the available quantity, return all the balls.” in line 45-51 of my previous code, I believe you’re talking about when “num_balls_drawn” in the call for the function experiment (e.g. print(experiment(hat=hat,
expected_balls={“red”: 2, “green”: 1},
num_balls_drawn=100000000,
num_experiments=2000))) is higher than the contents of the hat?
If so, i fixed this in the following code: (line 39-41)
import copy
import random
class Hat:
contents = []
def __init__(self, **kwargs):
# convert input to contents
color_dict = {}
color_dict.update(**kwargs)
for color in color_dict.keys():
if color_dict.get(color) > 0:
count = 0
while count < color_dict.get(color):
count += 1
self.contents.append(color)
def draw(self, drawn_balls):
draw_number = 0
remove_list = []
# returning the randomly drawn balls and removing them from contents
if drawn_balls <= len(self.contents):
while draw_number < drawn_balls:
draw_number += 1
random_number = random.randrange(0, len(self.contents))
# print("random number:" + str(random_number))
# print(len(copy_contents))
remove_list.append(self.contents[random_number])
self.contents.pop(random_number)
return remove_list
def experiment(hat, expected_balls, num_balls_drawn, num_experiments):
if num_balls_drawn > len(hat.contents):
print("Number of balls to draw is too high.")
exit()
run = 0
complete_success_counter = 0
# make copy of contents to restore original of contents (to return all the drawn balls)
copy_contents = copy.copy(hat.contents)
# return all the balls when the number of balls to draw exceeds the available quantity
while run <= num_experiments:
if len(hat.contents) < num_balls_drawn:
# print("not enough balls left, returning all the balls")
hat.contents.clear()
for count in copy_contents:
hat.contents.append(count)
# print(len(hat.contents))
run += 1
drawn_balls = hat.draw(num_balls_drawn)
drawn_balls_no_dupl = []
# remove duplicates (to not check colors multiple times)
for no_dupl in drawn_balls:
if no_dupl not in drawn_balls_no_dupl:
drawn_balls_no_dupl.append(no_dupl)
# count number of balls per color
draw_dict = {}
for color in drawn_balls:
try:
draw_dict[color] = draw_dict[color] + 1
except:
draw_dict[color] = 1
# print("expected balls: ")
# print(expected_balls)
# print(" ")
# print("drawn balls: ")
# print(draw_dict)
# print("---")
# count how many times expected and drawn balls match (per color)
success_counter = 0
for color in drawn_balls_no_dupl:
try:
if draw_dict[color] >= expected_balls[color]:
# print("Success: " + color)
success_counter += 1
except:
pass
# print("---")
# check if there is a match for all colors, and if so, add 1 to the complete success counter
if success_counter == len(expected_balls):
complete_success_counter += 1
# print(complete_success_counter)
# calculate probability and round it
probability = round(complete_success_counter / num_experiments, 3)
return probability
I have updated the code, so that now the draw function itself reacts accordingly to too many balls being drawn. The test is still failing, and I have absolutely no idea why. If possible, could you look over the code and maybe tell me where my problem is? I’m out of ideas.
Thank you in advance!
import copy
import random
class Hat:
contents = []
copy_contents = []
def __init__(self, **kwargs):
# convert input to contents
color_dict = {}
color_dict.update(**kwargs)
for color in color_dict.keys():
if color_dict.get(color) > 0:
count = 0
while count < color_dict.get(color):
count += 1
self.contents.append(color)
# make copy of contents to restore original of contents (to return all the drawn balls)
cc = copy.deepcopy(self.contents)
self.copy_contents = cc
def draw(self, drawn_balls):
if len(self.contents) < drawn_balls:
# print("not enough balls left, returning all the balls")
self.contents.clear()
for count in self.copy_contents:
self.contents.append(count)
if len(self.contents) < drawn_balls:
print("Too many balls drawn")
exit()
# print("COPY:")
# print(hat.copy_contents)
# print("OG:")
# print(hat.contents)
draw_number = 0
remove_list = []
# returning the randomly drawn balls and removing them from contents
if drawn_balls <= len(self.contents):
while draw_number < drawn_balls:
draw_number += 1
random_number = random.randrange(0, len(self.contents))
# print("random number:" + str(random_number))
# print(len(copy_contents))
remove_list.append(self.contents[random_number])
self.contents.pop(random_number)
return remove_list
def experiment(hat, expected_balls, num_balls_drawn, num_experiments):
run = 0
complete_success_counter = 0
# return all the balls when the number of balls to draw exceeds the available quantity
while run <= num_experiments:
run += 1
drawn_balls = hat.draw(num_balls_drawn)
drawn_balls_no_dupl = []
# remove duplicates (to not check colors multiple times)
for no_dupl in drawn_balls:
if no_dupl not in drawn_balls_no_dupl:
drawn_balls_no_dupl.append(no_dupl)
# count number of balls per color
draw_dict = {}
for color in drawn_balls:
try:
draw_dict[color] = draw_dict[color] + 1
except:
draw_dict[color] = 1
# print("expected balls: ")
# print(expected_balls)
# print(" ")
# print("drawn balls: ")
# print(draw_dict)
# print("---")
# count how many times expected and drawn balls match (per color)
success_counter = 0
for color in drawn_balls_no_dupl:
try:
if draw_dict[color] >= expected_balls[color]:
# print("Success: " + color)
success_counter += 1
except:
pass
# print("---")
# check if there is a match for all colors, and if so, add 1 to the complete success counter
if success_counter == len(expected_balls):
complete_success_counter += 1
# print(complete_success_counter)
# calculate probability and round it
probability = round(complete_success_counter / num_experiments, 3)
return probability```
If the number of balls to draw exceeds the available balls, just like in your example, this string is being printed and the program exits.
That is exactly what i programmed it to do in line 35-37.
I don’t get an error.
Okay I misinterpreted the it. I’ve updated the code (line 47-51), and it works like intended, but I’m still failing the test, and I don’t know why.
Here’s the updated code:
import copy
import random
class Hat:
contents = []
copy_contents = []
def __init__(self, **kwargs):
# convert input to contents
color_dict = {}
color_dict.update(**kwargs)
for color in color_dict.keys():
if color_dict.get(color) > 0:
count = 0
while count < color_dict.get(color):
count += 1
self.contents.append(color)
# make copy of contents to restore original of contents (to return all the drawn balls)
cc = copy.deepcopy(self.contents)
self.copy_contents = cc
def draw(self, drawn_balls):
# print("COPY:")
# print(hat.copy_contents)
# print("OG:")
# print(hat.contents)
draw_number = 0
remove_list = []
# returning the randomly drawn balls and removing them from contents
while draw_number < drawn_balls:
# print(self.contents)
# print(len(remove_list))
draw_number += 1
random_number = random.randrange(0, len(self.contents))
# print("random number:" + str(random_number))
# print(len(copy_contents))
remove_list.append(self.contents[random_number])
self.contents.pop(random_number)
if len(self.contents) < 1:
# print("not enough balls left, returning all the balls")
self.contents.clear()
for count in self.copy_contents:
self.contents.append(count)
return remove_list
def experiment(hat, expected_balls, num_balls_drawn, num_experiments):
run = 0
complete_success_counter = 0
# return all the balls when the number of balls to draw exceeds the available quantity
while run <= num_experiments:
run += 1
drawn_balls = hat.draw(num_balls_drawn)
drawn_balls_no_dupl = []
# remove duplicates (to not check colors multiple times)
for no_dupl in drawn_balls:
if no_dupl not in drawn_balls_no_dupl:
drawn_balls_no_dupl.append(no_dupl)
# count number of balls per color
draw_dict = {}
for color in drawn_balls:
try:
draw_dict[color] = draw_dict[color] + 1
except:
draw_dict[color] = 1
# print("expected balls: ")
# print(expected_balls)
# print(" ")
# print("drawn balls: ")
# print(draw_dict)
# print("---")
# count how many times expected and drawn balls match (per color)
success_counter = 0
for color in drawn_balls_no_dupl:
try:
if draw_dict[color] >= expected_balls[color]:
# print("Success: " + color)
success_counter += 1
except:
pass
# print("---")
# check if there is a match for all colors, and if so, add 1 to the complete success counter
if success_counter == len(expected_balls):
complete_success_counter += 1
# print(complete_success_counter)
# calculate probability and round it
probability = round(complete_success_counter / num_experiments, 3)
return probability```