Manipulating Strings to return concatenated username - python

Whenever I try to display the Firstname with first initial attached to the end, I get an out of string index range error!
def ForeName():
return raw_input("Please enter your Forename: ")
def MiddleName():
return raw_input("please enter your middle name, if none leave blank: ")
def LastName():
return raw_input("Please enter your last name: ")
def Test():
ForeNameT = ForeName()
MiddleNameT = MiddleName()
LastNameT = LastName()
if not MiddleNameT:
first_username = ForeNameT[0:] + LastNameT[0]
elif ForeNameT:
first_username = ForeNameT[0:][0] #i want to display the first name with the initial of the first name attached to the end of the first name.
else:
first_username = ForeNameT[0:] + MiddleNameT[0]
return first_username
print Test()

You can add an argument to Test function by doing def Test(name_method): and then set if to if name_method == 'without_middlename':.
Try to figure out yourself what you would change print Test() to.

I think i know what you are trying to do, try changing your Test function:
def Test():
ForeNameT = ForeName()
MiddleNameT = MiddleName()
LastNameT = LastName()
if not MiddleNameT:
first_username = ForeNameT + LastNameT
else:
first_username = ForeNameT + MiddleNameT + LastNameT
return first_username
notice the changes to the variable names vs. the function names and the return value so print has something to actually print

Related

Python error: global name Xis not defined

I've attached my Python Code below for a program our teacher as gave us in school. I keep on encountering an error "global name 'passwordValid' is not defined" and cannot find any way to solve this. This error occurs in the Password.append(passwordValid) line.
global firstName
global lastName
global cateGory
global passwordValid
global passwordNew
firstName = ""
lastName = ""
cateGory = ""
def newMember():
#Recieve user input to assign values to variables
firstName = str(input("Please enter your first name."))
lastName = str(input("Please enter your last name."))
#Validation to reject unspecifyed category input
cateGoryValid = False
while cateGoryValid == False:
cateGory = str(input("PLease enter your category from the following: (Junior,Adult,Senior)"))
cateGory = cateGory.lower()
cateGory = cateGory.capitalize()
if cateGory == "Junior" or cateGory == "Adult" or cateGory == "Senior":
cateGoryValid = True
else:
cateGory = str(input("PLease enter your category from the following: (Junior,Adult,Senior)"))
def passwordValidation():
#initalising global variables
#Creating Variables
Valid = False
firstCharacter =""
firstValue = 0
lastCharacter =""
lastValue = 0
passwordNew = ""
passwordValid = []
#Create conditional loop to validate the password
while Valid == False:
passwordNew = str(input("Please enter a new password"))
#Assigns both the first and last values of the password as variables
firstCharacter = passwordNew[0]
lastCharacter = passwordNew[-1]
#Assigns both values as ASCII characters
firstValue = ord(firstCharacter)
lastValue = ord(lastCharacter)
#Ensures password is within boundaries using ASCII characters
if firstValue >= 65 and firstValue and lastValue >= 35 and lastValue <=37:
passwordValid = passwordNew
Valid = True
return passwordValid
def valuesAppend():
return passwordValid
global Forname
global Surname
global Category
global Password
Forename = [""]
Surname = [""]
Category =[""]
Password = [""]
Position = 0
Members = ["","","",""] * 11
#Reading the text file
file = open("members.txt","rt")
#Create loop to assign all fields to a record
for line in file:
fields = line.split(",")
Members[Position] = [fields[0],fields[1],fields[2],fields[3]]
#Appending the fields into a global variable
Forename.append(fields[0])
Surname.append(fields[1])
Category.append(fields[2])
Position = Position + 1
#Assigning new variables into the record
Forename.append(firstName)
Surname.append(lastName)
Category.append(cateGory)
Password.append(passwordValid)
file.close
def categoryInfo():
totalMembers = 0
totalMembers = len(Forename)
for counter in range(len(Forename)):
print(Forename[counter], Surname[counter],Category[counter])
print("There are:",Category.count("Junior"),"Junior members.")
print("There are:",Category.count("Adult"),"Adult members.")
print("There are:",Category.count("Senior"),"Senior members.")
print("The current total is:",totalMembers,"members.")
def main():
newMember()
passwordValidation
valuesAppend()
categoryInfo()
main()
There seems to be a few bits wrong with the way your code is structured.
Firstly, you don't need to define your variables as globals, you only need to use 'global variable' within the local scope of a function so it knows it's accessing a global variable e.g.
password = "Password"
print(password)
# prints "Password"
def update_pass():
global password # saying that the 'password' variable in this function refers to the global variable called 'password'
password = "New password"
update_pass()
print(password)
# prints "New password"
Secondly, this block of code doesn't fall under any function and therefore would try to run before your main() function. Ensure this is correctly indented
#Assigning new variables into the record
Forename.append(firstName)
Surname.append(lastName)
Category.append(cateGory)
Password.append(passwordValid)
Lastly, this function is quite strange
def valuesAppend():
return passwordValid
global Forname
# ...
Here, your valuesAppend() function will try to return passwordValid and that's it, once a return happens the rest of the code below isn't ran so you'll get no other use from your function
Hope this helps

How can I check if a string has personalized errors?

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

Data from input not being accepted as arguments

When I enter data in to my function directly I get the right output but when I use input from the user to fill the list nothing happens. I don't get any errors or output what so ever.
The data from input should enter the list and the index from input should be deleted from the list.
#!/usr/bin/env python3
#class definitions
class record:
def __init__(self,telephone,lastname,firstname):
self.telephone = telephone
self.lastname = lastname
self.firstname = firstname
def __str__(self):
return f"Last name: {self.lastname}, First Name: {self.firstname}, Telephone: {self.telephone}"
class PhoneBook:
def __init__(self):
self.phonebook = []
def addrecord(self, record):
self.phonebook.append(record)
return self.phonebook.index(record)
def deleterecord(self, i):
self.phonebook.pop(i-1)
def printphonebook(self):
x = 1
for entry in self.phonebook:
print(x,'. ',entry,sep='')
x = x + 1
#Main
select = None
while select != 'exit':
ph = PhoneBook()
ph.addrecord(record(515,'fin','matt'))
ph.addrecord(record(657,'fisher','bill'))
select = input('Main Menu \n1. show phonebook \n2. add record \n3. remove record\nor "exit" to exit program\n')
test = False
while test == False:
if select == '1':
ph.printphonebook()
test = True
elif select == '2':
x = int(input('Enter telephone number.\n'))
y = str(input('Enter last name.\n'))
z = str(input('Enter first name.\n'))
ph.addrecord(record(x,y,z))
test = True
elif select == '3':
i = int(input('Enter the record number youd like to delete.\n'))
ph.deleterecord(i)
test = True
elif select == 'exit':
break
else:
print('Invalid selection. Please try again.')
test = True
The desired output would be getting the data to correctly enter and exit the list based on my x, y and z inputs and take out the specified index of the list based on the i input.
You clear and create a new Phonebook() object every time your first while loop runs.
I'm new and not skilled enough to fix every problem in a short amount of time.
You don't see your new entries, because they get wiped out every time.
Try using one while loop and a switch statement.

Python: Error passing user inputed variables between functions

I am currently trying to build a simple ATM program(text based) from scratch. My problem is passing the user inputed variables between functions. The error I'm getting is ( init() takes exactly 3 arguments (1 given) ). Could someone explain what is happening and what I'm doing wrong?
class Atm:
acctPass = 0
acctID = 0
def __init__(self, acctID, acctPass):
#self.acctName = acctName
#self.acctBal = acctBal
self.acctPass = acctPin
self.acctID = acctID
def greetMenu(self, acctID, acctPass):
while acctPass == 0 or acctID == 0:
print "Please enter a password and your account number to proceed: "
acctpass = raw_input("Password: ")
acctID = raw_input("Account Number: ")
foo.mainMenu()
return acctPass, acctID # first step to transfer data between two functions
def mainMenu(self, acctID, acctPass):
print ""
acctpass = foo.preMenu(acctPass, acctID)
print acctPass
print "Made it accross!"
def deposit():
pass
def withdrawl():
pass
foo = Atm()
foo.greetMenu()
foo = Atm()
passes exactly 1 argument to Atm.__init__ -- the implicit self. The other two arguments (acctId and acctPass) are missing so python complains.
It looks to me like you can get rid of __init__ all together and bind the instance attributes in greetMenu:
class Atm:
acctPass = 0
acctID = 0
def greetMenu(self):
while self.acctPass == 0 or self.acctID == 0:
print "Please enter a password and your account number to proceed: "
self.acctpass = raw_input("Password: ")
self.acctID = int(raw_input("Account Number: "))
self.mainMenu()
# etc.
Here you'll still probably need to mess with mainMenu a bit to get it working (note now we're not passing the arguments around via function call arguments -- The values are stored on the class).
Thats the constructor called with foo = ATM()
def __init__(self, acctID=0, acctPass=0):
adding the =0 to the parameters initializes them to 0
and you have now overrode the constructor to accept 1,2 or 3 values.
in the greetmenu
def greetMenu(self, acctID, acctPass):
while acctPass == 0 or acctID == 0:
print "Please enter a password and your account number to proceed: "
acctpass = raw_input("Password: ")
acctID = raw_input("Account Number: ")
foo.mainMenu()
return acctPass, acctID # first step to transfer data between two functions
you need to either send in the parameters to the function ATM.greetmenu(1234,'pwd') or use the ones defined in the class like this.
def greetMenu(self):
while self.acctPass == 0 or self.acctID == 0:
print "Please enter a password and your account number to proceed: "
self.acctpass = raw_input("Password: ")
self.acctID = raw_input("Account Number: ")
foo.mainMenu()
#return acctPass, acctID # first step to transfer data between two functions

Python return function not working for me

I have the following code:
#gets the filename from the user
b= input("Please enter a file name to be opened: ")
a = (b+".txt")
#main data storage and other boolean options
data =[]
result1 =[]
on = True
#File reading in main body with try and except functionality.
try:
check = open(a, 'r')
line =check.readlines()
for items in line:
breakup= items.split()
number, salary, position, first, oname1, oname2, last = breakup
data.append(tuple([last, first + ' ' + oname1 + ' ' + oname2, number, position, salary]))
except IOError as e :
print("Failed to open", fileName)
#Employee creation function, takes the line and stores it in the correct position.
def employee_creation():
result = [((item[0] +", "+ item[1]).ljust(30), int(item[2]), item[3].ljust(15), int(item[4])) for item in data]
for items in result:
result1.append((items[0][0:30], format(items[1], "^5d"), items[2][0:15], "£"+format((items[3]),"<8d")))
return(result)
employee_creation()
print(result)
while on == True:
print("Please select what option you would like to use to search for employees:")
option = int(input("""
1 - Salary (X to X)
2 - Job Titlle
3 - Name, Payroll Number
:"""))
if option == 1:
start = input("What range would you like to start from: ")
end = input("What is the maximum range you would like :")
for items in result:
print(items[3])
if items[3]>start and items[3]<end:
print(items)
else:
print("No employees with this information can be found")
on= False
else:
on= False
However my def employee_creation() doesn't actually return result. I need it to make it a global variable so that I can use it to launch personal querys against the data.
Can anyone see why its not working?
No need to use the evil global variables. You forgot to store the result of your function to another variable.
def employee_creation():
result = [((item[0] +", "+ item[1]).ljust(30), int(item[2]), item[3].ljust(15), int(item[4])) for item in data]
for items in result:
result1.append((items[0][0:30], format(items[1], "^5d"), items[2][0:15], "£"+format((items[3]),"<8d")))
return result # no need for () here
result = employee_creation() # store the return value of your function
print(result)

Categories