# 银行管理系统
"""
思考:
1.怎么随机产生不重复的6位数字?
2.怎么存储银行卡信息?
3.怎么引用自己写的模块
介绍:
从早期的钱庄到现如今的银行,金融行业在不断地变革,随着科技的发展,计算机的普及,
计算机技术在金融行业得到了广泛的应用。
银行管理系统是一个集开户、查询、取款、存款、转账、锁定、解锁、退出等功能的管理系统。
操作:本程序有两个系统,分别是管理员系统和普通用户系统,
初始管理员账户:123456,密码:123456
知识点:
1.类和对象的使用:类的定义、属性和方法的调用、类方法和静态方法的封装和调用
2.字典的使用;本程序是有字典来存储数据的,包括字典的增、删、改、查、遍历
3.文件模块引用:我把本程序和之前写的程序(文本进度条)进行调用
4.循环/嵌套循环语句:while/ for
5.条件/嵌套条件语句:if/ elif/ else
6.跳转语句:break/ continue
7.函数封装:把单一重复的代码封装成一个函数
8.旗帜的使用:方便我们跳出多层循环体
不足(待改善):
1.本程序有一个bug还没改善:在普通用户登录操作输入金额时,不能输入字符,否则会报错
"""
# 定义一个类 ===================================================================
class Info:
# 定义一个字典,用于存储银行卡信息
__info = {'123456': ['周华', '(空)', '(空)', 0, '123456', '管理员']}
# 管理员账户
admin_account = '123456' # 缺点:不是私有属性,可以被外部调用
# 随机生成6位数账号(不重复) ==================================================
@staticmethod
def __random_num(min=100000, max=999999):
from random import randint # 导入random模块的randomint函数
Info.num = str(randint(min, max)) # 随机生成一个(100000-999999)的账户
if Info.__info == dict(): # 判断字典是否为空
return Info.num # 返回随机产生的账户
else:
# 调用账户查找函数,判断现在生成的随机账户是否与字典中的账户相同(保证唯一性)
if not Info.find_account(find=Info.num): # 如果不相同
return Info.num # 那就返回这个账户
else: # 如果有重复
Info.__random_num() # 那就在重新产生一个账户(递归函数)
return Info.num # 返回账户
# 账号开户 ====================================================================
@classmethod
def create_account(cls, name='(空)', id_card='(空)', phone_num='(空)', money=0, password='(空)', state='(空)'):
Info.account = Info.__random_num() # 调用私有方法,随机生成6位数账户,并赋值
# 把账户信息添加到字典中(字典添加元素),注意不可以使用update()添加元素
Info.__info[Info.account] = [name, id_card, phone_num, money, password, state]
return Info.account # 返回新生成的账户
# 查找账户 ===================================================================
@staticmethod
def find_account(find, container=None):
if not container: # 判断传入的container是否为None
container = Info.__info # 如果为None,那就赋值
for i in container: # 字典遍历查找账户
if find == i: # 判断是否存在此账户
return True # 如果存在此账户,那就返回True
return None # 此返回值是:在字典中不存在此账户,返回None
# 查找密码 ===================================================================
@classmethod
def find_password(cls, account, password):
# 先判断账号是否存在
if not Info.find_account(find=account, container=Info.__info):
return None # 账户错误
# 再判断此账号的密码是否正确
if password == Info.__info[account][4]:
return True # 账户和密码正确
return False # 账户正确,密码错误
# 账户锁定
@staticmethod
def account_lock(account):
# 在账户信息里添加旗帜(说明此账户已被锁定)
Info.__info[account][5] = '已锁定'
# 账户解锁
@staticmethod
def account_unlock(account):
Info.__info[account][5] = '(空)'
# 判断账户是否被锁定
@staticmethod
def whether_account_lock(account):
# 判断账户是否被锁定
if '已锁定' == Info.__info[account][-1]:
return False
return True
# 账户销户 ===================================================================
@staticmethod
def remove_account(remove):
# 判断此账户是否存在
if Info.find_account(remove):
Info.__info.pop(remove) # 如果存在,就删除此账户
return True # 删除此账户并返回True
return None # 如果此账户不存在,就返回False
# 打印账户 ===================================================================
@staticmethod
def output_account(account, scope=None):
# 遍历打印账户信息
for i in Info.__info:
# 判断传入的参数是否为‘all’
if scope == 'all':
account = i # 如果是‘all’,就赋值
# 打印账户信息
if account == i:
print(f'账户:{i}\t密码:{Info.__info[i][4]}', end='\t')
print(f'余额:{Info.__info[i][3]}¥\t姓名:{Info.__info[i][0]}', end='\t')
print(f'身份证:{Info.__info[i][1]}\t手机号:{Info.__info[i][2]}\t状态:{Info.__info[i][5]}')
# 修改普通账户信息 ==========================================================
@staticmethod
def change_account(account, position, info):
Info.__info[account][position] = info # 索引赋值
# 修改管理员账号 =============================================================
@staticmethod
def change_admin_account(account, new_account):
# 把新的管理员账户保存进系统,(因为字典的特点是不可重复,所以键相同,就覆盖,如果键不同,就赋值产生新的元素)
Info.__info[new_account] = Info.__info[account]
# 如果键不同,就删除原管理员账号
if new_account != account:
Info.__info.pop(account)
# 把新账户啊设置成管理员
Info.admin_account = new_account
# 删库跑路 ===================================================================
@staticmethod
def clear_account():
buf = Info.__info[Info.admin_account] # 管理员账户保存
Info.__info.clear() # 清空系统账户信息
Info.__info[Info.admin_account] = buf # 复原管理员账户
# 打印加载进度条
from loading import show_load
show_load(0.5)
# 打印普通账户信息 +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
@staticmethod
def output_info(account):
print(f'账户:{account}\t姓名:{Info.__info[account][0]}\t余额:{Info.__info[account][3]}¥')
# 账户存款 ====================================================================
@staticmethod
def user_depo(account, money):
Info.__info[account][3] += money
# 账户取款 ====================================================================
@staticmethod
def user_withdrawal(account, money):
Info.__info[account][3] -= money
# 外部调用私有属性接口 ========================================================
@staticmethod
def user_money(account):
return Info.__info[account][3]
# 定义一个菜单功能实现类(管理员)
class Realize:
# 打印标题 ===================================================================
@staticmethod
def show_title(info='', num=9, num1=0):
print(' ' * num1 + '=' * num + info + '=' * num) # 字符串拼接
# 管理员菜单打印 ==============================================================
@staticmethod
def admin_menu():
Realize.show_title(info='银行管理系统(管理员)', num=4)
print('1.账号开户\t\t2.账户销户')
print('3.账户锁定\t\t4.账户解锁')
print('5.账户查询\t\t6.账户修改')
print('7.删库跑路\t\t0.退卡')
# 输入编号(选择菜单功能) ======================================================
@staticmethod
def input_num(info=''):
print(info, end='')
return input()
# 判断账户是否存在 ============================================================
@staticmethod
def account_whether_exist(info):
while True:
account = input(info)
# 如果账户存在
if Info.find_account(account):
return account
# 退出
elif account == 'q':
Realize.show_title(info='返回菜单')
return False
print(f'账户:{account}不存在!(返回:q)')
# 选择确认 ===================================================================
@staticmethod
def option_affirm(account, info, num=9, num1=0):
message = f'请确认是否对账户:{account},进行{info}(Y/N):' # 字符串拼接
while True:
buf = input(message)
# 确定
if buf == 'y' or buf == 'Y':
Realize.show_title(info=f'{info}成功', num=num, num1=num1)
return True
# 反悔
elif buf == 'n' or buf == 'N':
print(f'账户:{account},{info}失败!')
return False
# 输入有误
print('输入有误!请输入字母:Y/N')
# 账号开户 ===================================================================
@staticmethod
def set_up_account():
# 输入开户信息
Realize.show_title(info='账号开户')
name = input('请输入您的姓名:')
id_card = input('请输入您的身份证:')
phone_num = input('请输入您的手机号码:')
password = input('请设置您的账户密码:')
# 保存账户信息
account = Info.create_account(name=name, id_card=id_card, phone_num=phone_num, password=password)
# 打印账户信息
print(f'账户:{account}\t密码:{password}\t姓名:{name}\t余额:0元')
Realize.show_title(info='开户成功')
# 账户销户 ===================================================================
@staticmethod
def del_account():
Realize.show_title(info='账户销户')
# 如果账户不存在
account = Realize.account_whether_exist('请输入需要注销的账户:')
if not account:
return
Info.output_account(account) # 打印账户信息
# 管理员账户无法注销
if account == Info.admin_account:
print(f'{account}为管理员账户,无法注销!')
return
# 选择确认销户
if Realize.option_affirm(account=account, info='销户'):
Info.remove_account(account) # 销户
# 账户锁定 ===================================================================
@staticmethod
def frozen_account():
Realize.show_title(info='账户锁定')
# 如果账户不存在
account = Realize.account_whether_exist('请输入需要锁定的账户:')
if not account:
return
# 管理员账户无法锁定
if account == Info.admin_account:
print(f'{account}为管理员账户,无法锁定!')
return
# 如果账户已锁定
if not Info.whether_account_lock(account):
print(f'账户:{account},已被锁定!')
return
# 锁定选择确认
if Realize.option_affirm(account=account, info='锁定'):
# 账户锁定
Info.account_lock(account)
# 账户解锁 ===================================================================
@staticmethod
def account_unlock():
Realize.show_title('账户解锁')
# 如果账户不存在
account = Realize.account_whether_exist('请输入需要解锁的账户:')
if not account:
return
# 如果没有锁定
if Info.whether_account_lock(account):
print(f'账户:{account},未锁定,无需解锁!')
return
# 如果选择解锁
if Realize.option_affirm(account=account, info='解锁'):
Info.account_unlock(account) # 账户解锁
# 账户查询 ===================================================================
@staticmethod
def find_account_info():
Realize.show_title('账户查询')
# 因为这里添加了‘all’,所以要单独处理
while True:
account = input('请输入需要查询的账户(全部:all):')
# 如果账户存在
if Info.find_account(account):
break
# 退出
elif account == 'q':
Realize.show_title(info='返回菜单')
return False
# 打印全部
elif account == 'all' or account == 'ALL':
break
print(f'账户:{account}不存在!(返回:q)')
# 打印系统所有账户信息
if account == 'all':
Info.output_account(account='参数无要求', scope='all')
return
# 单纯打印此账户信息
Info.output_account(account)
# 账户修改 ===================================================================
@staticmethod
def change_account_info():
Realize.show_title('账户修改')
# 如果账户不存在
account = Realize.account_whether_exist('请输入需要修改的账户:')
if not account:
return
# 管理员特殊处理
if account == Info.admin_account:
while True:
new_account = input('请输入新的账号:')
# 如果修改成功
if Realize.option_affirm(account=account, info='账号修改', num=7, num1=1):
# 确认修改后赋值
Info.change_admin_account(account=account, new_account=new_account)
# 打印修改后账户信息
Info.output_account(new_account)
# 赋值
account = new_account
break
# 账户信息修改(可以封装到函数里)
while True:
# 打印账户信息修改菜单
Realize.show_title('账户修改')
print('1.修改姓名\t 2.修改身份证')
print('3.修改密码\t 4.修改手机号')
# 选择菜单功能
num = Realize.input_num(f'请账户{account}选择修改内容:')
# 1.修改姓名
if num == '1':
new_name = input('请输入新的姓名:')
# 参数传参赋值
info = '姓名修改'
index = 0
data = new_name
num = 7
space = 1
# 2.修改身份证
elif num == '2':
data = input('请输入新的身份证:')
# 参数传参赋值
info = '身份证修改'
index = 1
num = 6
space = 1
# 3.修改密码
elif num == '3':
data = input('请输入新的密码:')
# 参数传参赋值
info = '密码修改'
index = 4
num = 7
space = 1
# 4.修改手机号
elif num == '4':
data = input('请输入新的手机号:')
# 参数传参赋值
info = '手机号修改'
index = 2
num = 6
space = 1
# 返回
elif num == 'q':
break
# 其他
else:
print('编号输入有误!(退出:q)')
continue
# 如果修改失败
if not Realize.option_affirm(account=account, info=info, num=num, num1=space):
continue
# 修改成功后赋值
Info.change_account(account=account, position=index, info=data)
Info.output_account(account) # 打印赋值后信息
# 删库跑路 ===================================================================
@staticmethod
def clear_account():
Realize.show_title('恢复出厂')
while True:
buf = input('请确认是否删库跑路(Y/N):')
if buf == 'Y' or buf == 'y':
Info.clear_account()
Realize.show_title('恢复出厂')
break
elif buf == 'N' or buf == 'n':
Realize.show_title('删库失败')
break
elif buf == 'q':
Realize.show_title('放弃删库')
break
print('输入有误!(返回:q)')
# 登录界面打印 ==============================================================
@staticmethod
def interface():
while True:
Realize.show_title(info='账户登录') # 打印标题
whether = input('请问您是否有账户(Y/N):')
if whether == 'N' or whether == 'n':
print('很遗憾您还没有账户!!!')
print('快来找管理员开户吧!')
print('管理员账户:123456')
print('管理员密码:123456')
continue
elif whether == 'Y' or whether == 'y':
account = input('请输入账户:') # 输入账户
# 先判断账户是否正确
if not Info.find_account(find=account):
error_count = 1 # 记录输入错误的次数
while True:
print('账号输入错误!(返回:q)') # 打印错误提示语
account = input('请重新输入账户:') # 重新输入账户
# 判断系统里是否有此账户
if Info.find_account(find=account):
break # 如果有就停止输入
# 判断输入的次数能否被4整除
if error_count % 4 == 0:
buf = f'您已经输入错误{error_count + 1}次!' # 如果能被4整除,就打印提示语
Realize.show_title(info=buf, num=4) # 调用函数打印打印提示语
# 判断是否输入的账户是字符‘q’
if account == 'q':
break # 如果为真,就跳出循环输入
error_count += 1 # 输入错误数累加
# 判断输入的账户是否为字符‘q’
if account == 'q':
continue # 如果为真,就回到本次循环的开始
# 判断账户是否被锁定
if not Info.whether_account_lock(account):
print(f'此账户:{account} 已被锁定!\n请及时找管理员处理!')
continue
password = input('请输入密码:') # 输入密码
# 只有三次机会
for i in range(4):
# 再判断密码是否正确
if Info.find_password(account=account, password=password):
return account # 如果正确,就返回账户
else:
error = '输入密码错误!'
# 打印提示语
if i < 3:
print(error, end='') # 打印输入错误提示
print(f'还有{3 - i}次机会')
password = input('请重新输入密码:')
# 密码全输错了(账户锁定,管理员除外)
if account != Info.admin_account:
print(f'此账户:{account} 已被锁定!\n请及时找管理员处理!')
Info.account_lock(account) # 调用静态方法,说明此账户已被锁定
# 选择菜单功能 ================================================================
@staticmethod
def select_function(num):
# 1.账号开户
if num == '1':
Realize.set_up_account() # 调用静态方法开户
# 2.账号销户
elif num == '2':
Realize.del_account() # 调用静态方法
# 3.账户锁定
elif num == '3':
Realize.frozen_account() # 调用静态方法
# 4.账户解锁
elif num == '4':
Realize.account_unlock() # 调用静态方法
# 5.账户查询
elif num == '5':
Realize.find_account_info() # 调用静态方法
# 6.账户修改
elif num == '6':
Realize.change_account_info() # 调用静态方法
# 7.删库跑路
elif num == '7':
Realize.clear_account() # 调用静态方法
# 定义一个普通账户菜单功能实现类(普通用户)
class User:
# 打印菜单 ====================================================================
@staticmethod
def user_menu():
Realize.show_title(info='银行管理系统(用户)', num=5)
print('1.取款\t\t\t\t2.余额')
print('3.存款\t\t\t\t4.转账')
print('0.退卡')
# 存款 =====================================================================
@staticmethod
def deposit(account):
Realize.show_title('用户存款')
while True:
money = float(input('请输入存款金额:')) # 理想状态,如果输入负数和字符串会出现bug
if money < 0:
print('不能输入负数')
continue
break
Info.user_depo(account=account, money=money) # 金额增加
Info.output_info(account) # 打印账户信息
# 如果放弃存款
if not Realize.option_affirm(account=account, info='存款'):
Info.user_withdrawal(account=account, money=money) # 金额减少
return
# 取款 =====================================================================
@staticmethod
def withdrawal(account):
Realize.show_title('用户取款')
while True:
Info.output_info(account) # 打印账户信息
money = float(input('请输入取款金额:')) # 理想状态,如果输入负数和字符串会出现bug
if money < 0:
print('不能输入负数')
continue
# 如果银行卡里的余额<取款余额
elif Info.user_money(account) < money:
print('已超出最大取款金额!')
continue
break
# 如果放弃存款
if not Realize.option_affirm(account=account, info='取款'):
return
Info.user_withdrawal(account=account, money=money) # 金额减少
# 转账 =====================================================================
@staticmethod
def transfer(account):
Realize.show_title('账户转账')
# 被转账账户真是存在,且不是管理员
while True:
new_account = input('请输入转账的账户:')
# 如果被转账账户存在
if Info.find_account(new_account):
break
# 返回上一级
elif new_account == 'q':
Realize.show_title('转账失败')
return
# 不能对管理员转账
elif new_account == Info.admin_account:
print('无法给管理员账户转账!')
continue
print('此账户不存在,(返回:q)')
# 输入合适的转账金额
while True:
Info.output_info(account) # 打印账户信息
# 输入转账金额
money = float(input('请输入转账金额:'))
if money < 0:
print('不能输入负数')
continue
# 如果银行卡里的余额<取款余额
elif Info.user_money(account) < money:
print('已超出最大取款金额!')
continue
break
# 如果放弃转账
if not Realize.option_affirm(account=account, info='转账'):
return
# 转账成功
Info.user_withdrawal(account=account, money=money) # 金额减少
Info.user_depo(account=new_account, money=money) # 金额增加
# 菜单功能实现 ===============================================================
@staticmethod
def option_function(num, account):
# 1.取款
if num == '1':
User.withdrawal(account)
# 2.余额
elif num == '2':
Realize.show_title('显示余额')
Info.output_info(account)
# 3.存款
elif num == '3':
User.deposit(account)
# 4.转账
elif num == '4':
User.transfer(account)
# 功能实现(等价于C语言的主函数) ====================================================
while True:
flag_break = 0 # 跳出循环旗帜
account = Realize.interface() # 判断是否有账户,并赋值
while not False:
if flag_break == 1: # 跳出两层循环
break
# 如果被锁定
if not Info.whether_account_lock(account):
print(f'此账户:{account} 已被锁定!\n请及时找管理员处理!')
break
# 打印加载进度条
from loading import show_load
show_load()
# 如果是管理员账户登录
if account == Info.admin_account:
while True:
Realize.admin_menu() # 打印管理员菜单
num = Realize.input_num('请管理员选择功能:') # 选择功能
if num == '0':
flag_break = 1 # 跳出两层循环旗帜
Realize.show_title(info='已退出管理员管理系统', num=4)
break
Realize.select_function(num) # 菜单功能实现
# 普通账户登录
else:
while True:
User.user_menu() # 打印用户菜单
num = Realize.input_num(f'请[{account}]选择功能:') # 选择功能
if num == '0':
flag_break = 1 # 跳出两层循环旗帜
Realize.show_title(info='已退出银行管理系统', num=5)
break
User.option_function(num=num, account=account) # 菜单功能实现
loading.py 文本进度加载
# 文本下载进度条
"""
知识点:
1、time 模块使用
2、回到本行首位置'\r'与 替换本行末尾换行符end=''
3、显示百分号
4、字符串运算,只能用加法和乘法
5、while 循环使用
"""
def show_load(speed=0.1):
import time # 导入 time模块
# 变量定义
i = 1
a = '*'
# b = '.'
start = '='*10 + '加载中' + '='*10 # 字符串拼接
finish = '='*9 + '加载完成' + '='*9
# 打印开始下载
# print(start)
while True:
# 字符串拼接
progress_bar = '[{}{}{:.0%}]'.format(a * i, '.' * (19 - i), (i * 100 / 19) / 100)
# 打印进度条
print('\r' + progress_bar, end='')
# 循环结束条件
if i >= 19:
break # 跳出循环
i += 1 # 循环累加
time.sleep(speed) # 等待0.5秒
# 打印下载完成
# print('\n' + finish)
print()
运行结果:
=========账户登录=========
请问您是否有账户(Y/N):n
很遗憾您还没有账户!!!
快来找管理员开户吧!
管理员账户:123456
管理员密码:123456
=========账户登录=========
请问您是否有账户(Y/N):y
请输入账户:123456
请输入密码:123456
[*******************100%]
====银行管理系统(管理员)====
1.账号开户 2.账户销户
3.账户锁定 4.账户解锁
5.账户查询 6.账户修改
7.删库跑路 0.退卡
请管理员选择功能:5
=========账户查询=========
请输入需要查询的账户(全部:all):all
账户:123456 密码:123456 余额:0¥ 姓名:周华 身份证:(空) 手机号:(空) 状态:管理员
====银行管理系统(管理员)====
1.账号开户 2.账户销户
3.账户锁定 4.账户解锁
5.账户查询 6.账户修改
7.删库跑路 0.退卡
请管理员选择功能:
作者:周华