当前位置: 首页 > news >正文

PyQt批量年龄计算工具:从身份证到指定日期的周岁处理

目录

一、引言

二、GUI界面设计

1.相关提示

2.效果演示

3.界面设计.py

三、主要程序详解

1.导入相关模块

2.初始化设置

3.“日”选项的设置

4.年龄(周岁)的计算

5.自定义函数


一、引言

在公安、民政、保险及教育等领域的日常工作中,批量计算人员年龄是一项常见但繁琐的任务,传统的手工处理方式不仅效率低下,还容易因人为操作导致错误。为此,我们开发了基于PyQt框架的批量年龄(周岁)计算工具,该工具能够从18位身份证号中自动提取出生日期(第7-14位为YYYYMMDD格式),并结合用户指定的目标日期,高效、精准地计算出周岁年龄。同时支持将结果直接复制导出,便于后续数据分析与系统集成。无论是公安系统的户籍核查、保险行业的保费核保,还是教育机构的学生年龄统计,本工具都能提供标准化、可复用的解决方案,助力各行业在数字化转型中实现效率提升。

二、GUI界面设计

使用PyQt5进行界面的搭建,界面如下:

   

初始界面搭建采用极简风格。当批量输入(也可直接从excel中复制粘贴)合法的身份证号码后,若其合法,点击“计算”后会在右侧给出对应年龄(周岁)结果;否则,会告知用户输入身份证号码存在不合法项并提示重新输入。

需要注意的是:该计算工具会结合用户指定的目标日期,高效、精准地计算出周岁年龄。如上图红框所示:当两者均为2000年出生,得到的年龄相差为1,原因在于前者是4月份出生(到2025年的10月7日满周岁),后者是11月份出生(到2025年的10月7日未满周岁)

1.相关提示

在未输入身份证和未选择指定日期,进行“计算”操作后,均会给出提示;当用户输入的身份证存在长度错误或特殊字符时,提示“输入身份证有误,请重新输入”。

2.效果演示

3.界面设计.py

通过pyuic5产生的GUI界面代码jiemian.py如下:

# -*- coding: utf-8 -*-# Form implementation generated from reading ui file 'jiemian.ui'
#
# Created by: PyQt5 UI code generator 5.15.11
#
# WARNING: Any manual changes made to this file will be lost when pyuic5 is
# run again.  Do not edit this file unless you know what you are doing.from PyQt5 import QtCore, QtGui, QtWidgetsclass Ui_Form(object):def setupUi(self, Form):Form.setObjectName("Form")Form.setEnabled(True)Form.resize(360, 450)Form.setMinimumSize(QtCore.QSize(360, 450))Form.setMaximumSize(QtCore.QSize(360, 450))icon = QtGui.QIcon()icon.addPixmap(QtGui.QPixmap(":/image1.png"), QtGui.QIcon.Normal, QtGui.QIcon.Off)Form.setWindowIcon(icon)self.label_5 = QtWidgets.QLabel(Form)self.label_5.setGeometry(QtCore.QRect(210, 40, 141, 31))font = QtGui.QFont()font.setFamily("Adobe Arabic")font.setPointSize(16)self.label_5.setFont(font)self.label_5.setObjectName("label_5")self.label_8 = QtWidgets.QLabel(Form)self.label_8.setGeometry(QtCore.QRect(130, 10, 251, 31))font = QtGui.QFont()font.setFamily("Adobe Arabic")font.setPointSize(18)font.setBold(False)font.setWeight(50)self.label_8.setFont(font)self.label_8.setObjectName("label_8")self.label_10 = QtWidgets.QLabel(Form)self.label_10.setGeometry(QtCore.QRect(290, 30, 71, 51))self.label_10.setText("")self.label_10.setPixmap(QtGui.QPixmap(":/image1.png"))self.label_10.setObjectName("label_10")self.textEdit = QtWidgets.QTextEdit(Form)self.textEdit.setGeometry(QtCore.QRect(30, 110, 141, 201))self.textEdit.setObjectName("textEdit")self.textEdit_2 = QtWidgets.QTextEdit(Form)self.textEdit_2.setGeometry(QtCore.QRect(200, 110, 141, 201))self.textEdit_2.setObjectName("textEdit_2")self.label = QtWidgets.QLabel(Form)self.label.setGeometry(QtCore.QRect(30, 85, 121, 21))self.label.setObjectName("label")self.label_2 = QtWidgets.QLabel(Form)self.label_2.setGeometry(QtCore.QRect(200, 90, 54, 12))self.label_2.setObjectName("label_2")self.pushButton = QtWidgets.QPushButton(Form)self.pushButton.setGeometry(QtCore.QRect(30, 410, 311, 23))self.pushButton.setObjectName("pushButton")self.comboBox = QtWidgets.QComboBox(Form)self.comboBox.setGeometry(QtCore.QRect(40, 360, 67, 22))self.comboBox.setObjectName("comboBox")self.comboBox_2 = QtWidgets.QComboBox(Form)self.comboBox_2.setGeometry(QtCore.QRect(150, 360, 67, 22))self.comboBox_2.setObjectName("comboBox_2")self.comboBox_3 = QtWidgets.QComboBox(Form)self.comboBox_3.setGeometry(QtCore.QRect(260, 360, 67, 22))self.comboBox_3.setObjectName("comboBox_3")self.label_3 = QtWidgets.QLabel(Form)self.label_3.setGeometry(QtCore.QRect(110, 360, 16, 21))self.label_3.setObjectName("label_3")self.label_4 = QtWidgets.QLabel(Form)self.label_4.setGeometry(QtCore.QRect(220, 360, 21, 21))self.label_4.setObjectName("label_4")self.label_6 = QtWidgets.QLabel(Form)self.label_6.setGeometry(QtCore.QRect(330, 360, 21, 21))self.label_6.setObjectName("label_6")self.label_7 = QtWidgets.QLabel(Form)self.label_7.setGeometry(QtCore.QRect(30, 330, 121, 31))self.label_7.setObjectName("label_7")self.retranslateUi(Form)QtCore.QMetaObject.connectSlotsByName(Form)def retranslateUi(self, Form):_translate = QtCore.QCoreApplication.translateForm.setWindowTitle(_translate("Form", "Age_cal"))self.label_5.setText(_translate("Form", "Designed By"))self.label_8.setText(_translate("Form", "年龄计算"))self.label.setText(_translate("Form", "请输入身份证号码:"))self.label_2.setText(_translate("Form", "年龄如下:"))self.pushButton.setText(_translate("Form", "计算"))self.label_3.setText(_translate("Form", "年"))self.label_4.setText(_translate("Form", "月"))self.label_6.setText(_translate("Form", "日"))self.label_7.setText(_translate("Form", "请选择指定日期:"))
import ziyuan_rc

三、主要程序详解

1.导入相关模块

import sys, time
from jiemian import *
from PyQt5.QtWidgets import QApplication, QWidget
# 保持窗口大小和qtdesigner中的一致
from PyQt5 import QtCore
QtCore.QCoreApplication.setAttribute(QtCore.Qt.AA_EnableHighDpiScaling)

导入前端页面设计文件:jiemian.py;不懂为啥需要导入Qtcore的,请看一键曝光:Python+PyQt实现的文件目录透视镜

2.初始化设置

    def __init__(self):super(QWidget, self).__init__()self.setupUi(self)self.pushButton.clicked.connect(self.jisuan)self.comboBox.currentIndexChanged.connect(self.day_show)  # 年份选项发生改变self.comboBox_2.currentIndexChanged.connect(self.day_show)  # 月份选项发生改变self.comboBox.addItem('请选择')self.comboBox_2.addItem('请选择')# 针对“年”self.cur_nian = time.strftime("%Y", time.localtime())# 使用列表推导式增添选项self.comboBox.addItems([str(int(self.cur_nian) + i) for i in range(-5, 6)])  # 年self.comboBox_2.addItems([str(i) for i in range(1, 13)])  # 月

pushbutton绑定于jisuan;当用户改变年度/月份时,对应的“日”也需要紧随变化,故将其绑定于day_show;同时在初始化时将年份comboBox和月份comboBox_2添加首选项“请选择”,日comboBox暂时不做处理;接着通过time.strftime获取当前年份并存储于cur_nian中;以当前年份为时间中点,使用列表推导式往前往后各推5年添加至comboBox中;最后再通过列表推导式添加12个月份。

3.“日”选项的设置

    def day_show(self):"""主要对日进行设置,因为其不仅与月份有关,还与年份有关(闰年的2月)"""self.comboBox_3.clear()self.comboBox_3.addItem('请选择')yue_text = self.comboBox_2.currentText()  # 判断用户选择的是哪个月if yue_text in ['1', '3', '5', '7', '8', '10', '12']:  # 31天的月份self.comboBox_3.addItems([str(i) for i in range(1, 32)])elif yue_text in ['4', '6', '9', '11']:  # 30天的月份self.comboBox_3.addItems(str(i) for i in range(1, 31))elif yue_text == '2':  # 针对2月要特殊处理if self.comboBox.currentIndex() != 0:  # 除去年份为“请选择”的特殊情况if year_judge(self.comboBox.currentText()):  # 为闰年,2月为29天self.comboBox_3.addItems([str(i) for i in range(1, 30)])else:  # 不为闰年,2月为28天self.comboBox_3.addItems([str(i) for i in range(1, 29)])else:  # 表示月份的“请选择”选项pass

与其他combobox一样,combobox_3“日下拉框”也需要clear()和添加首选项“请选择”;combobox_3其不仅取决于“年下拉框”combobox是否为闰年,而且还取决于“月下拉框”combobox_2的选择(有31天的月份,也有30天的月份);所以先判断combobox_2的text是否在31天和30天的月份中,如果存在,直接使用列表推导式additems即可;否则如果为2月,还需通过自定义函数year_judge判断当前年份是否为闰年;如果为闰年,则列表推导式产生29天,否则产生28天;此时,combobox_3未讨论情况只剩下“请选择”选项,pass即可。

4.年龄(周岁)的计算

    def jisuan(self):shuru = self.textEdit.toPlainText()  # 读取的默认类型为strif shuru != "": # 用户输入不为空时if (self.comboBox.currentIndex()!=0) and(self.comboBox_2.currentIndex()!=0) and (self.comboBox_3.currentIndex()!=0): # 用户做出年月日的选择shuru_nian = self.comboBox.currentText()shuru_yue = self.comboBox_2.currentText()shuru_ri = self.comboBox_3.currentText()zhiding_riqi = riqi_return(shuru_nian,shuru_yue,shuru_ri) # 合并为YYYYMMDD的形式shuru_list = shuru.split()  # 以换行符分割riqi = [i[6:14] for i in shuru_list] # 截取所有身份证的8位日期jieguo  =[] # 年龄差存放for i in riqi:if (len(i) == 8) and i.isdigit(): # 长度为8且均为数字jieguo.append(niancha_cal(zhiding_riqi, i))else:QtWidgets.QMessageBox.critical(self, "提示", "输入身份证有误,请重新输入!")breakself.textEdit_2.clear() # 清除上次结果for item in jieguo:self.textEdit_2.append(str(item))else:QtWidgets.QMessageBox.critical(self, "提示", "请选择指定日期!")else:QtWidgets.QMessageBox.critical(self, "提示", "请输入身份证号!")

当用户输入不为空时,判断用户是否进行了“年月日”的选择(依据item的索引);若用户已经进行选择,则读取年月日并存储,通过调用自定义函数riqi_return从而返回YYYYMMDD的日期规范格式;再通过对用户输入的所有身份证进行切片操作,获取8位日期,并与上述YYYYMMDD通过自定义函数niancha_cal进行比较和计算,将得到的结果添加至jieguo中;最后通过循环显示到textedit_2中。

5.自定义函数

def year_judge(year):"""判断用户输入是否为闰年"""if (int(year)%4==0) and (int(year)%100!=0):return Trueelif int(year)%400==0:return Trueelse:return False

闰年的标志:能被4整除的同时,但不能被100整除;或者是能被400直接整除。

def riqi_return(nian, yue, ri):"""将年月日三数字转换合并为YYYYMMDD形式"""if (int(yue)<10): # 单月形式if (int(ri)<10): # 单日return nian+'0'+yue+'0'+ri # 补零操作else:return nian+'0'+yue+rielse:if (int(ri) < 10):return nian+yue+'0'+rielse:return nian+yue+ri

通过分支结构,在单数字前进行补零,最后将字符串拼接即可得到YYYYMMDD形式。

def niancha_cal(date1, date2):# 默认date1先于date2if int(date1)<int(date2): # 交换两者顺序temp = date1date1 = date2date2 = tempif int(date1[4:6]) < int(date2[4:6]): # 判断月的大小关系return int(date1[0:4])-int(date2[0:4])-1 # 不满周岁得减一elif int(date1[4:6]) > int(date2[4:6]):return int(date1[0:4])-int(date2[0:4])else:if int(date1[6:8]) < int(date2[6:8]): # 进一步判断“日”的大小关系return int(date1[0:4]) - int(date2[0:4]) - 1  # 不满周岁得减一else:return int(date1[0:4]) - int(date2[0:4])

默认date1先于date2,否则进行交换;接下来截取月份和日进行比较,最终截取年份相减,根据是否满周岁判断是否多减一。

四、总程序代码

import sys, time
from jiemian import *
from PyQt5.QtWidgets import QApplication, QWidget
# 保持窗口大小和qtdesigner中的一致
from PyQt5 import QtCore
QtCore.QCoreApplication.setAttribute(QtCore.Qt.AA_EnableHighDpiScaling)class window(QWidget, Ui_Form):def __init__(self):super(QWidget, self).__init__()self.setupUi(self)self.pushButton.clicked.connect(self.jisuan)self.comboBox.currentIndexChanged.connect(self.day_show)  # 年份选项发生改变self.comboBox_2.currentIndexChanged.connect(self.day_show)  # 月份选项发生改变self.comboBox.addItem('请选择')self.comboBox_2.addItem('请选择')# 针对“年”self.cur_nian = time.strftime("%Y", time.localtime())# 使用列表推导式增添选项self.comboBox.addItems([str(int(self.cur_nian) + i) for i in range(-5, 6)])  # 年self.comboBox_2.addItems([str(i) for i in range(1, 13)])  # 月def day_show(self):self.comboBox_3.clear()self.comboBox_3.addItem('请选择')yue_text = self.comboBox_2.currentText()  # 判断用户选择的是哪个月if yue_text in ['1', '3', '5', '7', '8', '10', '12']:  # 31天的月份self.comboBox_3.addItems([str(i) for i in range(1, 32)])elif yue_text in ['4', '6', '9', '11']:  # 30天的月份self.comboBox_3.addItems(str(i) for i in range(1, 31))elif yue_text == '2':  # 针对2月要特殊处理if self.comboBox.currentIndex() != 0:  # 除去年份为“请选择”的特殊情况if year_judge(self.comboBox.currentText()):  # 为闰年,2月为29天self.comboBox_3.addItems([str(i) for i in range(1, 30)])else:  # 不为闰年,2月为28天self.comboBox_3.addItems([str(i) for i in range(1, 29)])else:  # 表示月份的“请选择”选项passdef jisuan(self):shuru = self.textEdit.toPlainText()  # 读取的默认类型为strif shuru != "": # 用户输入不为空时if (self.comboBox.currentIndex()!=0) and(self.comboBox_2.currentIndex()!=0) and (self.comboBox_3.currentIndex()!=0): # 用户做出年月日的选择shuru_nian = self.comboBox.currentText()shuru_yue = self.comboBox_2.currentText()shuru_ri = self.comboBox_3.currentText()zhiding_riqi = riqi_return(shuru_nian,shuru_yue,shuru_ri) # 合并为YYYYMMDD的形式shuru_list = shuru.split()  # 以换行符分割riqi = [i[6:14] for i in shuru_list] # 截取所有身份证的8位日期jieguo  =[] # 年龄差存放for i in riqi:if (len(i) == 8) and i.isdigit(): # 长度为8且均为数字jieguo.append(niancha_cal(zhiding_riqi, i))else:QtWidgets.QMessageBox.critical(self, "提示", "输入身份证有误,请重新输入!")breakself.textEdit_2.clear() # 清除上次结果for item in jieguo:self.textEdit_2.append(str(item))else:QtWidgets.QMessageBox.critical(self, "提示", "请选择指定日期!")else:QtWidgets.QMessageBox.critical(self, "提示", "请输入身份证号!")def year_judge(year):"""判断用户输入是否为闰年"""if (int(year)%4==0) and (int(year)%100!=0):return Trueelif int(year)%400==0:return Trueelse:return Falsedef riqi_return(nian, yue, ri):"""将年月日三数字转换合并为YYYYMMDD形式"""if (int(yue)<10): # 单月形式if (int(ri)<10): # 单日return nian+'0'+yue+'0'+ri # 补零操作else:return nian+'0'+yue+rielse:if (int(ri) < 10):return nian+yue+'0'+rielse:return nian+yue+ridef niancha_cal(date1, date2):# 默认date1先于date2if int(date1)<int(date2): # 交换两者顺序temp = date1date1 = date2date2 = tempif int(date1[4:6]) < int(date2[4:6]): # 判断月的大小关系return int(date1[0:4])-int(date2[0:4])-1 # 不满周岁得减一elif int(date1[4:6]) > int(date2[4:6]):return int(date1[0:4])-int(date2[0:4])else:if int(date1[6:8]) < int(date2[6:8]): # 进一步判断“日”的大小关系return int(date1[0:4]) - int(date2[0:4]) - 1  # 不满周岁得减一else:return int(date1[0:4]) - int(date2[0:4])if __name__ == '__main__':app = QApplication(sys.argv)w = window()w.show()sys.exit(app.exec_())

欢迎留言沟通交流!

http://www.dtcms.com/a/454318.html

相关文章:

  • L2TPv2-原理浅谈+报文示例+简易配置-RFC2661
  • 信息系统项目的风险管理
  • hot100-3
  • 网站推广的措施和手段有哪些网站优化顺义案例
  • CompletableDeferred、defer 和 Job 关系
  • 呼市做引产z首大网站网站设计和建设ppt
  • 做面膜的网站如何才能做好品牌网站建设策划
  • 外贸社交网站排名网站搜不出来怎么办
  • 做影视网站规模不大洛阳网站建设哪个好点
  • 《投资-82》价值投资者的认知升级与交易规则重构 - 第二层:五大财务指标的定义、分析方法、误区
  • 做网站哪家强wordpress 不用插件代码高亮
  • string类的理解和使用
  • 做羞羞网站谷歌广告联盟怎么做
  • 网站规划建设与管理维护的论文软件推广
  • 备案的网站名称可以改吗pc网站怎么做适配
  • 用 AI 工具简化西瓜视频用户增长实操教程
  • 滁州市建设工程协会网站免费logo设计在线生成器钙网
  • 从winlogon!StateMachineWorkerCallback看ntdll!TpPostWork原理
  • Intel Loihi芯片的脉冲神经网络编程范式迁移
  • 个人博客网站源码网站子目录是什么
  • 网站开发用哪些字体wordpress响应+延时
  • 400网站建设地方门户网站用户
  • LangGraph 集成 MCP Server
  • 深度学习基础:从原理到实践——第一章感知机(下)
  • Python3 list()函数
  • 凡科建站的怎么取消手机网站厦门编程培训机构
  • 建站时长是什么原因造成的专业手机移动网站建设
  • 免费空间 个人网站 google广告联盟wordpress raw
  • 怎么做网站搜索引擎大连高新园区
  • 常州高端网站制作公司排名站长查询