I am working through a course where this has come up a few times now, and I've not been able to get it right.
**Edit: I have solved this now. I used a while loop, "while bidding:", then within that while loop I was able to create an 'if' statement to impact the 'bidding' variable. A function was the wrong idea for this code. **
I am creating a variable that = True early on in the code, then while it is True, running a function. Within that function is an 'if' statement that should be changing the variable to False, stopping the function, but it doesn't. I think I must have the code in the wrong order or maybe the wrong indentation.
Here is the relevant code.
bidding = True
bidder = input("What is your name?: ")
bid_amount = int(input("What's your bid?: $"))
more_bidders = input("Are there any other bidders? Type 'yes' or 'no'. \n").lower
def add_to_dict(bidder_name, dollar_amount, anyone_else):
bidder_dict[bidder_name] = dollar_amount
if anyone_else == "no":
bidding = False
while bidding:
add_to_dict(bidder_name = bidder, dollar_amount = bid_amount, anyone_else = more_bidders)
I run the code fine, I type "no" when it asks if there's any more bidders, and it just pauses because it thinks "bidding" is still True. So my 'if' statement isn't doing what I need it to, but I don't know why.
Without changing your code much, you can use global:
def add_to_dict(bidder_name, dollar_amount, anyone_else):
global bidding
bidder_dict[bidder_name] = dollar_amount
if anyone_else == "no":
bidding = False
while bidding:
add_to_dict(bidder_name = bidder, dollar_amount = bid_amount, anyone_else = more_bidders)
A better solution would be to return bidding from add_to_dict():
def add_to_dict(bidder_name, dollar_amount, anyone_else):
bidder_dict[bidder_name] = dollar_amount
if anyone_else == "no":
return False
return True
while bidding:
bidding = add_to_dict(bidder_name = bidder, dollar_amount = bid_amount, anyone_else = more_bidders)
I believe the issue is coming from the comparison in the if statement. You are seeing if the string in anyone_else is equal to "no" but you have the variable more_bidders taking in the string "yes" or "no. So I recommend either change anyone_else to more_bidders or initialize anyone_else with more_bidders before the if statement.
you can try in this way:
bidding = True
bidder_dict = {}
bidder = ""
bid_amount = 0
more_bidders = "yes"
def add_to_dict():
bidder = input("What is your name?: ")
bid_amount = int(input("What's your bid?: $"))
more_bidders = str(input("Are there any other bidders? Type 'yes' or 'no'. \n"))
bidder_dict[bidder] = bid_amount
print(more_bidders)
if more_bidders == "no":
return False
else:
return True
while bidding:
if add_to_dict():
print("OK")
else:
print("Terminou")
break
print(bidder_dict)
Related
status_login = False
use_atm = "y"
data =[{"norek":932012042,
"pin":123,
"name":"grizly",
"bank":"BCA",
"balance":5000000},
{"norek":932012052,
"pin":1234,
"name":"Basuki Pepeh",
"bank":"BRI",
"balance":4000000},
{"norek":932012099,
"pin":1235,
"name":"Bambang Gentolet",
"bank":"Mandiri",
"balance":3500000}]
def cek_login(p):
for login in data:
if login['pin'] == p:
return login
return False
while use_atm == "y":
while status_login == False:
print("Welcome to ATM")
print("insert your pin")
pin = input("PIN : ")
if cek_login(pin) != False:
print("welcome "+cek_login(pin)['name'])
status_login = True
else:
print("")
print("Ops Your PIN is wrong")
print("")
print("")
I want to make a login using a pin but why the result is always wrong, what is wrong with the code above
Welcome to ATM
insert your pin
PIN : 123
Ops Your PIN is wrong
The pin in your data is int.
input is str.
str is not equal to int.
pin = int(input("PIN : "))
Your comparison is failing in cek_login, so print the values using repr() and see why they don't compare. Note that repr() gives a debugging representation of the data so it is easier to spot differences:
def cek_login(p):
for login in data:
print(repr(long['pin']),repr(p)) # see why they don't compare
if login['pin'] == p:
return login
return False
You will see:
Welcome to ATM
insert your pin 123
123 '123' # note integer versus string (quoted).
1234 '123'
1235 '123'
Convert the input to an integer to fix the problem.
pin = int(input("PIN : "))
You'll also find that you will enter an infinite loop after getting the pin correct, because use_atm never changes.
Learn to use a source debugger so you don't have to litter your code with print statements.
There were a couple bugs here, and some other people already pointed them out:
cek_login(p) uses data, which is a list of dictionaries, so you need to first access the dictionary in the list by index ([0], [1], ...), and THEN access the dictionary element with bracket notation like ['pin']
data[0]['pin'] is an int, whereas the result of input() is a str, so you need to CONVERT the str to an int with int(my_str_input)
Similar to point 1, the print statement under the while loop which prints the user's name needs to first access the index in the list (data) before accessing the dictionary value ([name])
Try this:
status_login = False
use_atm = "y"
data =[{"norek":932012042,
"pin":123,
"name":"grizly",
"bank":"BCA",
"balance":5000000},
{"norek":932012052,
"pin":1234,
"name":"Basuki Pepeh",
"bank":"BRI",
"balance":4000000},
{"norek":932012099,
"pin":1235,
"name":"Bambang Gentolet",
"bank":"Mandiri",
"balance":3500000}]
def cek_login(p):
print(int(p))
print(data[0]['pin'])
if data[0]['pin'] == int(p):
return True
return False
while use_atm == "y":
while status_login == False:
print("Welcome to ATM")
print("insert your pin")
pin = input("PIN : ")
if cek_login(pin) != False:
print("welcome "+ data[0]['name'])
status_login = True
use_atm = "n"
else:
print("")
print("Ops Your PIN is wrong")
print("")
print("")
I keep getting an error when I run this functions. Everything goes through and then it shows this error. I have tried adding .items() to the end when I print the dictionary and still throws this error.
CLARIFICATION just realized. Not getting any type errors or anything. It prints fine but when doesn't add the second variable to the dictionary. Instead it prints this..
{'Frappe': ('small', function type_of_milk at 0x000002BE2BCD2F78>)}
def order():
ready_to_order = True
while ready_to_order != False:
ordering_q = input(
"""Do you know what you would like to order or do you need to see the menu?
[M]enu or [R]eady to order or [Q]uit: """)
if ordering_q.upper() == "Q":
sys.exit()
elif ordering_q.upper() == "M":
print(Menu())
elif ordering_q.upper() == "R":
ready_to_order = False
else:
print("Please enter valid letters only, try again.")
print(" ")
print(" ")
add_cart = True
while add_cart != False:
order1 = input("What would you like to order?")
if order1.upper() == "Done":
add_cart = False
elif order1 == 'a1':
print("Frappe added to cart")
global total_order
total_order += 3
drink_size()
type_of_milk()
order_dict['Frappe'] = (drink_sizes, type_of_milk)
add_cart = False
print(order_dict)
This line:
order_dict['Frappe'] = (drink_sizes, type_of_milk)
is adding the function type_of_milk to your dict, which is why you see function type_of_milk at 0x000002BE2BCD2F78> when you print the dict out. Maybe you meant to say type_of_milk()?
I'm trying to make a program where I input a name and a surname and the code checks if the name is invalid (list of invalidiations below). If it has any invalidations, it asks me to say the name again and presents me a list of all the invalidations.
Invalidations list (I'll show the code version too):
- The name has digits
- The name has symbols
- The name has no spaces
- It has more then one space
- One of the names is either too short or too long
- The first letter of the name is a space
- The last letter of the name is a space
I can't use exceptions here, because these are not code erros. I've made it with Ifs, but it got to a point where there a simply lots of Ifs for it to be viable.
def has_digits(name):
digits = any(c.isdigit() for c in name)
if digits == True:
return True
print("Your name has digits.")
else:
return False
def has_symbols(name):
symbols = any(not c.isalnum() and not c.isspace() for c in name)
if symbols == True:
return True
print("Your name has symbols.")
else:
return False
def has_no_spaces(name):
spaces = any(c.isspace() for c in name)
if not spaces == True:
return True
print("You only gave me a name.")
else:
return False
def many_spaces(name):
m_s = name.count(' ') > 1
if m_s == True:
return True
print("Your name has more than one space.")
else:
return False
def unrealistic_length(name, surname):
length= (float(len(name)) < 3 or float(len(name)) > 12) or float(len(surname)) < 5 or float(len(surname) > 15)
if length == True:
return True
print("Your name has an unrealistic size.")
else:
return False
def first_space(name):
f_s = name[0] == " "
if f_s == True:
return True
print("The first letter of your name is a space.")
else:
return False
def last_space(name):
l_s = name[-1] == " "
if l_s == True:
return True
print("The last letter of your name is a space.")
else:
return False
name = "bruh browski"
namesplit = name.split(" ")
name1 = namesplit[0]
name2 = namesplit[1]
print(has_digits(name))
print(has_symbols(name))
print(has_no_spaces(name))
print(many_spaces(name))
print(unrealistic_length(name1, name2))
print(first_space(name))
print(last_space(name))
Maybe the prints shouldn't be in the defs themselves. I don't know. I'm almost sure doing a for loop is the way to go, but I just can't imagine how to do it.
Result:
False
False
False
False
False
False
False
The methods you've used to define exactly what counts as each "invalidation" will have to stay, unless you can replace them with something else that does the same thing. But you can check all of those conditions at once using a generator expression:
if any(is_invalid(name) for is_invalid in [
has_digits, has_symbols, has_no_spaces, many_spaces, unrealistic_length, first_name, last_name
]):
# then this string is invalid
# otherwise, all of those returned false, meaning the string is valid.
You can then use that condition to determine when to stop asking the user, or however else you need to.
If you wanted to not individually define all those functions, you could also maybe use lambdas to do the same thing.
As a sidenote, before actually using this in production for checking the validity of names, I advise having a look at the list of Falsehoods Programmers Believe about Names. It's a fun read even if it's not relevant to your use case, though.
You could have a single function which calls all of your other functions and handles it appropriately.
def master_verify(name):
# Put all your verify functions in the list below.
verify_funcs = [has_digits, has_symbols, has_no_spaces, many_spaces,
unrealistic_length, first_space, last_space]
# It will return True if any your functions return True. In this case,
# returning True means the name is invalid (matching your other
# function design). Returning False means the name is valid.
return any(is_invalid(name) for is_invalid in verify_funcs)
Since you mentioned you want the program to find any name errors and ask the user to try again, we can write a loop to handle this.
def get_name():
while True:
# Loop until you get a good name
name = input("Enter your name: ").strip()
if master_verify(name):
# Remember, if True this means invalid
print("Invalid name. Try again.")
continue # continue jumps to the top of a loop, skipping everything else.
return name # Will only get here if the name is valid.
I also suggest you should do the name and surname split inside your unrealistic_length function.
Then, all you need to do is
name = get_name()
# All of the validation has already happened.
print(f"The correct and validated name is: {name}")
Last but not least, anything in a function after a return is unreachable. So a lot of your prints will never happen. Put the print statements before your return.
Alright. I've managed to do it by myself. I still fill there's a better way to do it, but this is the way I found.
errors_list = []
print("Hi. Tell me your first and last name.")
def choose_name(name):
global fname
global sname
fname = ""
sname = ""
global errors_list
try:
no_letters = any(c.isalpha() for c in name)
no_spaces = name.count(" ") == 0
digits = any(c.isdigit() for c in name)
symbols = any(not c.isalnum() and not c.isspace() for c in name)
many_spaces = name.count(" ") > 1
first_space = name[0] == " "
last_space = name[-1] == " "
if no_letters == False:
errors_list.append("It has no letters")
if no_spaces == True:
errors_list.append("It has no spaces")
else:
namesplit = name.split(" ")
fname = namesplit[0]
sname = namesplit[1]
pass
if fname and sname is not "":
bad_length = (float(len(fname)) < 3 or float(len(fname)) > 12) or float(len(sname)) < 4 or float(len(sname) > 15)
if bad_length == True:
errors_list.append("One of your names has an unrealistic size")
pass
else:
bad_length = (float(len(name)) < 3 or float(len(name)) > 12)
if bad_length == True:
errors_list.append("It has an unrealistic size")
pass
if digits == True:
errors_list.append("It has digits")
pass
if symbols == True:
errors_list.append("It has symbols")
pass
if many_spaces == True:
errors_list.append("It has more than one space")
pass
if first_space == True:
errors_list.append("The first letter is a space")
pass
if last_space == True:
errors_list.append("The last letter is a space")
pass
except IndexError:
print("You must write something. Try again.")
name = input("My name is ").title()
choose_name(name)
name = input("My name is ").title()
choose_name(name)
while True:
if len(errors_list) != 0:
print("Your name has these errors:")
for i in errors_list:
print(" " + str(errors_list.index(i) + 1) + "- " + i + ".")
print("Try again.")
errors_list.clear()
name = input("My name is ").title()
choose_name(name)
else:
print("Nice to meet you, " + fname + " " + sname + ".")
break
Result when I type the name '----... '
Hi. Tell me your first and last name.
My name is ----...
Your name has these errors:
1- It has no letters.
2- It has symbols.
3- It has more than one space.
4- The last letter is a space.
Try again.
My name is
I'm writing a simple program that is basically a signup program for a run. I am very new to python, but cant seem to find out why this isn't working. My error message is saying something is wrong with line 9. I would really appreciate if someone could help me work this out. I have been looking around for ages trying to find solutions, it's probably a very easy mistake.
Cheers!!
allnames = []
allages = []
allgenders = []
alltimes = []
allhouses = []
more = "yes"
print "---- RUN ----"
while (more) == "yes":
runnername = input("Input runner name:")
allnames.append(runnername)
print str(allnames)
Thanks for all the help! Got it now. It's for NAT 5 Computing so i'm very new and inexperienced. Appreciate everyones answers!!
Use this:
while (more == "yes"):
instead of :
while (more) == "yes":
and it should work fine.
Change:
input() to raw_input()
Read more here:
What's the difference between raw_input() and input() in python3.x?
You're in an infinite loop. Try this:
allnames = []
more = "yes"
print "---- RUN ----"
while more == "yes":
runnername = raw_input("Input runner's name: ")
allnames.append(runnername)
if len(allnames) == 5:
more = "no"
print allnames
Change the condition in if len(allnames) == 5 according to your requirement.
in this code you have looking ages also. In your code you miss the '()' bracket in print statment and also miss secound time run statment for ages.
allnames = []
allages = []
allgenders = []
alltimes = []
allhouses = []
more = "yes"
print("---- RUN ----")
while (more) == "yes":
runnername = input("Input runner name:")
allnames.append(runnername)
print(str(allnames))
runnerages = input("Input runner ages:")
allages.append(runnerages)
print(str(allages))
You are getting error beacuse of input(). Replace it with raw_input() for python2.X .
Then try this way :
allnames = []
allages = []
allgenders = []
alltimes = []
allhouses = []
more = "yes"
print "---- RUN ----"
while (more) == "yes":
runnername = raw_input("Input runner name:")
allnames.append(runnername)
print str(allnames)
N.B: python2.X
While working on my program I have run into a problem where the information stored in Menu option 1 is not being transferred to Menu option 2. As you can see it is correctly stored when in menu one. When it returns to go to menu option 2 its like it never went to option 1.
update #1:
some suggestions I've had is to understand scope? from what I can tell the program is not passing the data along to its parent program even though I've typed out return in each of the definitions.
#Must be able to store at least 4 grades
#Each class can have up to 6 tests and 8 hw's
#Weighted 40%*testavg 40% hw average attendance is 20%
#User must be able to input a minimum grade warning
#after each test the your program must calculate the students average and issue warning if necessary
##Define the Modules##
import math
def menu (a): #2nd thing to happen
menuend = 'a'
while menuend not in 'e':
menuend = raw_input("Type anything other then 'e' to continue:\n")
print "What would you like to do ?"
menudo = 0
print "1 - Enter Courses\n2 - Select Course to Edit\n3 - Save File\n4 - Load File\n5 - Exit\n"
menudo = input("Enter Selection:")
if (menudo == 1):
menuchck = 0
menuchck = raw_input("\nYou have entered #1 (y/n)?:\n")
if menuchck in ["Yes","yes","y","Y"]:
x = m1()
else:
print "I'm sorry,",nam,",for the confusion, lets try again\n"
menu()
elif (menudo == 2):
menuchck1 = 0
menuchck1 = raw_input("\nYou have entered #2 (y/n)?:\n")
if menuchck1 in ["Yes","yes","y","Y"]:
x = m2()
else:
print "I'm sorry,",nam,",for the confusion, lets try again\n"
menu()
elif (menudo == 3):
print "Entered 3"
elif (menudo == 4):
print "Entered 4"
else:
print "Anything Else Entered"
def course(): #3rd thing to happen
b = {}
while True:
while True:
print "\n",name,", please enter your courses below ('e' to end):"
coursename = raw_input("Course Name:")
if (coursename == 'e'):
break
will = None
while will not in ('y','n'):
will = raw_input('Ok for this name : %s ? (y/n)' % coursename)
if will=='y':
b[coursename] = {}
print "\n",name,", current course load:\n",b
coursechck = None
while coursechck not in ('y','n'):
coursechck = raw_input("Are your courses correct (y/n)")
if coursechck =='y':
return b
else:
b = {}
print
##Menu Options##
def m1():
a = course()
return a
def m2():
print "Excellent",name,"lets see what courses your enrolled in\n"
print x
return x
###User Input Section###
name = raw_input("Enter Students Name:\n")
a = {}
menu(a)
raw_input("This is the end, my only friend the end")
In your if-elif blocks in the do==1 case, you write m1(), but for the last case, you write x=m1(). You should have the latter everywhere (by typing m1() you only run the function, but do not store the returned x anywhere).
By the way, you can avoid this if-elif confusion using if chck in ["Yes","yes","Y","y"]: