我們常見的爬蟲基本上都是命令行的樣式,對(duì)于爬蟲而言這樣頁面就足夠了。但是進(jìn)行數(shù)據(jù)分析的時(shí)候這樣的頁面是遠(yuǎn)遠(yuǎn)不夠的。今天我們介紹一個(gè)python爬取車票信息的代碼,使用pyqt5實(shí)現(xiàn)GUI頁面的部分。話不多說,快來了解這個(gè)項(xiàng)目吧。
1、搭載QT環(huán)境
按win+R輸入 pip install pyqt5 下載QT5 當(dāng)然也可以去Qt的官網(wǎng)的下載 ,使用命令行更快捷方便 所以建議使用命令行 ,去官網(wǎng)下載安裝有它的好處就是不用自己安裝 toosl
作者使用的是pyCharm 完成后期的后臺(tái)程序設(shè)置,使用pyCharm 外部工具鏈接把Designer,pyUIC,qrcTopy程序加進(jìn)去
2、主窗體設(shè)置
打Qt5主程序設(shè)置主窗體,設(shè)計(jì)完成保存為windows
添加到創(chuàng)建好的python項(xiàng)目中,然后選中單擊右鍵-》External toosl-》Py UIC 將ui文件轉(zhuǎn)換成py文件
windows.py
from PyQt5.QtGui import QPalette, QPixmap, QColor # result = [] # 保存車次分類后最后的數(shù)據(jù) # UI類 class Ui_MainWindow(object): # 設(shè)置UI的方法 def setupUi(self, MainWindow): MainWindow.setObjectName("MainWindow") # 設(shè)置窗體對(duì)象名稱 MainWindow.resize(960, 786) # 設(shè)置窗體大小 MainWindow.setMinimumSize(QtCore.QSize(960, 786)) # 主窗體最小值 MainWindow.setMaximumSize(QtCore.QSize(960, 786)) # 主窗體最大值 self.centralwidget = QtWidgets.QWidget(MainWindow) # 主窗體的widget控件 self.centralwidget.setObjectName("centralwidget") # 設(shè)置對(duì)象名稱 # 通過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) # 設(shè)置調(diào)色板 # 查詢部分的widget self.widget_query = QtWidgets.QWidget(self.centralwidget) self.widget_query.setGeometry(QtCore.QRect(0, 141, 960, 80)) self.widget_query.setObjectName("widget_query") # 開啟自動(dòng)填充背景 self.widget_query.setAutoFillBackground(True) palette = QPalette() # 調(diào)色板類 palette.setBrush(QPalette.Background, QtGui.QBrush(QtGui.QPixmap('img/bg2.png'))) # 設(shè)置背景圖片 self.widget_query.setPalette(palette) # 為控件設(shè)置對(duì)應(yīng)的調(diào)色板即可 # 出發(fā)地與對(duì)應(yīng)的編輯框控件 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() # 創(chuàng)建QFont()對(duì)象 font.setPointSize(13) # 設(shè)置編輯框字體大小的值 self.textEdit.setFont(font) # 設(shè)置編輯框字體 self.textEdit.setObjectName("textEdit") # 出發(fā)地對(duì)應(yīng)編輯框?qū)ο竺Q # 目的地與對(duì)應(yīng)的編輯框 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") # 出發(fā)日與有對(duì)應(yīng)的編輯框 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") # 開啟自動(dòng)填充背景 self.widget_checkBox.setAutoFillBackground(True) palette = QPalette() # 調(diào)色板類 palette.setBrush(QPalette.Background, QtGui.QBrush(QtGui.QPixmap('img/bg3.png'))) # 設(shè)置背景圖片 self.widget_checkBox.setPalette(palette) # 設(shè)置調(diào)色板控件對(duì)應(yīng)的方法即可 # 顯示車次類型文字 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") # 選擇動(dòng)車 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") # 選擇直達(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) # 設(shè)置調(diào)色板 # 顯示車次信息的列表 self.tableView = QtWidgets.QTableView(self.centralwidget) self.tableView.setGeometry(QtCore.QRect(0, 320, 960, 440)) self.tableView.setObjectName("tableView") self.model = QStandardItemModel()# 創(chuàng)建存儲(chǔ)數(shù)據(jù)的模式 # 根據(jù)空間自動(dòng)改變列寬度并且不可修改列寬度 self.tableView.horizontalHeader().setSectionResizeMode(QHeaderView.Stretch) # 設(shè)置表頭不可見 self.tableView.horizontalHeader().setVisible(False) # 縱向表頭不可見 self.tableView.verticalHeader().setVisible(False) # 設(shè)置表格內(nèi)容文字大小 font = QtGui.QFont() font.setPointSize(10) self.tableView.setFont(font) # 設(shè)置表格內(nèi)容不可編輯 self.tableView.setEditTriggers(QAbstractItemView.NoEditTriggers) # 垂直滾動(dòng)條始終開啟 self.tableView.setVerticalScrollBarPolicy(Qt.ScrollBarAlwaysOn) # 主窗體設(shè)置主Widget MainWindow.setCentralWidget(self.centralwidget) self.retranslateUi(MainWindow) # 調(diào)用retranslateUi方法顯示窗體文字 QtCore.QMetaObject.connectSlotsByName(MainWindow) # 關(guān)聯(lián)信號(hào)槽 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-直達(dá)")) self.checkBox_D.setText(_translate("MainWindow", "D-動(dòng)車")) self.checkBox_G.setText(_translate("MainWindow", "GC-高鐵")) self.label_type.setText(_translate("MainWindow", "車次類型:")) self.label.setText(_translate("MainWindow", "出發(fā)地:")) self.label_2.setText(_translate("MainWindow", "目的地:")) self.label_3.setText(_translate("MainWindow", "出發(fā)日:")) self.pushButton.setText(_translate("MainWindow", "查詢")) def show_MainWindow(): app = QtWidgets.QApplication(sys.argv) # 首先必須實(shí)例化QApplication類,作為GUI主程序入口 MainWindow = QtWidgets.QMainWindow() # 實(shí)例化QtWidgets.QMainWindow類,創(chuàng)建自帶menu的窗體類型QMainWindow ui = Ui_MainWindow() # 實(shí)例UI類 ui.setupUi(MainWindow) # 設(shè)置窗體UI MainWindow.show() # 顯示窗體 sys.exit(app.exec_()) # 當(dāng)來自操作系統(tǒng)的分發(fā)事件指派調(diào)用窗口時(shí), # 應(yīng)用程序開啟主循環(huán)(mainloop)過程, # 當(dāng)窗口創(chuàng)建完成,需要結(jié)束主循環(huán)過程, # 這時(shí)候呼叫sys.exit()方法來,結(jié)束主循環(huán)過程退出, # 并且釋放內(nèi)存。為什么用app.exec_()而不是app.exec()? # 因?yàn)閑xec是python系統(tǒng)默認(rèn)關(guān)鍵字,為了以示區(qū)別,所以寫成exec_ if __name__ == "__main__": if isStations() == False: # 判斷是否有所有車站的文件,沒有就下載,有就直接顯示窗體 getStation() # 下載所有車站文件 show_MainWindow() # 調(diào)用顯示窗體的方法 else: show_MainWindow() # 調(diào)用顯示窗體的方法
3、下載網(wǎng)站文件
在這之前我們的先去12306網(wǎng)站分析相關(guān)參數(shù)
獲取完整的查票地址,注意每一個(gè)時(shí)期的地址是會(huì)發(fā)生改變的
創(chuàng)建用于下載網(wǎng)站文件的py文件,get_stations.py
import re import requests import os def getStation(): # 發(fā)送請(qǐng)求獲取所有車站名稱,通過輸入的站名稱轉(zhuǎn)化查詢地址的參數(shù) url = 'https://kyfw.12306.cn/otn/resources/js/framework/station_name.js?station_version=1.9190' response = requests.get(url, verify=True) # 請(qǐng)求并進(jìn)行驗(yàn)證 stations = re.findall(u'([u4e00-u9fa5]+)|([A-Z]+)', response.text) # 獲取需要的車站名稱 stations = dict(stations) # 轉(zhuǎn)換為dic stations = str(stations) # 轉(zhuǎn)換為字符串類型否則無法寫入文件 write(stations) #調(diào)用寫入方法 def write(stations): file = open('stations.text', 'w', encoding='utf_8_sig') # 以寫模式打開文件 file.write(stations) # 寫入數(shù)據(jù) 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、車票信息的請(qǐng)求與顯示
創(chuàng)建 query_request.py文件用于發(fā)現(xiàn)數(shù)據(jù)后的處理工作
from get_stations import * import requests '''5-7 目的地 3 車次 6 出發(fā)地 8 出發(fā)時(shí)間 9 到達(dá)時(shí)間 10 歷時(shí) 26 無坐 29 硬座 24 軟座 28 硬臥 33 動(dòng)臥 23 軟臥 21 高級(jí)軟臥 30 二等座 31 一等座 32 商務(wù)座特等座 ''' data = [] # 用于保存整理好的車次信息 type_data = [] # 保存車次分類后最后的數(shù)據(jù) 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() # 清空數(shù)據(jù) type_data.clear() # 清空車次分類保存的數(shù)據(jù) # 查詢請(qǐng)求地址 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) # 發(fā)送查詢請(qǐng)求 response = requests.get(url=url,headers=headers) # # 將json數(shù)據(jù)轉(zhuǎn)換為字典類型,通過鍵值對(duì)取數(shù)據(jù) result = response.json() result = result['data']['result'] # 判斷車站文件是否存在 if isStations() == True: stations = eval(read()) # 讀取所有車站并轉(zhuǎn)換為dic類型 if len(result) != 0: # 判斷返回?cái)?shù)據(jù)是否為空 for i in result: # # 分割數(shù)據(jù)并添加到列表中 tmp_list = i.split('|') # 因?yàn)椴樵兘Y(jié)果中出發(fā)站和到達(dá)站為站名的縮寫字母,所以需要在車站庫中找到對(duì)應(yīng)的車站名稱 from_station = list(stations.keys())[list(stations.values()).index(tmp_list[6])] to_station = list(stations.keys())[list(stations.values()).index(tmp_list[7])] # 創(chuàng)建座位數(shù)組,由于返回的座位數(shù)據(jù)中含有空既“”,所以將空改成--這樣好識(shí)別 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 = [] # 循環(huán)將座位信息中的空既“”,改成--這樣好識(shí)別 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: # 循環(huán)所有火車數(shù)據(jù) i = g[0].startswith('G') # 判斷車次首字母是不是高鐵 if i: # 如果是將該條信息添加到高鐵數(shù)據(jù)中 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) # 獲取動(dòng)車信息的方法 def d_vehicle(): if len(data) != 0: for d in data: # 循環(huán)所有火車數(shù)據(jù) i = d[0].startswith('D') # 判斷車次首字母是不是動(dòng)車 if i == True: # 如果是將該條信息添加到動(dòng)車數(shù)據(jù)中 type_data.append(d) # 移除動(dòng)車信息的方法 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: # 移除動(dòng)車信息 type_data.remove(d) # 獲取直達(dá)車信息的方法 def z_vehicle(): if len(data) != 0: for z in data: # 循環(huán)所有火車數(shù)據(jù) i = z[0].startswith('Z') # 判斷車次首字母是不是直達(dá) if i == True: # 如果是將該條信息添加到直達(dá)數(shù)據(jù)中 type_data.append(z) # 移除直達(dá)車信息的方法 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: # 移除直達(dá)車信息 type_data.remove(z) # 獲取特快車信息的方法 def t_vehicle(): if len(data) != 0: for t in data: # 循環(huán)所有火車數(shù)據(jù) i = t[0].startswith('T') # 判斷車次首字母是不是特快 if i == True: # 如果是將該條信息添加到特快車數(shù)據(jù)中 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) # 獲取快速車數(shù)據(jù)的方法 def k_vehicle(): if len(data) != 0: for k in data: # 循環(huán)所有火車數(shù)據(jù) i = k[0].startswith('K') # 判斷車次首字母是不是快車 if i == True: # 如果是將該條信息添加到快車數(shù)據(jù)中 type_data.append(k) # 移除快速車數(shù)據(jù)的方法 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)創(chuàng)建 get_time 和is_valid.date方法用判斷日期是否有效
def get_time(): # 獲得當(dāng)前時(shí)間時(shí)間戳 now = int(time.time()) # 轉(zhuǎn)換為其它日期格式,如:"%Y-%m-%d %H:%M:%S" timeStruct = time.localtime(now) strTime = time.strftime("%Y-%m-%d", timeStruct) return strTime def is_valid_date(str): '''判斷是否是一個(gè)有效的日期字符串''' try: time.strptime(str, "%Y-%m-%d") return True except: return False
(2)創(chuàng)建車次分類復(fù)選事件處理方法
# 將所有車次分類復(fù)選框取消勾選 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) # 高鐵復(fù)選框事件處理 def change_G(self, state): # 選中將高鐵信息添加到最后要顯示的數(shù)據(jù)當(dāng)中 if state == QtCore.Qt.Checked: # 獲取高鐵信息 g_vehicle() # 通過表格顯示該車型數(shù)據(jù) self.displayTable(len(type_data), 16, type_data) else: # 取消選中狀態(tài)將移除該數(shù)據(jù) r_g_vehicle() self.displayTable(len(type_data), 16, type_data) # 動(dòng)車復(fù)選框事件處理 def change_D(self, state): # 選中將動(dòng)車信息添加到最后要顯示的數(shù)據(jù)當(dāng)中 if state == QtCore.Qt.Checked: # 獲取動(dòng)車信息 d_vehicle() # 通過表格顯示該車型數(shù)據(jù) self.displayTable(len(type_data), 16, type_data) else: # 取消選中狀態(tài)將移除該數(shù)據(jù) r_d_vehicle() self.displayTable(len(type_data), 16, type_data) # 直達(dá)復(fù)選框事件處理 def change_Z(self, state): # 選中將直達(dá)車信息添加到最后要顯示的數(shù)據(jù)當(dāng)中 if state == QtCore.Qt.Checked: # 獲取直達(dá)車信息 z_vehicle() self.displayTable(len(type_data), 16, type_data) else: # 取消選中狀態(tài)將移除該數(shù)據(jù) r_z_vehicle() self.displayTable(len(type_data), 16, type_data) # 特快復(fù)選框事件處理 def change_T(self, state): # 選中將特快車信息添加到最后要顯示的數(shù)據(jù)當(dāng)中 if state == QtCore.Qt.Checked: # 獲取特快車信息 t_vehicle() self.displayTable(len(type_data), 16, type_data) else: # 取消選中狀態(tài)將移除該數(shù)據(jù) r_t_vehicle() self.displayTable(len(type_data), 16, type_data) # 快速復(fù)選框事件處理 def change_K(self, state): # 選中將快車信息添加到最后要顯示的數(shù)據(jù)當(dāng)中 if state == QtCore.Qt.Checked: # 獲取快速車信息 k_vehicle() self.displayTable(len(type_data), 16, type_data) else: # 取消選中狀態(tài)將移除該數(shù)據(jù) r_k_vehicle() self.displayTable(len(type_data), 16, type_data)
(3)創(chuàng)建messageDialog與displayTable方法分別用于非法輸入的處理與車輛信息的顯示
# 顯示消息提示框,參數(shù)title為提示框標(biāo)題文字,message為提示信息 def messageDialog(self, title, message): msg_box = QMessageBox(QMessageBox.Warning, title, message) msg_box.exec_() # 顯示車次信息的表格 # train參數(shù)為共有多少趟列車,該參數(shù)作為表格的行。 # info參數(shù)為每趟列車的具體信息,例如有座、無座臥鋪等。該參數(shù)作為表格的列 def displayTable(self, train, info, data): self.model.clear() for row in range(train): for column in range(info): # 添加表格內(nèi)容 item = QStandardItem(data[row][column]) # 向表格存儲(chǔ)模式中添加表格具體信息 self.model.setItem(row, column, item) # 設(shè)置表格存儲(chǔ)數(shù)據(jù)的模式 self.tableView.setModel(self.model)
(4)創(chuàng)建on_click方法該方法用于查詢事件的處理
# 查詢按鈕的單擊事件 def on_click(self): get_from = self.textEdit.toPlainText() # 獲取出發(fā)地 get_to = self.textEdit_2.toPlainText() # 獲取到達(dá)地 get_date = self.textEdit_3.toPlainText() # 獲取出發(fā)時(shí)間 # 判斷車站文件是否存在 if isStations() == True: stations = eval(read()) # 讀取所有車站并轉(zhuǎn)換為dic類型 # 判斷所有參數(shù)是否為空,出發(fā)地、目的地、出發(fā)日期 if get_from != "" and get_to != "" and get_date != "": # 判斷輸入的車站名稱是否存在,以及時(shí)間格式是否正確 if get_from in stations and get_to in stations and is_valid_date(get_date): # 獲取輸入的日期是當(dāng)前年初到現(xiàn)在一共過了多少天 inputYearDay = time.strptime(get_date, "%Y-%m-%d").tm_yday # 獲取系統(tǒng)當(dāng)前日期是當(dāng)前年初到現(xiàn)在一共過了多少天 yearToday = time.localtime(time.time()).tm_yday # 計(jì)算時(shí)間差,也就是輸入的日期減掉系統(tǒng)當(dāng)前的日期 timeDifference = inputYearDay - yearToday # 判斷時(shí)間差為0時(shí)證明是查詢當(dāng)前的查票, # 以及29天以后的車票。12306官方要求只能查詢30天以內(nèi)的車票 if timeDifference >= 0 and timeDifference <= 28: from_station = stations[get_from] # 在所有車站文件中找到對(duì)應(yīng)的參數(shù),出發(fā)地 to_station = stations[get_to] # 目的地 data = query(get_date, from_station, to_station) # 發(fā)送查詢請(qǐng)求,并獲取返回的信息 self.checkBox_default() if len(data) != 0: # 判斷返回的數(shù)據(jù)是否為空 # 如果不是空的數(shù)據(jù)就將車票信息顯示在表格中 self.displayTable(len(data), 16, data) else: self.messageDialog('警告', '沒有返回的網(wǎng)絡(luò)數(shù)據(jù)!') else: self.messageDialog('警告', '超出查詢?nèi)掌诘姆秶鷥?nèi),' '不可查詢昨天的車票信息,以及29天以后的車票信息!') else: self.messageDialog('警告', '輸入的站名不存在,或日期格式不正確!') else: self.messageDialog('警告', '請(qǐng)?zhí)顚戃囌久Q!') else: self.messageDialog('警告', '未下載車站查詢文件!')
(5)在retranslateUi方法中分別加入以下代碼
self.textEdit_3.setText(get_time()) # 出發(fā)日顯示當(dāng)天日期 self.pushButton.clicked.connect(self.on_click) # 查詢按鈕指定單擊事件的方法 self.checkBox_G.stateChanged.connect(self.change_G) # 高鐵選中與取消事件 self.checkBox_D.stateChanged.connect(self.change_D) # 動(dòng)車選中與取消事件 self.checkBox_Z.stateChanged.connect(self.change_Z) # 直達(dá)車選中與取消事件 self.checkBox_T.stateChanged.connect(self.change_T) # 特快車選中與取消事件 self.checkBox_K.stateChanged.connect(self.change_K) # 快車選中與取消事件
到此結(jié)束,以下是運(yùn)行結(jié)果
到此這篇python爬取車票信息并使用pyqt5實(shí)現(xiàn)GUI的文章就介紹到這了,更多python學(xué)習(xí)內(nèi)容請(qǐng)搜索W3Cschool以前的文章或繼續(xù)瀏覽下面的相關(guān)文章。