Im making a program in python 2.7 that are going to roll dices, and then count how many times each number gets rolled. But cant seem to figure out this problem.
it returns: Traceback (most recent call last):
File "DiceRoller.py", line 16, in
counter[s] += 1
KeyError: 3
from random import randint
while True:
z = raw_input("How many sides should the dice(s) have?\n> ")
i = 0
x = raw_input("How many dices do you want?\n> ")
dice = {}
while i <= int(x):
dice[i] = randint(1,int(z))
i += 1
counter = {}
for p, s in dice.iteritems():
counter[s] += 1
print counter
raw_input("Return to restart.")
You are setting each counter to the value +1:
counter[s] =+ 1
# ^^^
You are not using += there; Python sees that as:
counter[s] = (+1)
Swap the + and the =:
counter[s] += 1
This will raise an exception as the key s is not going to be present the first time; use counter.get() to get a default value in that case:
counter[s] = counter.get(s, 0) + 1
or use a collections.defaultdict() object rather than a regular dictionary:
from collections import defaultdict
counter = defaultdict(int)
for s in dice.itervalues():
counter[s] =+ 1
or use a collections.Counter() object to do the counting:
from collections import Counter
counter = Counter(dice.itervalues())
Use xrange and just increment each count as you go, using two dicts is unnecessary if you just want to count how many times each side is rolled:
from collections import defaultdict
from random import randint
z = int(raw_input("How many sides should the dice(s) have?\n> "))
x = int(raw_input("How many dices do you want?\n> "))
counts = defaultdict(int) # store dices sides as keys, counts as values
# loop in range of how many dice
for _ in xrange(x):
counts[randint(1,z)] += 1
for side,count in counts.iteritems():
print("{} was rolled {} time(s)".format(side,count))
Output:
How many sides should the dice(s) have?
> 6
How many dices do you want?
> 10
1 was rolled 2 time(s)
2 was rolled 3 time(s)
3 was rolled 1 time(s)
4 was rolled 1 time(s)
5 was rolled 1 time(s)
6 was rolled 2 time(s)
If you want to include all dice sides in the output you can create the counts dict using xrange:
counts = {k:0 for k in xrange(1, z+1)}
So the output will then be:
How many sides should the dice(s) have?
> 6
How many dices do you want?
> 10
1 was rolled 0 time(s)
2 was rolled 2 time(s)
3 was rolled 0 time(s)
4 was rolled 0 time(s)
5 was rolled 5 time(s)
6 was rolled 3 time(s)
Related
So this is what I've got. The output is every answer leading up to the final outcome of Odd = 100 and Even = 110. I was hoping someone could maybe suggest what I could do to only print the final answers rather than the whole list of iterations.
Thanks a million x
#inputs
odd = 0
even = 0
counter = 0
# calculations for even numbers
while counter <= 20 and counter % 2 == 0:
even = even + counter
print("The sum of the EVEN numbers between 1 and 20 is", even)
counter += 1
# calculations for odd numbers
if counter <= 20 and counter % 2 != 0:
odd = odd + counter
print("The sum of the ODD numbers between 1 and 20 is", odd)
counter += 1
use the print statement after incrementing the counter, outside the while loop
#inputs
odd = 0
even = 0
counter = 0
# calculations for even numbers
while counter <= 20 and counter % 2 == 0:
even = even + counter
counter += 1
# calculations for odd numbers
if counter <= 20 and counter % 2 != 0:
odd = odd + counter
counter += 1
print("The sum of the ODD numbers between 1 and 20 is", odd)
print("The sum of the EVEN numbers between 1 and 20 is", even)
Something like this should work; note the print statement is outside the while loop and the arithmetic is being done on odd and even using the if statement to determine which is to be added. Hope this makes sense
odd = 0
even = 0
counter = 0
while counter <= 20:
if counter % 2 == 0:
even += counter
elif counter % 2 != 0:
odd += counter
counter += 1
print("Sum of odd numbers is: {}, sum of even numbers is: {}".format(odd, even))
I am writing a program that is to repeatedly roll two dice until the user input target value is reached. I can not figure out how to make the dice roll happen repeatedly. Please, help...
from random import randrange
print ("This program rolls two 6-sided dice until their sum is a given target value.")
input = int (input("Enter the target sum to roll for:"))
#def main():
dice1 = randrange (1,7)
dice2 = randrange (1,7)
sumofRoll = dice1 + dice2
output = "Roll: {} and {}, sum is {}".format (dice1,dice2,sumofRoll)
print (output)
if sumofRoll == input:
print ("All done!!")
if sumofRoll != input:
#how do I make this repeatedly run until input number is reached?!
Here is a complete working code which takes care of invalid sum entered as input as well. The sum of two dice rolls cannot be either less than 2 or more than 13. So a check for this condition makes your code slightly more robust. You need to initialize sumofRoll = 0 before entering the while loop as this would be needed to first enter the while loop. The value of 0 is a safe value because we excluded the value of 0 entered by user to be a valid sum.
from random import randrange
print ("This program rolls two 6-sided dice until their sum is a given target value.")
input_sum = int(input("Enter the target sum to roll for:"))
def main():
sumofRoll = 0
if input_sum < 2 or input_sum > 13:
print ("Enter a valid sum of dices")
return
while sumofRoll != input_sum:
dice1 = randrange (1,7)
dice2 = randrange (1,7)
sumofRoll = dice1 + dice2
output = "Roll: {} and {}, sum is {}".format (dice1,dice2,sumofRoll)
print (output)
if sumofRoll == input_sum:
print ("All done!!")
main()
This program rolls two 6-sided dice until their sum is a given target value.
Enter the target sum to roll for:10
Roll: 3 and 5, sum is 8
Roll: 6 and 6, sum is 12
Roll: 5 and 1, sum is 6
Roll: 2 and 5, sum is 7
Roll: 6 and 6, sum is 12
Roll: 3 and 5, sum is 8
Roll: 1 and 2, sum is 3
Roll: 6 and 4, sum is 10
All done!!
I took your game and added some elements for you to peek through. One is you could use random.choice and select from a die list instead of generating new random ints repeatedly. Second you can use a try/except block to only accept an int and one that is within the range of (2, 13). Next we can add a roll_count to track the amount of rolls to hit our target. Our while loop will continue until target == roll_sum and then we can print our results.
from random import choice
die = [1, 2, 3, 4, 5, 6]
print('This program rolls two 6-sided dice until their sum is a given target.')
target = 0
while target not in range(2, 13):
try:
target = int(input('Enter the target sum to roll (2- 12): '))
except ValueError:
print('Please enter a target between 2 and 12')
roll_sum = 0
roll_count = 0
while target != roll_sum:
die_1 = choice(die)
die_2 = choice(die)
roll_sum = die_1 + die_2
roll_count += 1
print('You rolled a total of {}'.format(roll_sum))
print('You hit your target {} in {} rolls'.format(target, roll_count))
...
You rolled a total of 4
You rolled a total of 12
You hit your target 12 in 29 rolls
This is a simple while loop:
sumofRoll = -1; #a starting value!
while sumofRoll != input:
#Put the code that updates the sumofRoll variable here
count = 0
while(sumOfRoll != input):
dice1 = randrange(1,7)
dice2 = rangrange(1,7)
count = count + 1
sumOfRoll = dice1 + dice2
print("sum = %s, took %s tries" % (sumOfRoll, count))
Use a do while statement
do:
dice1=randrange(1,7)
...
while(sumofroll != input)
print("all done")
import random
sample_size = int(input("Enter the number of times you want me to roll the die: "))
if (sample_size <=0):
print("Please enter a positive number!")
else:
counter1 = 0
counter2 = 0
final = 0
while (counter1<= sample_size):
dice_value = random.randint(1,6)
if ((dice_value) == 6):
counter1 += 1
else:
counter2 +=1
final = (counter2)/(sample_size) # fixing indention
print("Estimation of the expected number of rolls before pigging out: " + str(final))
Is the logic used here correct? It will repeat rolling a die till a one is rolled, while keeping track of the number of rolls it took before a one showed up. It gives a value of 0.85 when I run it for high values(500+)
Thanks
import random
while True:
sample_size = int(input("Enter the number of times you want me to roll a die: "))
if sample_size > 0:
break
roll_with_6 = 0
roll_count = 0
while roll_count < sample_size:
roll_count += 1
n = random.randint(1, 6)
#print(n)
if n == 6:
roll_with_6 += 1
print(f'Probability to get a 6 is = {roll_with_6/roll_count}')
One sample output:
Enter the number of times you want me to roll a dile: 10
Probability to get a 6 is = 0.2
Another sample output:
Enter the number of times you want me to roll a die: 1000000
Probability to get a 6 is = 0.167414
Sticking with your concept, I would create a list that contains each roll then use enumerate to count the amount of indices between each 1 and sum those, using the indicies as markers.
the variable that stores the sum of the number of rolls it took before a 1 showed up - OP
from random import randint
sample_size = 0
while sample_size <= 0:
sample_size = int(input('Enter amount of rolls: '))
l = [randint(1, 6) for i in range(sample_size)]
start = 0
count = 0
for idx, item in enumerate(l):
if item == 1:
count += idx - start
start = idx + 1
print(l)
print(count)
print(count/sample_size)
Enter amount of rolls: 10
[5, 3, 2, 6, 2, 3, 1, 3, 1, 1]
7
0.7
Sameple Size 500:
Enter amount of rolls: 500
406
0.812
I'm a longterm lurker first time questioner. I'm trying to teach myself Python and while I've researched my question I couldn't find an answer. My below code runs if I remove the first While loop but currently it doesn't seem to enter the second while loop. I think I might be channelling my inner VBA which I use at work and this is only second time I've tried Python.
I've tried changing the first while so it isn't just while true and tried variants on the second while.
The intent here is to investigate a dice pool mechanic for a game I'm thinking of and model rolling multiple D6s, 5-6 explode, 3+ successes and 1-2 failures. Ultimately I want it to run roll the dice return the dice list number of successes etc and then reset asking the user for number of dice to roll again.
import random
Scount = 0
Xcount = 0
Fcount = 0
rollcount = 0
cheat = 0
NoOfDice = 1
Dicelist = []
while True:
print ("Input number of dice to roll")
NoOfDice=input()
while cheat<int(NoOfDice):
rand = random.randint(1, 6)
Dicelist.append(rand)
if rand <= 4:
cheat += 1
if rand >= 3:
Scount += 1
if rand >= 2:
Fcount += 1
if rand <= 5:
Xcount += 1
print (Dicelist)
print ("We rolled " + str(NoOfDice) + " you got " + str(Scount) + " number of succeses with " + str(Xcount) + " number of dice exploded with " + str(Fcount) + " dice failed")
Thank you all and appreciate your time!
The condition for your first while loop is essentially going to always be True, meaning that it's an infinite loop.
Your second loop may not seem like it's running, but it definitely is (as long as you enter a number greater than 0).
The reason your program has no output is because your print() statements are after the infinite loop, so they'll never run. This is why your program runs as desired when you remove the infinite loop.
To fix this, just move your print() statements inside the first loop but at the end.
Note: If you want to get time to read what is being printed when you run the program, you should change the print()s to input()s as this will mean that the first loop only loops around after you've pressed Enter.
Additional Note: random.randint(1, 6) returns a value from 0 to 5 not from 1 to 6. Looking at your values in your if statements, you probably want to change code to:
rand = random.randint(1,6) + 1
Your code could further be condensed using with just 2 if statements instead of 4. Below is my proposed solution. I wrapped it in a function but you don't have to. I'll leave it for you think and decide how to escape the first "while" loop after the second while loop finished execution.
def rolldice ():
... while True:
... scount = 0
... xcount = 0
... fcount = 0
... cheat = 0
... NoOfDice = ''
... DiceList = []
... NoOfDice = input ('Number of dice to roll: ')
... while cheat < int (NoOfDice):
... rand = random.randint(1, 6)
... DiceList.append (rand)
... if rand <= 5:
... cheat += 1
... xcount += 1
... if rand >= 2:
... fcount += 1
... scount += 1
... print ('Dice List: ', DiceList)
... print ('Number of dice rolled:', NoOfDice)
... print ('Success Count: %d' % scount)
... print ('Exploded Count: %d' % xcount)
... print ('Failed Count: %d' % fcount)
...
>>> rolldice()
Number of dice to roll: >? 3
Dice List: [2, 3, 1]
Number of dice rolled: 3
Success Count: 2
Exploded Count: 3
Failed Count: 2
Number of dice to roll: >? 1
Dice List: [5]
Number of dice rolled: 1
Success Count: 1
Exploded Count: 1
Failed Count: 1
Number of dice to roll:
I want this while loop to change numbers with every iteration (both the count and random int.) but when I run the program, the loop just goes on with the same numbers on the count and random int.:
# if 4 sides
die1 = random.randint(1,4)
die2 = random.randint(1,4)
count = 1
while sides == 4 and die1 != die2:
print (count, ". die number 1 is", die1, "and die number 2 is", die2,".")
count == count + 1
print ("You got snake eyes! Finally! On try number", count,".")
Each time you call random.randint(1,4), you are creating a single random number. It does not magically change to a new random number whenever you print it.
Generate new random numbers with random.randint(1, 4) inside your while loop.
The second problem is that count == count + 1 checks for equality (and returns False in your case). To do an assignment, use the assignment operator = or count += 1 to increment count by one.
If you want a generator that endlessly spits out random numbers, write one:
>>> import random
>>> def rng(i, j):
... while True:
... yield random.randint(i, j)
...
>>> random_gen = rng(1, 4)
>>> next(random_gen)
2
>>> next(random_gen)
3
>>> next(random_gen)
2
>>> next(random_gen)
2
>>> next(random_gen)
1
You need to do the random calls also inside the while loop otherwise they will not change. And the other thing is that you compare == and not set = the counter:
import random
sides = 4
count = 1
die1 = random.randint(1,4)
die2 = random.randint(1,4)
while sides == 4 and die1 != die2:
print (count, ". die number 1 is", die1, "and die number 2 is", die2,".")
count += 1
die1 = random.randint(1,4)
die2 = random.randint(1,4)
print ("You got snake eyes! Finally! On try number", count,".")
Trying a test run gives me:
1 . die number 1 is 4 and die number 2 is 3 .
2 . die number 1 is 2 and die number 2 is 1 .
3 . die number 1 is 1 and die number 2 is 2 .
4 . die number 1 is 3 and die number 2 is 4 .
5 . die number 1 is 1 and die number 2 is 4 .
You got snake eyes! Finally! On try number 6 .
One alternative that is almost identical but uses break instead of conditions on the while loop would be:
import random
sides = 4
count = 1
def tossdie():
"""Function to create a random integer for a die"""
return random.randint(1,4)
while True:
die1 = tossdie()
die2 = tossdie()
print (count, ". die number 1 is", die1, "and die number 2 is", die2,".")
if die1 == die2:
break
count += 1
print ("You got snake eyes! Finally! On try number", count,".")
Not sure why you needed the sides variable, so I left it out.
You want to roll the die in every loop, which means you have to re-assign die1 and die2 to a random number in each loop.
import random
# Initial parameters
die1 = random.randint(1,4)
die2 = random.randint(1,4)
count = 1
# Loop and roll die each time
while die1 != die2:
print(count, ". die number 1 is", die1, "and die number 2 is", die2,".")
die1 = random.randint(1,4)
die2 = random.randint(1,4)
count += 1
# Print on which die roll you got two equal die numbers rolled
print ("You got snake eyes! Finally! On try number", count,".")
You can use a for loop with iter to spit out pairs of random numbers , enumerate will do the counting, for snake-eyes you should also be checking that both are 1's not a random matching pair:
from random import randint
def repeating_rand(i, j):
for count, (r1, r2 ) in enumerate(iter(lambda: (randint(i, j), randint(i, j)), None), 1):
if r1 == 1 and r2 == 1:
return "You got snake eyes! Finally! On try number {}.".format(count)
print("Try no. {}, die number 1 is {} and die number 2 is {}".format(count, r1, r2))
Output:
In [12]: repeating_rand(1, 4)
Try no. 1, die number 1 is 1 and die number 2 is 2
Try no. 2, die number 1 is 4 and die number 2 is 1
Try no. 3, die number 1 is 1 and die number 2 is 2
Try no. 4, die number 1 is 1 and die number 2 is 3
Try no. 5, die number 1 is 1 and die number 2 is 3
Try no. 6, die number 1 is 3 and die number 2 is 4
Try no. 7, die number 1 is 4 and die number 2 is 2
Try no. 8, die number 1 is 1 and die number 2 is 2
Try no. 9, die number 1 is 3 and die number 2 is 2
Try no. 10, die number 1 is 4 and die number 2 is 3
Try no. 11, die number 1 is 1 and die number 2 is 3
Try no. 12, die number 1 is 3 and die number 2 is 4
Out[12]: 'You got snake eyes! Finally! On try number 13.'