Testing user input against a list in python - python

I need to test if the user input is the same as an element of a list, right now I'm doing this:
cars = ("red", "yellow", "blue")
guess = str(input())
if guess == cars[1] or guess == cars[2]:
print("success!")
But I'm working with bigger lists and my if statement is growing a lot with all those checks, is there a way to reference multiple indexes something like:
if guess == cars[1] or cars[2]
or
if guess == cars[1,2,3]
Reading the lists docs I saw that it's impossible to reference more than one index like, I tried above and of course that sends a syntax error.

The simplest way is:
if guess in cars:
...
but if your list was huge, that would be slow. You should then store your list of cars in a set:
cars_set = set(cars)
....
if guess in cars_set:
...
Checking whether something is present is a set is much quicker than checking whether it's in a list (but this only becomes an issue when you have many many items, and you're doing the check several times.)
(Edit: I'm assuming that the omission of cars[0] from the code in the question is an accident. If it isn't, then use cars[1:] instead of cars.)

Use guess in cars to test if guess is equal to an element in cars:
cars = ("red","yellow","blue")
guess = str(input())
if guess in cars:
print ("success!")

Use in:
if guess in cars:
print( 'success!' )
See also the possible operations on sequence type as documented in the official documentation.

#Sean Hobbs:
First you'd have to assign a value to the variable index.
index = 0
You might want to use while True to create the infinite loop, so your code would be like this:
while True:
champ = input("Guess a champion: ")
champ = str(champ)
found_champ = False
for i in listC:
if champ == i:
found_champ = True
if found_champ:
print("Correct")
else:
print("Incorrect")

Related

How to add values to list without deleting already exsists

so as i have written in title i have problem with 2 things, mainly i want to add values in to a list and dont delete already existing, but i cant figure out how to do it, for now when im writing something everything old gets deleted. My second problem is that i cant make condition to use upper letter T and lower t, can anyone help me? here is the code:
import pickle
zadania = []
a = input("Do you want to add value? T/N")
while True:
if a == 'T':
zadania.append(str(input('Write what you want to add: ')))
a = input("Do you want add something else? T/N")
elif a == 'N':
break
else:
while a not in 'TN':
print("Wrong value")
a = input("Do you want add something else? T/N")
with open('zad', 'wb') as fp:
pickle.dump(zadania, fp)
zadania = []
This always starts with an empty list. If you don't want that, then you should do something different. For example, you could check if the file you wrote before already exists. If it does, load it before getting more items.
For lower and upper case you could use if check as follows:
if a.lower()=="t":
pass
OR
if a.upper()=="T":
pass
Regarding list, your list is adding new element in existing list.
But if you are loading your list from pickle then you should first initialize zadania to pickle value and not directly [] empty. If pickle is not having any value then assign [] else pickle value.

How to remove a name from a list if user doesn't accept invitation

Here's what I have been asked to do:
Create a program that will use 2 Lists to store details about guests invited to a wedding.
Method:
Set up two lists - one for the names of the guests and one to store whether the invitation has been accepted or not. NOTE the second array should be a list of boolean elements that are initially set to false
You need to ask for the names of the guests and then ask if they are attending the wedding.
Print out a list of only those who will attend.
Here is what I have done:
names = [""]*10
accept = [False]*10
accepted = [""]*10
counter = 10
for counter in range(0,10):
names[counter] = str(input("What is your name?"))
accepted[counter] = input("Are you accepting the invitation?")
if accepted[counter] == "Yes" or accepted[counter] == "yes":
accept[counter] = True
else:
names[counter] = ""
print("Here is a list of peoples names whom are attending:")
print(names)
And here is what my teacher said:
Works but can you think of a better way to display the names of those attending?
Are you able to help me work this out, I think the teacher wants me to remove the name from the list however I don't know how to do this. I have tried using pop() but I just don't understand it. :(
The names list is supposed to contain all the people who were invited, you shouldn't replace a name with an empty string, because then it won't be complete.
Use a loop to print the names of just the people who are attending, using the index in the corresponding element in the accepted list.
There's also no need for accepted to be a list. Just use an ordinary variable for the current answer.
names = [""]*10
accept = [False]*10
for counter in range(0,10):
names[counter] = input("What is your name?")
accepted = input("Are you accepting the invitation?")
if accepted.lower() == "yes":
accept[counter] = True
print("Here is a list of peoples names whom are attending:")
for i, attending in enumerate(accept):
if attending:
print(names[i])
pop() is used to remove a value from a list. If used without parameters, it will remove the last value. If given a value it will "pop it", or delete it in other words, and print the deleted value.

Question regarding comparison of two lists in Python

I'm coding a small game for fun where the computer randomly chooses 4 colors as a secret code and the user's job is to guess what they think the colors are, with clues being given based on how close you are to the secret code. When an element in your guess list is a match, the program appends a clue value of 2 to a new list and if the element in your guess list doesn't match the position but occurs in the secret code list, it should append a value of 1 to our clue list.
A problem I'm having is when you compare your list of guesses with the secret code list. Here is an example:
say if the computer secret code is a list with 4 elements as shown: ["Blue", "Yellow", "Green", "Red"]
and your guess is ["Blue", "Blue", "Green", "Red"], the program returns a clue list[2, 1, 2, 2]. I want it to return [2, 2, 2] because I don't want to double count the Blue guess in the guess list when it only occurs once in the secret code.
Here is the code for the function so far.
def get_clue(secret_code, guess_list):
clue_list = []
for i in range(len(guess_list)):
if guess_list[i] == secret_code[i]:
clue_list.append(2)
elif guess_list[i] != secret_code[i] and guess_list[i] in secret_code:
clue_list.append(1)
else:
clue_list = clue_list
print("Your Clue is : ", clue_list)
return clue_list
The first change I would make is to take out some redundant code:
The condition of the elif can be shortened - we already know that guess_list[i] != secret_code[i] if the first if-statement didn't get executed, so we don't need to check for that explicitly.
Additionally, your else branch does nothing, so why even include
it? You can safely remove that as well.
I would remove the print statement as well. I wouldn't expect a
function with a prefix of get_ to have a printing side-effect. If
you need to print the contents of the clue_list, do that in the
calling-code once get_clue returns.
With these changes, your code looks like this:
def get_clue(secret_code, guess_list):
clue_list = []
for i in range(len(guess_list)):
if guess_list[i] == secret_code[i]:
clue_list.append(2)
elif guess_list[i] in secret_code:
clue_list.append(1)
return clue_list
Here's the second round of changes I would make:
The name get_clue isn't entirely accurate to describe this
function. This function returns a list of clues, so I think a better
name would be get_clues.
secret_code isn't a great name for the first parameter. It's a list
of secrets. I would either call it secrets or secret_codes.
guess_list isn't a great name for the second parameter. We can see
that this object is a list by virtue of the fact that we are doing
list-like things with it, so don't include "list" in the name. I
would ditch this nasty habit of including the type of the variable in
the variable's identifier. A better name would be guesses.
Same thing goes for clue_list. We already know it's a list. Don't
make "list" part of the name. A better name would be clues.
Instead of working with indices (plural of "index"), we can get more
Pythonic by using zip to iterate through both lists at the same
time.
With these changes your code now looks like this:
def get_clues(secrets, guesses):
clues = []
for secret, guess in zip(secrets, guesses):
if guess == secret:
clues.append(2)
elif guess in secrets:
clues.append(1)
return clues
With that out of the way, you said:
I want it to return [2, 2, 2] because I don't want to double count the
Blue guess
Wouldn't you want the clues to always have four elements, though? If my guess is ["Blue", "Blue", "Blue", "Blue"], and get_clues returns [2], I have no way of knowing where Blue actually is.
You could use a set to keep track of previously made guesses:
def get_clues(secrets, guesses):
clues = []
previous_guesses = set()
for secret, guess in zip(secrets, guesses):
if guess == secret:
clues.append(2)
elif guess not in previous_guesses and guess in secrets:
clues.append(1)
previous_guesses.add(guess)
return clues

Best alternative to using if statement?

I am trying to break out of a bad habit of using if/else too frequently. I am new to how functions work and the proper way to call them but I am constantly researching the correct way to implement them with my code. The code that I am making is suppose to check for 3 different words and if the word is not in the input then the user will receive a statement that says "rejected" if the word is correct it will say "accepted". The issue that I am facing is getting my program to work correctly. So far I have set up my program to check each index of the word and if it matches the full word it will be marked as accepted. I am trying to figure out the correct way to add a rejected flag and to avoid the error that I recieve after running this program.
def checker():
q0 = input("enter word:")
if (q0[0]) +(q0[1]) == "if":
print ("accepted")
if (q0[0]) + (q0[1]) + (q0[2]) + q0[3] == "else":
print("accepted")
if(q0[0]) + (q0[1]) == "do":
print("accepted")
else:
print("rejected")
checker()
For this program, I am not going to use a dictionary so I can correctly challenge myself and implement this in an automata fashion. How can I implement this code without getting the string index out of range error. I tried to put break after my print statement but it doesn't work.
Thanks in advance to everyone. This is my first post so if I have made any mistakes in my post please let me know!
Here's an extensible one-liner for you:
def check():
q = input().strip()
acceptable = {'if', 'else', 'do'}
print('accepted' if q in acceptable else 'rejected')
The variable acceptable is set; a data structure which is very quick to check if something is inside of it. You can modify this set (or pass it to check as an argument!) to change the range of acceptable words without changing the control flow of the program (as you would in your original if/else implementation that you're laudably trying to move away from).
EDIT: I guess it's not strictly a 'one-liner'...
First, why do you access each character of the input string, then concatenate them again, then compare to a target string("if", "else", "do")?
Second, why do you use if statements repeatedly if matching either one of them will lead to the same result (print("accepted")?
Try this:
def checker():
q0 = input("enter word:")
if q0 in ["if", "else", "do"]:
print("accepted")
else:
print("rejected")
checker()
Now, you just compare a string q0 to another (each element of the list ["if", "else", "do"]). Also, the first hit in the list will make stop comparing anymore and will continue on to print "accepted".
++ Just to let you know why are you seeing "index out of range error", you are accessing each character of q0 without knowing how many there are. So if the user inputs a string like a, there's no q0[1] or q0[2], but you're asking your program to access it. Thus index out of range error.
You can do this with a for loop and one if statement if that is better for you. Simply put all the accepted values into a list and check if each word is in q0.
def checker():
q0 = input('enter word:')
for i in ['if', 'else', 'do']:
result = ('accepted' if i in q0 else 'rejected')
if result == 'accepted':
break
print(result)
you can do it as one liner with lambda function.
checker = lambda q: print("accepted" if q in ["elif", "if", "else"] else "rejected")
checker()
here is a sample
>>> checker = lambda q: print("accepted" if q in ["elif", "if", "else"] else
"rejected")
>>> checker("if")
accepted
>>> checker("fool")
rejected

python, loops: searching against a list to see if item is present, appending to new list

I am trying to make a program where my students will enter their ID numbers so I can (later in the code) automate sending attendance, and record who has handed in homework and who hasn't so emails can be sent to parents. I have everything else made, but I cannot get the inputting of student ID's working.
What I am trying to do:
1)make sure that their input is 7 characters long
2)check their ID exists in 'fakeID'
2a)have the students confirm their name from 'classNames' with a y/n.
2b) append their name into inputIDList
3) if the input is == to 9999990 exit the loop.
What it is doing:
1) asking for input
2) moving on in the code and not looping
3) not appending inputIDList
I think I am making this too complicated for my current skill level.
edit:
The loop is not checking to see if the inputed ID is in my fakeID list.
Also, it isnt looping for, so once the input is entered it continues on with the next set of code.
edit2:
updated code that works. :D
fakeID = ['1111111','1111112','1111113','1111114','1111115']
classNames = ['name1', 'name2', 'name3', 'name4', 'name5']
toplist = list(zip(fakeID, classNames))
inputIDList =[]
def inputID():
while True:
id = input('Please enter your student ID and hit Enter')
if id == '9999990':
print('Done')
break
if id in fakeID:
inputIDList.append(id)
print('recorder')
continue
if id not in fakeID:
print('I do not know this ID. Please try again.')
continue
If I understood your problem correctly then I suppose that you are trying to save the ID numbers of the students in inputIdList and then check whether a particular ID is in inputIdList or not. In the last if condition you are trying to compare a List type object with a String type object which will definitely throw an TypeError. Instead define the following function and call it in the if condition.
def check_list(id):
try:
inputIdList.index(id)
return True
except TypeError:
return False
list.index() method tries to find the element in the list and returns the index number of the element. And then call this function in your if condition.
if check_list('9999990'):
print('done')
#break
Furthermore there is no need to assign inputIdList = [""] if you have already intialized it to inputIdList = [].
If the problem persists please send the output in the thread.
Here is something to get you started:
fakeID = {'1111111','1111112','1111113','1111114','1111115'}
while True:
id = input('Please enter your student ID and hit Enter')
if id == '9999990':
print('Done')
break
if id not in fakeID:
print('I do not know this ID. Please try again.')
continue
as Abarnert said you need to restructure your method. but I think I found where you were stuck.
after you have checked for the length of input number, you should check whether that number matches any fakeID,and get the corresponding class name.
so your first loop should be like this
for i in toplist:
rather than
for i in [i for i,x in enumerate(inputIDList) if x == fakeID]:
since inputIDList is empty your program will not go inside the loop. And inside the changed loop you should be checking
if s == fakeID
This is the limit of what I could understand of your desired operation. But if you need further help just ask.
cheers.

Categories

Resources