我正在尝试为基于文本的基本解决方案创建登录注册系统
注册系统工作正常,但在尝试登录时,它只接受外部文件最后一行的用户名和密码,即使输入的用户名和密码正确。我不确定问题是什么,因为只接受文件的最后一行。谢谢您的帮助!
def loginSys():
("=========LOGIN=========")
f = open("loginDetails.txt","r")
for line in open("loginDetails.txt","r").readlines():
loginInfoP1 = line.split()
print("Player One, enter your details first!")
correctDetailsP1 = 0
while correctDetailsP1 == 0:
usnmAttemptP1 = input("Enter your username\n")
pswdAttemptP1 = input("Enter your password\n")
if usnmAttemptP1 == loginInfoP1[0] and pswdAttemptP1 == loginInfoP1[1]:
correctDetailsP1 += 1
print("You have successfully logged on " + usnmAttemptP1 + "!")
else:
print("Either your username or password is incorrect! Please try again")
f.close()
x = open("loginDetails.txt","r")
for line in open("loginDetails.txt","r").readlines():
loginInfoP2 = line.split()
#print(loginInfoP2)
print("Player Two, enter your details now!")
correctDetailsP2 = 0
while correctDetailsP2 == 0:
usnmAttemptP2 = input("Enter your username\n")
pswdAttemptP2 = input("Enter your password\n")
if usnmAttemptP2 == loginInfoP2[0] and pswdAttemptP2 == loginInfoP2[1]:
correctDetailsP2 += 1
print("You have successfully logged on " + usnmAttemptP2 + "!")
else:
print("Either your username or password is incorrect! Please try again")
x.close()
startGame()
谢谢
再看一下这里发生的事情:
f = open("loginDetails.txt","r")
for line in open("loginDetails.txt","r").readlines():
loginInfoP1 = line.split()
您正在打开文本文件,然后迭代其所有行。对于每一行,您将其内容放在loginInfoP1
上。对于每一行。
这意味着在for循环之后,loginInfoP1
的内容实际上将是最后一个迭代行,它是文件的最后一行。
如果这些行遵循某个顺序,即第一行是玩家1的凭证,第二行是玩家2的凭证;那么你可以返回一个生成器(yield
)并按需迭代这些行:
def get_login_information(file):
with open(file, 'r') as fh:
for line in fh:
yield line.split()
def loginSys():
login_information = get_login_information('loginDetails.txt')
print("=========LOGIN=========")
print("Player One, enter your details first!")
loginInfoP1 = next(login_information) # <------
correctDetailsP1 = 0
while correctDetailsP1 == 0:
usnmAttemptP1 = input("Enter your username\n")
pswdAttemptP1 = input("Enter your password\n")
if usnmAttemptP1 == loginInfoP1[0] and pswdAttemptP1 == loginInfoP1[1]:
correctDetailsP1 += 1
print("You have successfully logged on " + usnmAttemptP1 + "!")
else:
print("Either your username or password is incorrect! Please try again")
print("Player Two, enter your details now!")
loginInfoP2 = next(login_information) # <------
correctDetailsP2 = 0
while correctDetailsP2 == 0:
usnmAttemptP2 = input("Enter your username\n")
pswdAttemptP2 = input("Enter your password\n")
if usnmAttemptP2 == loginInfoP2[0] and pswdAttemptP2 == loginInfoP2[1]:
correctDetailsP2 += 1
print("You have successfully logged on " + usnmAttemptP2 + "!")
else:
print("Either your username or password is incorrect! Please try again")
startGame()
这里:
for line in open("loginDetails.txt","r").readlines():
loginInfoP1 = line.split()
# code using loginInfoP1 here
你正在迭代文件的内容并在每次迭代时重新绑定loginInfoP1
- 所以很明显,一旦for循环结束,loginInfoP1
就会包含最后一行的值。
你想要的是从整个登录数据构建一个dict(使用用户名作为密钥):
accounts = {}
# NB : make sure we close the file after use
with open("loginDetails.txt") as f:
# nb: files are iterable, no need to read the whole
# file at once
for line in f:
# make sure we don't have an empty line
line = line.strip()
if not line:
continue
username, passwd = line.split()
accounts[username] = passwd
然后你只需检查字典:
usnmAttemptP1 = input("Enter your username\n").strip()
pswdAttemptP1 = input("Enter your password\n").strip()
if usnmAttemptP1 in accounts and accounts[usnmAttemptP1] == pswdAttemptP1:
# ok
请注意,您的“登录”代码对于两个玩家完全相同,因此您可以在专用函数中重构此代码。此外,您的执行流程是错误的 - 登录功能没有业务开始游戏,它应该只返回一些值(用户的帐户详细信息或只是一个指示用户正确登录的布尔值)给它的来电者并让呼叫者携带继续下一步:
def read_accounts():
accounts = {}
# NB : make sure we close the file after use
with open("loginDetails.txt") as f:
# nb: files are iterable, no need to read the whole
# file at once
for line in f:
# make sure we don't have an empty line
line = line.strip()
if not line:
continue
username, passwd = line.split()
accounts[username] = passwd
return accounts
def auth_user(accounts, prompt):
print(prompt)
max_attempts = 10 # let's not loop forever
correctDetailsP1 = 0
while correctDetailsP1 < max_attemps:
usnmAttemptP1 = input("Enter your username\n")
pswdAttemptP1 = input("Enter your password\n")
if usnmAttemptP1 in accounts and accounts[usnmAttemptP1] == pswdAttemptP1:
correctDetailsP1 += 1
print("You have successfully logged on " + usnmAttemptP1 + "!")
return True
else:
print("Either your username or password is incorrect! Please try again")
# failed
return False
def main():
accounts = read_accounts()
for prompt in ("Player One, enter your details first!", "Player Two, enter your details now!"):
if not auth_user(accounts, prompt):
return False
startGame()
if __name__ == "__main__":
main()
作为旁注:我知道这不是关键任务软件,但存储未加密的密码是一个非常糟糕的主意。规范的方法是存储加密的密码,并在登录时加密用户给出的密码(当然使用相同的算法)并将其与存储的加密密码进行比较。