PyQt5爬取12306车票信息程序的实现


Posted in Python onMay 14, 2021

1、搭载QT环境

按win+R输入 pip install pyqt5 下载QT5 当然也可以去Qt的官网的下载 ,使用命令行更快捷方便 所以建议使用命令行 ,去官网下载安装有它的好处就是不用自己安装 toosl
作者使用的是pyCharm 完成后期的后台程序设置,使用pyCharm 外部工具链接把Designer,pyUIC,qrcTopy程序加进去

PyQt5爬取12306车票信息程序的实现

PyQt5爬取12306车票信息程序的实现

PyQt5爬取12306车票信息程序的实现

2、主窗体设置

打Qt5主程序设置主窗体,设计完成保存为windows
添加到创建好的python项目中,然后选中单击右键-》External toosl-》Py UIC 将ui文件转换成py文件
windows.py

from PyQt5.QtGui import QPalette, QPixmap, QColor


# result = []  # 保存车次分类后最后的数据


# UI类
class Ui_MainWindow(object):

    # 设置UI的方法
    def setupUi(self, MainWindow):
        MainWindow.setObjectName("MainWindow")  # 设置窗体对象名称
        MainWindow.resize(960, 786)  # 设置窗体大小
        MainWindow.setMinimumSize(QtCore.QSize(960, 786))  # 主窗体最小值
        MainWindow.setMaximumSize(QtCore.QSize(960, 786))  # 主窗体最大值
        self.centralwidget = QtWidgets.QWidget(MainWindow)  # 主窗体的widget控件
        self.centralwidget.setObjectName("centralwidget")  # 设置对象名称

        # 通过label控件显示顶部图片
        self.label_title_img = QtWidgets.QLabel(self.centralwidget)
        self.label_title_img.setGeometry(QtCore.QRect(0, 0, 960, 141))
        self.label_title_img.setObjectName("label_title_img")
        title_img = QPixmap('img/TE3.png')  # 打开顶部位图
        self.label_title_img.setPixmap(title_img)  # 设置调色板

        # 查询部分的widget
        self.widget_query = QtWidgets.QWidget(self.centralwidget)
        self.widget_query.setGeometry(QtCore.QRect(0, 141, 960, 80))
        self.widget_query.setObjectName("widget_query")
        # 开启自动填充背景
        self.widget_query.setAutoFillBackground(True)
        palette = QPalette()  # 调色板类
        palette.setBrush(QPalette.Background, QtGui.QBrush(QtGui.QPixmap('img/bg2.png')))  # 设置背景图片
        self.widget_query.setPalette(palette)  # 为控件设置对应的调色板即可

        # 出发地与对应的编辑框控件
        self.label = QtWidgets.QLabel(self.widget_query)
        self.label.setGeometry(QtCore.QRect(30, 30, 54, 12))
        self.label.setObjectName("label")
        self.textEdit = QtWidgets.QTextEdit(self.widget_query)
        self.textEdit.setGeometry(QtCore.QRect(80, 20, 104, 31))
        font = QtGui.QFont()  # 创建QFont()对象
        font.setPointSize(13)  # 设置编辑框字体大小的值
        self.textEdit.setFont(font)  # 设置编辑框字体
        self.textEdit.setObjectName("textEdit")  # 出发地对应编辑框对象名称

        # 目的地与对应的编辑框
        self.label_2 = QtWidgets.QLabel(self.widget_query)
        self.label_2.setGeometry(QtCore.QRect(220, 30, 54, 12))
        self.label_2.setObjectName("label_2")
        self.textEdit_2 = QtWidgets.QTextEdit(self.widget_query)
        self.textEdit_2.setGeometry(QtCore.QRect(270, 20, 104, 31))
        font = QtGui.QFont()
        font.setPointSize(13)
        self.textEdit_2.setFont(font)
        self.textEdit_2.setObjectName("textEdit_2")

        # 出发日与有对应的编辑框
        self.label_3 = QtWidgets.QLabel(self.widget_query)
        self.label_3.setGeometry(QtCore.QRect(410, 30, 54, 12))
        self.label_3.setObjectName("label_3")
        self.textEdit_3 = QtWidgets.QTextEdit(self.widget_query)
        self.textEdit_3.setGeometry(QtCore.QRect(460, 20, 104, 31))
        font = QtGui.QFont()
        font.setPointSize(13)
        self.textEdit_3.setFont(font)
        self.textEdit_3.setObjectName("textEdit_3")
        # 查询按钮
        self.pushButton = QtWidgets.QPushButton(self.widget_query)
        self.pushButton.setGeometry(QtCore.QRect(610, 20, 91, 31))
        self.pushButton.setObjectName("pushButton")

        # 选择车次类型的widget
        self.widget_checkBox = QtWidgets.QWidget(self.centralwidget)
        self.widget_checkBox.setGeometry(QtCore.QRect(0, 220, 961, 35))
        self.widget_checkBox.setAutoFillBackground(False)
        self.widget_checkBox.setObjectName("widget_checkBox")
        # 开启自动填充背景
        self.widget_checkBox.setAutoFillBackground(True)
        palette = QPalette()  # 调色板类
        palette.setBrush(QPalette.Background, QtGui.QBrush(QtGui.QPixmap('img/bg3.png')))  # 设置背景图片
        self.widget_checkBox.setPalette(palette)  # 设置调色板控件对应的方法即可

        # 显示车次类型文字
        self.label_type = QtWidgets.QLabel(self.widget_checkBox)
        self.label_type.setGeometry(QtCore.QRect(30, 9, 65, 16))
        font = QtGui.QFont()
        font.setPointSize(10)
        self.label_type.setFont(font)
        self.label_type.setObjectName("label_type")

        # 选择高铁
        self.checkBox_G = QtWidgets.QCheckBox(self.widget_checkBox)
        self.checkBox_G.setGeometry(QtCore.QRect(100, 9, 70, 17))
        font = QtGui.QFont()
        font.setPointSize(10)
        self.checkBox_G.setFont(font)
        self.checkBox_G.setObjectName("checkBox_GC")

        # 选择动车
        self.checkBox_D = QtWidgets.QCheckBox(self.widget_checkBox)
        self.checkBox_D.setGeometry(QtCore.QRect(258, 9, 63, 17))
        font = QtGui.QFont()
        font.setPointSize(10)
        self.checkBox_D.setFont(font)
        self.checkBox_D.setObjectName("checkBox_D")
        # 选择直达
        self.checkBox_Z = QtWidgets.QCheckBox(self.widget_checkBox)
        self.checkBox_Z.setGeometry(QtCore.QRect(415, 9, 63, 17))
        font = QtGui.QFont()
        font.setPointSize(10)
        self.checkBox_Z.setFont(font)
        self.checkBox_Z.setObjectName("checkBox_Z")
        # 选择特快
        self.checkBox_T = QtWidgets.QCheckBox(self.widget_checkBox)
        self.checkBox_T.setGeometry(QtCore.QRect(572, 9, 63, 17))
        font = QtGui.QFont()
        font.setPointSize(10)
        self.checkBox_T.setFont(font)
        self.checkBox_T.setObjectName("checkBox_T")
        # 选择快速
        self.checkBox_K = QtWidgets.QCheckBox(self.widget_checkBox)
        self.checkBox_K.setGeometry(QtCore.QRect(730, 9, 63, 17))
        font = QtGui.QFont()
        font.setPointSize(10)
        self.checkBox_K.setFont(font)
        self.checkBox_K.setObjectName("checkBox_K")

        # 通过label控件显示火车信息图片
        self.label_train_img = QtWidgets.QLabel(self.centralwidget)
        self.label_train_img.setGeometry(QtCore.QRect(0, 256, 960, 62))
        self.label_train_img.setObjectName("label_train_img")
        train_img = QPixmap('img/bg4.png')  # 打开火车信息位图
        self.label_train_img.setPixmap(train_img)  # 设置调色板
        # 显示车次信息的列表
        self.tableView = QtWidgets.QTableView(self.centralwidget)
        self.tableView.setGeometry(QtCore.QRect(0, 320, 960, 440))
        self.tableView.setObjectName("tableView")
        self.model = QStandardItemModel()# 创建存储数据的模式
        # 根据空间自动改变列宽度并且不可修改列宽度
        self.tableView.horizontalHeader().setSectionResizeMode(QHeaderView.Stretch)
        # 设置表头不可见
        self.tableView.horizontalHeader().setVisible(False)
        # 纵向表头不可见
        self.tableView.verticalHeader().setVisible(False)
        # 设置表格内容文字大小
        font = QtGui.QFont()
        font.setPointSize(10)
        self.tableView.setFont(font)
        # 设置表格内容不可编辑
        self.tableView.setEditTriggers(QAbstractItemView.NoEditTriggers)
        # 垂直滚动条始终开启
        self.tableView.setVerticalScrollBarPolicy(Qt.ScrollBarAlwaysOn)
        # 主窗体设置主Widget
        MainWindow.setCentralWidget(self.centralwidget)

        self.retranslateUi(MainWindow)  # 调用retranslateUi方法显示窗体文字
        QtCore.QMetaObject.connectSlotsByName(MainWindow)  # 关联信号槽

    def retranslateUi(self, MainWindow):
        _translate = QtCore.QCoreApplication.translate
        MainWindow.setWindowTitle(_translate("MainWindow", "爬票"))
        self.checkBox_T.setText(_translate("MainWindow", "T-特快"))
        self.checkBox_K.setText(_translate("MainWindow", "K-快速"))
        self.checkBox_Z.setText(_translate("MainWindow", "Z-直达"))
        self.checkBox_D.setText(_translate("MainWindow", "D-动车"))
        self.checkBox_G.setText(_translate("MainWindow", "GC-高铁"))
        self.label_type.setText(_translate("MainWindow", "车次类型:"))
        self.label.setText(_translate("MainWindow", "出发地:"))
        self.label_2.setText(_translate("MainWindow", "目的地:"))
        self.label_3.setText(_translate("MainWindow", "出发日:"))
        self.pushButton.setText(_translate("MainWindow", "查询"))
def show_MainWindow():
    app = QtWidgets.QApplication(sys.argv)  # 首先必须实例化QApplication类,作为GUI主程序入口
    MainWindow = QtWidgets.QMainWindow()  # 实例化QtWidgets.QMainWindow类,创建自带menu的窗体类型QMainWindow
    ui = Ui_MainWindow()  # 实例UI类
    ui.setupUi(MainWindow)  # 设置窗体UI
    MainWindow.show()  # 显示窗体
    sys.exit(app.exec_())  # 当来自操作系统的分发事件指派调用窗口时,
    # 应用程序开启主循环(mainloop)过程,
    # 当窗口创建完成,需要结束主循环过程,
    # 这时候呼叫sys.exit()方法来,结束主循环过程退出,
    # 并且释放内存。为什么用app.exec_()而不是app.exec()?
    # 因为exec是python系统默认关键字,为了以示区别,所以写成exec_


if __name__ == "__main__":
    if isStations() == False:  # 判断是否有所有车站的文件,没有就下载,有就直接显示窗体
        getStation()  # 下载所有车站文件
        show_MainWindow()  # 调用显示窗体的方法
    else:
        show_MainWindow()  # 调用显示窗体的方法

3、下载网站文件

在这之前我们的先去12306网站分析相关参数

PyQt5爬取12306车票信息程序的实现

获取完整的查票地址,注意每一个时期的地址是会发生改变的
创建用于下载网站文件的py文件,get_stations.py

import re
import  requests
import os

def getStation():
    # 发送请求获取所有车站名称,通过输入的站名称转化查询地址的参数
    url = 'https://kyfw.12306.cn/otn/resources/js/framework/station_name.js?station_version=1.9190'
    response = requests.get(url, verify=True)  # 请求并进行验证
    stations = re.findall(u'([\u4e00-\u9fa5]+)\|([A-Z]+)', response.text)  # 获取需要的车站名称
    stations = dict(stations)  # 转换为dic
    stations = str(stations)  # 转换为字符串类型否则无法写入文件
    write(stations)           #调用写入方法
def write(stations):
    file = open('stations.text', 'w', encoding='utf_8_sig')  # 以写模式打开文件
    file.write(stations)  # 写入数据
    file.close()
def read():
    file = open('stations.text', 'r', encoding='utf_8_sig')  # 以写模式打开文件
    data = file.readline()                                  #读取文件
    file.close()
    return data

def isStations():
    isStations = os.path.exists('stations.text')      #判断车站文件是否存在
    return isStations

4、车票信息的请求与显示

创建 query_request.py文件用于发现数据后的处理工作

from get_stations import *
import requests

'''5-7 目的地 3  车次 6  出发地 8  出发时间 9  到达时间 10 历时 26 无坐 29 硬座
   24 软座 28 硬卧 33 动卧 23 软卧 21 高级软卧 30 二等座 31 一等座 32 商务座特等座
'''
data = []  # 用于保存整理好的车次信息
type_data = []  # 保存车次分类后最后的数据
headers = {'user-agent':'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/76.0.3809.100 Safari/537.36',
           'Cookie':'_uab_collina=162044599452968647580256; JSESSIONID=ABB3D0F36AA12C3E5DAD5CD1D3CFF031; '
                    'RAIL_EXPIRATION=1620786883959; RAIL_DEVICEID=hu-C8-xxpDNSCuX_BiPS1CGOlxAyoXu-dncsv32QDPvmjG'
                    'R9Ua0AUywoyJ6FDeqRWMoixIIL24hbMf9ucn2MrHcPWjgYFJ6y6Fon9ihvKvZV8SIiGDYmZTuR-S2OLu3wyezmWPPO'
                    'un2B-v2BR_Q0wEYkIrBLIE8j; _jc_save_fromStation=%u5317%u4EAC%2CBJP; _jc_save_toStation=%u4E0'
                    'A%u6D77%2CSHH; _jc_save_fromDate=2021-05-08; _jc_save_toDate=2021-05-08; _jc_save_wfdc_flag='
                    'dc; BIGipServerpassport=988283146.50215.0000; route=495c805987d0f5c8c84b14f60212447d; BIGipS'
                    'erverotn=417857802.50210.0000; BIGipServerportal=3084124426.17183.0000'}
def query(date, from_station, to_station):
    data.clear()  # 清空数据
    type_data.clear()  # 清空车次分类保存的数据
    # 查询请求地址
    url = 'https://kyfw.12306.cn/otn/leftTicket/query?leftTicketDTO.train_date={}&leftTicketDTO.from_station={}&leftTicketDTO.to_station={}&purpose_codes=ADULT'.format(
        date, from_station, to_station)
    # 发送查询请求
    response = requests.get(url=url,headers=headers)
    # # 将json数据转换为字典类型,通过键值对取数据
    result = response.json()
    result = result['data']['result']
    # 判断车站文件是否存在
    if isStations() == True:
        stations = eval(read())  # 读取所有车站并转换为dic类型
        if len(result) != 0:  # 判断返回数据是否为空
            for i in result:
                # # 分割数据并添加到列表中
                tmp_list = i.split('|')
                # 因为查询结果中出发站和到达站为站名的缩写字母,所以需要在车站库中找到对应的车站名称
                from_station = list(stations.keys())[list(stations.values()).index(tmp_list[6])]
                to_station = list(stations.keys())[list(stations.values()).index(tmp_list[7])]
                # 创建座位数组,由于返回的座位数据中含有空既“”,所以将空改成--这样好识别
                seat = [tmp_list[3], from_station, to_station, tmp_list[8], tmp_list[9], tmp_list[10]
                    , tmp_list[32], tmp_list[31], tmp_list[30], tmp_list[21]
                    , tmp_list[23], tmp_list[33], tmp_list[28], tmp_list[24], tmp_list[29], tmp_list[26]]
                newSeat = []
                # 循环将座位信息中的空既“”,改成--这样好识别
                for s in seat:
                    if s == "":
                        s = "--"
                    else:
                        s = s
                    newSeat.append(s)  # 保存新的座位信息
                data.append(newSeat)
        return data  # 返回整理好的车次信息


# 获取高铁信息的方法
def g_vehicle():
    if len(data) != 0:
        for g in data:  # 循环所有火车数据
            i = g[0].startswith('G')  # 判断车次首字母是不是高铁
            if i:  # 如果是将该条信息添加到高铁数据中
                type_data.append(g)


# 移除高铁信息的方法
def r_g_vehicle():
    if len(data) != 0 and len(type_data) != 0:
        for g in data:
            i = g[0].startswith('G')
            if i:  # 移除高铁信息
                type_data.remove(g)


# 获取动车信息的方法
def d_vehicle():
    if len(data) != 0:
        for d in data:  # 循环所有火车数据
            i = d[0].startswith('D')  # 判断车次首字母是不是动车
            if i == True:  # 如果是将该条信息添加到动车数据中
                type_data.append(d)


# 移除动车信息的方法
def r_d_vehicle():
    if len(data) != 0 and len(type_data) != 0:
        for d in data:
            i = d[0].startswith('D')
            if i == True:  # 移除动车信息
                type_data.remove(d)


# 获取直达车信息的方法
def z_vehicle():
    if len(data) != 0:
        for z in data:  # 循环所有火车数据
            i = z[0].startswith('Z')  # 判断车次首字母是不是直达
            if i == True:  # 如果是将该条信息添加到直达数据中
                type_data.append(z)


# 移除直达车信息的方法
def r_z_vehicle():
    if len(data) != 0 and len(type_data) != 0:
        for z in data:
            i = z[0].startswith('Z')
            if i == True:  # 移除直达车信息
                type_data.remove(z)


# 获取特快车信息的方法
def t_vehicle():
    if len(data) != 0:
        for t in data:  # 循环所有火车数据
            i = t[0].startswith('T')  # 判断车次首字母是不是特快
            if i == True:  # 如果是将该条信息添加到特快车数据中
                type_data.append(t)


# 移除特快车信息的方法
def r_t_vehicle():
    if len(data) != 0 and len(type_data) != 0:
        for t in data:
            i = t[0].startswith('T')
            if i == True:  # 移除特快车信息
                type_data.remove(t)


# 获取快速车数据的方法
def k_vehicle():
    if len(data) != 0:
        for k in data:  # 循环所有火车数据
            i = k[0].startswith('K')  # 判断车次首字母是不是快车
            if i == True:  # 如果是将该条信息添加到快车数据中
                type_data.append(k)


# 移除快速车数据的方法
def r_k_vehicle():
    if len(data) != 0 and len(type_data) != 0:
        for k in data:
            i = k[0].startswith('K')
            if i == True:  # 移除快车信息
                type_data.remove(k)

5、在主窗体中显示查票信息

注意这些方法是写在windows.py
(1)创建 get_time 和is_valid.date方法用判断日期是否有效

def get_time():
    # 获得当前时间时间戳
    now = int(time.time())
    # 转换为其它日期格式,如:"%Y-%m-%d %H:%M:%S"
    timeStruct = time.localtime(now)
    strTime = time.strftime("%Y-%m-%d", timeStruct)
    return strTime


def is_valid_date(str):
    '''判断是否是一个有效的日期字符串'''
    try:
        time.strptime(str, "%Y-%m-%d")
        return True
    except:
        return False

(2)创建车次分类复选事件处理方法

# 将所有车次分类复选框取消勾选
    def checkBox_default(self):
        self.checkBox_G.setChecked(False)
        self.checkBox_D.setChecked(False)
        self.checkBox_Z.setChecked(False)
        self.checkBox_T.setChecked(False)
        self.checkBox_K.setChecked(False)

    # 高铁复选框事件处理
    def change_G(self, state):
        # 选中将高铁信息添加到最后要显示的数据当中
        if state == QtCore.Qt.Checked:
            # 获取高铁信息
            g_vehicle()
            # 通过表格显示该车型数据
            self.displayTable(len(type_data), 16, type_data)
        else:
            # 取消选中状态将移除该数据
            r_g_vehicle()
            self.displayTable(len(type_data), 16, type_data)

    # 动车复选框事件处理
    def change_D(self, state):
        # 选中将动车信息添加到最后要显示的数据当中
        if state == QtCore.Qt.Checked:
            # 获取动车信息
            d_vehicle()
            # 通过表格显示该车型数据
            self.displayTable(len(type_data), 16, type_data)

        else:
            # 取消选中状态将移除该数据
            r_d_vehicle()
            self.displayTable(len(type_data), 16, type_data)

    # 直达复选框事件处理
    def change_Z(self, state):
        # 选中将直达车信息添加到最后要显示的数据当中
        if state == QtCore.Qt.Checked:
            # 获取直达车信息
            z_vehicle()
            self.displayTable(len(type_data), 16, type_data)
        else:
            # 取消选中状态将移除该数据
            r_z_vehicle()
            self.displayTable(len(type_data), 16, type_data)

    # 特快复选框事件处理
    def change_T(self, state):
        # 选中将特快车信息添加到最后要显示的数据当中
        if state == QtCore.Qt.Checked:
            # 获取特快车信息
            t_vehicle()
            self.displayTable(len(type_data), 16, type_data)
        else:
            # 取消选中状态将移除该数据
            r_t_vehicle()
            self.displayTable(len(type_data), 16, type_data)

    # 快速复选框事件处理
    def change_K(self, state):
        # 选中将快车信息添加到最后要显示的数据当中
        if state == QtCore.Qt.Checked:
            # 获取快速车信息
            k_vehicle()
            self.displayTable(len(type_data), 16, type_data)

        else:
            # 取消选中状态将移除该数据
            r_k_vehicle()
            self.displayTable(len(type_data), 16, type_data)

(3)创建messageDialog与displayTable方法分别用于非法输入的处理与车辆信息的显示

# 显示消息提示框,参数title为提示框标题文字,message为提示信息
    def messageDialog(self, title, message):
        msg_box = QMessageBox(QMessageBox.Warning, title, message)
        msg_box.exec_()

    # 显示车次信息的表格
    # train参数为共有多少趟列车,该参数作为表格的行。
    # info参数为每趟列车的具体信息,例如有座、无座卧铺等。该参数作为表格的列
    def displayTable(self, train, info, data):
        self.model.clear()
        for row in range(train):
            for column in range(info):
                # 添加表格内容
                item = QStandardItem(data[row][column])
                # 向表格存储模式中添加表格具体信息
                self.model.setItem(row, column, item)
        # 设置表格存储数据的模式
        self.tableView.setModel(self.model)

(4)创建on_click方法该方法用于查询事件的处理

# 查询按钮的单击事件
    def on_click(self):
        get_from = self.textEdit.toPlainText()  # 获取出发地
        get_to = self.textEdit_2.toPlainText()  # 获取到达地
        get_date = self.textEdit_3.toPlainText()  # 获取出发时间
        # 判断车站文件是否存在
        if isStations() == True:
            stations = eval(read())  # 读取所有车站并转换为dic类型
            # 判断所有参数是否为空,出发地、目的地、出发日期
            if get_from != "" and get_to != "" and get_date != "":
                # 判断输入的车站名称是否存在,以及时间格式是否正确
                if get_from in stations and get_to in stations and is_valid_date(get_date):
                    # 获取输入的日期是当前年初到现在一共过了多少天
                    inputYearDay = time.strptime(get_date, "%Y-%m-%d").tm_yday
                    # 获取系统当前日期是当前年初到现在一共过了多少天
                    yearToday = time.localtime(time.time()).tm_yday
                    # 计算时间差,也就是输入的日期减掉系统当前的日期
                    timeDifference = inputYearDay - yearToday
                    # 判断时间差为0时证明是查询当前的查票,
                    # 以及29天以后的车票。12306官方要求只能查询30天以内的车票
                    if timeDifference >= 0 and timeDifference <= 28:
                        from_station = stations[get_from]  # 在所有车站文件中找到对应的参数,出发地
                        to_station = stations[get_to]  # 目的地
                        data = query(get_date, from_station, to_station)  # 发送查询请求,并获取返回的信息
                        self.checkBox_default()
                        if len(data) != 0:  # 判断返回的数据是否为空
                            # 如果不是空的数据就将车票信息显示在表格中
                            self.displayTable(len(data), 16, data)
                        else:
                            self.messageDialog('警告', '没有返回的网络数据!')
                    else:
                        self.messageDialog('警告', '超出查询日期的范围内,'
                                                 '不可查询昨天的车票信息,以及29天以后的车票信息!')
                else:
                    self.messageDialog('警告', '输入的站名不存在,或日期格式不正确!')
            else:
                self.messageDialog('警告', '请填写车站名称!')
        else:
            self.messageDialog('警告', '未下载车站查询文件!')

(5)在retranslateUi方法中分别加入以下代码

self.textEdit_3.setText(get_time())  # 出发日显示当天日期
        self.pushButton.clicked.connect(self.on_click)  # 查询按钮指定单击事件的方法
        self.checkBox_G.stateChanged.connect(self.change_G)  # 高铁选中与取消事件
        self.checkBox_D.stateChanged.connect(self.change_D)  # 动车选中与取消事件
        self.checkBox_Z.stateChanged.connect(self.change_Z)  # 直达车选中与取消事件
        self.checkBox_T.stateChanged.connect(self.change_T)  # 特快车选中与取消事件
        self.checkBox_K.stateChanged.connect(self.change_K)  # 快车选中与取消事件

到此结束,以下是运行结果

PyQt5爬取12306车票信息程序的实现

PyQt5爬取12306车票信息程序的实现

PyQt5爬取12306车票信息程序的实现

PyQt5爬取12306车票信息程序的实现

PyQt5爬取12306车票信息程序的实现

PyQt5爬取12306车票信息程序的实现

PyQt5爬取12306车票信息程序的实现

PyQt5爬取12306车票信息程序的实现

到此这篇关于PyQt5爬取12306车票信息程序的实现的文章就介绍到这了,更多相关PyQt5爬取12306内容请搜索三水点靠木以前的文章或继续浏览下面的相关文章希望大家以后多多支持三水点靠木!

Python 相关文章推荐
采用python实现简单QQ单用户机器人的方法
Jul 03 Python
python使用wmi模块获取windows下硬盘信息的方法
May 15 Python
彻底理解Python list切片原理
Oct 27 Python
利用python如何处理nc数据详解
May 23 Python
python中的turtle库函数简单使用教程
Jul 23 Python
Python OpenCV对本地视频文件进行分帧保存的实例
Jan 08 Python
Python 操作 ElasticSearch的完整代码
Aug 04 Python
python实现猜拳游戏
Mar 04 Python
tensorflow常用函数API介绍
Apr 19 Python
Python变量及数据类型用法原理汇总
Aug 06 Python
python实现企业微信定时发送文本消息的示例代码
Nov 24 Python
python for循环赋值问题
Jun 03 Python
python flask框架快速入门
如何将numpy二维数组中的np.nan值替换为指定的值
May 14 #Python
使用numpy nonzero 找出非0元素
May 14 #Python
Python机器学习之KNN近邻算法
May 14 #Python
Python爬虫基础讲解之请求
自己搭建resnet18网络并加载torchvision自带权重的操作
May 13 #Python
如何使用flask将模型部署为服务
May 13 #Python
You might like
为什么那些咖啡爱好者大多看不上连锁咖啡店?
2021/03/06 咖啡文化
php数组键名技巧小结
2015/02/17 PHP
php编写简单的文章发布程序
2015/06/18 PHP
PHP迭代与递归实现无限级分类
2017/08/28 PHP
jquery.ui.progressbar 中文文档
2009/11/26 Javascript
javascript放大镜效果的简单实现
2013/12/09 Javascript
浅析IE10兼容性问题(frameset的cols属性)
2014/01/03 Javascript
深入探讨JavaScript、JQuery屏蔽网页鼠标右键菜单及禁止选择复制
2014/06/10 Javascript
JavaScript的内存释放问题详解
2015/01/21 Javascript
jQuery插件dataTables添加序号列的方法
2016/07/06 Javascript
jQuery web 组件 后台日历价格、库存设置的代码
2016/10/14 Javascript
webpack实现热更新(实施同步刷新)
2017/07/28 Javascript
vue组件父子间通信详解(三)
2017/11/07 Javascript
JS实现面向对象继承的5种方式分析
2018/07/21 Javascript
Nodejs实现多文件夹文件同步
2018/10/17 NodeJs
微信小程序实现订单倒计时
2020/11/01 Javascript
js中offset,client , scroll 三大元素知识点总结
2019/09/11 Javascript
Vue 实现一个简单的鼠标拖拽滚动效果插件
2020/12/10 Vue.js
python中去空格函数的用法
2014/08/21 Python
python服务器端收发请求的实现代码
2014/09/29 Python
python实现从网络下载文件并获得文件大小及类型的方法
2015/04/28 Python
利用Python脚本在Nginx和uwsgi上部署MoinMoin的教程
2015/05/05 Python
Pycharm编辑器技巧之自动导入模块详解
2017/07/18 Python
python中scikit-learn机器代码实例
2018/08/05 Python
python使用PIL模块获取图片像素点的方法
2019/01/08 Python
Python 函数用法简单示例【定义、参数、返回值、函数嵌套】
2019/09/20 Python
python3实现语音转文字(语音识别)和文字转语音(语音合成)
2020/10/14 Python
详解CSS3中border-image的使用
2015/07/18 HTML / CSS
波兰珠宝品牌:YES
2019/08/09 全球购物
在职研究生自我鉴定
2013/10/16 职场文书
秋天的雨教学反思
2014/04/27 职场文书
领导干部群众路线教育实践活动个人对照检查材料
2014/09/23 职场文书
作弊检讨书
2015/01/27 职场文书
肖申克的救赎观后感
2015/06/02 职场文书
活动简报范文
2015/07/22 职场文书
详解MySql中InnoDB存储引擎中的各种锁
2022/02/12 MySQL