PTT 文章排序問題
Hi, 老師
以下有兩個問題,再跟您請教一下
一、時間排序轉換
在解答中,您們針對時間的轉換有進行一些說明與介紹,但是在這個範例中,我發現所取得的 List 為空
可否再麻煩請您確認一下
# 我們發現這個時間好像不是正確的,原因是我們前面存到的時間,其實不是正確的格式
# 改成 Gossiping 版,發生錯誤,因為八卦版會跳轉到一個「十八歲的同意驗證頁面」導致錯誤。
# 參考圖片下載時的解法,加上 cookies 繞過驗證(後面課程會再進行補充)
import requests
from bs4 import BeautifulSoup
url = 'https://www.ptt.cc/bbs/Gossiping/index.html'
r = requests.get(url, cookies={'over18': '1'})
soup = BeautifulSoup(r.text, "html5lib")
posts = []
for d in soup.find_all(class_="title"):
try:
post = {}
post['標題'] = d.text.replace('\t', '').replace('\n', '')
r = BeautifulSoup(requests.get('https://www.ptt.cc'+d.find('a')['href'], cookies={'over18': '1'}).text, "html5lib")
post['作者'] = r.find(class_='article-meta-value').text
post['時間'] = r.find_all(class_='article-meta-value')[-1].text
post['時間'] = datetime.strptime(post['時間'], "%a %b %d %H:%M:%S %Y")
# 時間轉換:https://stackoverflow.com/questions/10256093/how-to-convert-ctime-to-datetime-in-python
posts.append(post)
except:
continue
print(posts)
posts = sorted(posts, key= lambda x: x['時間'])
posts[-1]
[]
---------------------------------------------------------------------------
IndexError Traceback (most recent call last)
<ipython-input-13-e95f5211bb72> in <module>
31 print(posts)
32 posts = sorted(posts, key= lambda x: x['時間'])
---> 33 posts[-1]
IndexError: list index out of range
PS: 把時間轉換拿走,確認可以正常取得資料
# 我們發現這個時間好像不是正確的,原因是我們前面存到的時間,其實不是正確的格式
# 改成 Gossiping 版,發生錯誤,因為八卦版會跳轉到一個「十八歲的同意驗證頁面」導致錯誤。
# 參考圖片下載時的解法,加上 cookies 繞過驗證(後面課程會再進行補充)
import requests
from bs4 import BeautifulSoup
url = 'https://www.ptt.cc/bbs/Gossiping/index.html'
r = requests.get(url, cookies={'over18': '1'})
soup = BeautifulSoup(r.text, "html5lib")
posts = []
for d in soup.find_all(class_="title"):
try:
post = {}
post['標題'] = d.text.replace('\t', '').replace('\n', '')
r = BeautifulSoup(requests.get('https://www.ptt.cc'+d.find('a')['href'], cookies={'over18': '1'}).text, "html5lib")
post['作者'] = r.find(class_='article-meta-value').text
post['時間'] = r.find_all(class_='article-meta-value')[-1].text
# post['時間'] = datetime.strptime(post['時間'], "%a %b %d %H:%M:%S %Y")
# 時間轉換:https://stackoverflow.com/questions/10256093/how-to-convert-ctime-to-datetime-in-python
posts.append(post)
except:
continue
print(posts)
posts = sorted(posts, key= lambda x: x['時間'])
posts[-1]
[{'標題': '[問卦] 即時通 狀態上掛自己無名是不是很秋?', '作者': 'z72117211 (高橋李依我老婆)', '時間': 'Mon Mar 23 20:35:31 2020'}, {'標題': '[問卦] 正妹是不是想賺很多錢都很容易?', '作者': 'great5566 (陳央)', '時間': 'Mon Mar 23 20:35:43 2020'}, {'標題': '[問卦] 內地真的穩了?', '作者': 'ptt5566fan (5566)', '時間': 'Mon Mar 23 20:36:18 2020'}, {'標題': '[政治] 要怎麼跟迷信姓名學的人合理溝通??', '作者': 'q347 (q347)', '時間': 'Mon Mar 23 20:36:20 2020'}, {'標題': '[新聞] 瑞士單日暴增千例新冠肺炎確診 累積至806', '作者': 'silentknight (清純男)', '時間': 'Mon Mar 23 20:36:32 2020'}, {'標題': '[問卦] 窮養小孩會比不生小孩好嗎?', '作者': 'DavidJam (越小越簡單越好)', '時間': 'Mon Mar 23 20:36:32 2020'}, {'標題': '[問卦] 臺灣如果宣佈退出奧運,影響力多大', '作者': 'lauwei (lauwei)', '時間': 'Mon Mar 23 20:37:15 2020'}, {'標題': '[問卦] 國安基金護盤若是嚴重虧損會如何?', '作者': 'aitt (非主流,有何不可(M))', '時間': 'Mon Mar 23 20:38:12 2020'}, {'標題': 'Re: [問卦] 請問我這樣能買多少片口罩?', '作者': 'sunblues (太陽藍)', '時間': 'Mon Mar 23 20:38:55 2020'}, {'標題': '[問卦] 碇真嗣會選綾波零.明日香.渚薰其中哪個? ', '作者': 'lovesaber (幻想神)', '時間': 'Mon Mar 23 20:39:11 2020'}, {'標題': '[問卦] ☹☹☹☹☹☹☹☹☹☹☹☹☹☹☹☹☹☹', '作者': 'ILoveMegumin (中島小姐家裡的刻印蟲)', '時間': 'Mon Mar 23 20:39:35 2020'}, {'標題': 'Re: [新聞] N號房「趙博士」正面露出!\u3000大學才剛畢', '作者': 'palindromes ()', '時間': 'Mon Mar 23 20:39:48 2020'}, {'標題': '[問卦] 有多少人的下巴有疤痕?', '作者': 'mariewtsai (是狗狗可愛還是貓貓可愛)', '時間': 'Mon Mar 23 20:40:03 2020'}, {'標題': '[問卦]嘔嘔嘔! 肥宅會分泌油脂!?', '作者': 'jp6vu04boy (多多)', '時間': 'Mon Mar 23 20:40:24 2020'}, {'標題': '[問卦] 推薦一些youtube十萬訂閱以下的', '作者': 'PHXNASH13 (永遠的鳳凰NASH)', '時間': 'Mon Mar 23 20:40:34 2020'}, {'標題': '[問卦] 單戀的時間', '作者': 'bread220 (blessing in disguise)', '時間': 'Mon Mar 23 20:41:13 2020'}, {'標題': 'Re: [問卦] 如果中國全力發展半導體?', '作者': 'wnglon (冷麵笑匠)', '時間': 'Mon Mar 23 20:41:15 2020'}, {'標題': 'Re: [問卦] 如果中國全力發展半導體?', '作者': 'nk (除了累還剩下啥...)', '時間': 'Mon Mar 23 20:41:44 2020'}, {'標題': '[協尋] 埔里埔霧公路/七堵俊賢路/高雄博愛同盟路/交大/國一南下42', '作者': 'arsonlolita (板主)', '時間': 'Tue Mar 17 11:28:02 2020'}, {'標題': '[公告] 八卦闆闆規(2020.03.21)', '作者': 'DreamYeh (天使)', '時間': 'Sat Mar 21 00:42:44 2020'}, {'標題': '[公告] 說明[政治]分類使用方式', '作者': 'arsonlolita (板主)', '時間': 'Sat Mar 21 15:03:36 2020'}, {'標題': '[協尋] 家人妹妹失蹤', '作者': 'mirai11 (Mace & Nutmeg)', '時間': 'Sun Mar 22 02:42:57 2020'}, {'標題': '[公告] 三月份置底閒聊文', '作者': 'DreamYeh (天使)', '時間': 'Tue Mar 3 11:34:55 2020'}]
[14]:
{'標題': '[協尋] 埔里埔霧公路/七堵俊賢路/高雄博愛同盟路/交大/國一南下42', '作者': 'arsonlolita (板主)', '時間': 'Tue Mar 17 11:28:02 2020'}
二、PTT 置頂文章判別
另外為上題的衍生問題,PPT 的置頂文章會影響最新文章排序的判別,已經使用了依照時間進行排序,但是仍無法判斷最新發布文章,請問這該如何解決?謝謝!
newPapers = []
for d in soup.find_all(class_='title'):
try:
newPaper = {}
newPaper['標題'] = d.text.replace('\t', ' ').replace('\n', ' ')
r = BeautifulSoup(requests.get('https://www.ptt.cc'+d.find('a')['href'], cookies={'over18': '1'}).text, 'xml')
newPaper['作者'] = r.find(class_='article-meta-value').text
newPaper['時間'] = r.find_all(class_='article-meta-value')[-1].text
# newPaper['時間'] = datetime.strptime(newPaper['時間'], "%b %d %H:%M:%S %Y")
# 時間轉換:https://stackoverflow.com/questions/10256093/how-to-convert-ctime-to-datetime-in-python
newPapers.append(newPaper)
except:
continue
newPapers = sorted(newPapers, key=lambda x: x['時間'])
newPapers
print(newPapers[-1])
[{'標題': ' Re: [問卦] 興趣是吃東西的人 是豬嗎? ',
'作者': 'Dinenger (低能兒)',
'時間': 'Mon Mar 23 19:39:29 2020'},
{'標題': ' [問卦] 『小玉』算是洗白了嗎? ',
'作者': 'sasaki3630 (♥伊莉雅の老公 ♥)',
'時間': 'Mon Mar 23 19:39:30 2020'},
{'標題': ' [爆卦] 鬼島夢想家(32)融資斷頭 ',
'作者': 'rhino0314 (鬼島夢想家)',
'時間': 'Mon Mar 23 19:39:52 2020'},
{'標題': ' Re: [政治] 口罩很多盡量買!陳時中:1400萬片口罩2. ',
'作者': 'rexlin (Some like it hot!!)',
'時間': 'Mon Mar 23 19:40:09 2020'},
{'標題': ' [問卦] 士\u3000林\u3000板\u3000聚 ',
'作者': 'wuyiulin (機掰客家人)',
'時間': 'Mon Mar 23 19:40:18 2020'},
{'標題': ' [問卦] 為何藥局還是一堆人排口罩== ',
'作者': 'westdoorcard (West)',
'時間': 'Mon Mar 23 19:40:20 2020'},
{'標題': ' [政治] 中共果然開始有動作了 ',
'作者': 'dete911 (dete911)',
'時間': 'Mon Mar 23 19:40:41 2020'},
{'標題': ' Re: [問卦] 熊貓的外送員 很愛騙說他到了? ',
'作者': 'poeta (鍵盤詩人)',
'時間': 'Mon Mar 23 19:40:41 2020'},
{'標題': ' [問卦] 哪個居住地一講出來就覺得很有格調? ',
'作者': 'suileen (我為櫻島麻衣而活)',
'時間': 'Mon Mar 23 19:40:44 2020'},
{'標題': ' Re: [問卦] +26確診 ',
'作者': 'Bionut (生物堅果)',
'時間': 'Mon Mar 23 19:41:19 2020'},
{'標題': ' [新聞] 坦承「隨機開車門想偷東西」 法官判無罪 ',
'作者': 'Rrrxddd (有噴 鋼鐵LULU粉 RR)',
'時間': 'Mon Mar 23 19:41:24 2020'},
{'標題': ' Re: [問卦] 預言成真KFK...? ',
'作者': 'a810086 (眼睛業障重)',
'時間': 'Mon Mar 23 19:41:28 2020'},
{'標題': ' [問卦] 覺得自己有點症狀 第一步要做甚麼?? ',
'作者': 'a152508 (a十五二十五零八)',
'時間': 'Mon Mar 23 19:41:32 2020'},
{'標題': ' [問卦] 臺北市如果封城 實務上要怎麼做? ',
'作者': 'iphone15 (哀鳳15)',
'時間': 'Mon Mar 23 19:42:49 2020'},
{'標題': ' [公告] 八卦闆闆規(2020.03.21) ',
'作者': 'DreamYeh (天使)',
'時間': 'Sat Mar 21 00:42:44 2020'},
{'標題': ' [公告] 說明[政治]分類使用方式 ',
'作者': 'arsonlolita (板主)',
'時間': 'Sat Mar 21 15:03:36 2020'},
{'標題': ' [協尋] 家人妹妹失蹤 ',
'作者': 'mirai11 (Mace Nutmeg)',
'時間': 'Sun Mar 22 02:42:57 2020'},
{'標題': ' [公告] 三月份置底閒聊文 ',
'作者': 'DreamYeh (天使)',
'時間': 'Tue Mar 3 11:34:55 2020'},
{'標題': ' [協尋] 埔里埔霧公路/七堵俊賢路/高雄博愛同盟路/交大/國一南下42 ',
'作者': 'arsonlolita (板主)',
'時間': 'Tue Mar 17 11:28:02 2020'}]
{'標題': ' [協尋] 埔里埔霧公路/七堵俊賢路/高雄博愛同盟路/交大/國一南下42 ', '作者': 'arsonlolita (板主)', '時間': 'Tue Mar 17 11:28:02 2020'}
回答列表
-
2020/03/24 上午 00:00張維元 (WeiYuan)贊同數:1不贊同數:0留言數:1
嗨,
下次兩個問題建議分成兩篇問答討論,這樣方便之後遇到問題的同學。
第一個問題,可以先把「try-except」拿掉,去看一下真正的錯誤原因是什麼。目前只要出錯就會進入到 except 導致看不出來錯誤原因為何。第二個問題應該是說你抓的文章中會包含置頂文章,如果直接排序會分不出來哪些是置頂哪些是一般的文章,我這樣理解對嗎?
如果這個回答對你有幫助請主動點選「有幫助」的按鈕,也可以追蹤我的GITHUB帳號。若還有問題的話,也歡迎繼續再追問或者把你理解的部分整理上來,我都會提供你 Review 和 Feedback 😃😃😃
-
2020/03/24 上午 11:14許義翔贊同數:2不贊同數:0留言數:1
Hi, 老師
感謝您提供的建議檢查的方法,我找到原因了!在這個問題官方解答有個地方有遺漏。
並未設置導入「時間模組」
from datetime import datetime
解答修正如下
# 我們發現這個時間好像不是正確的,原因是我們前面存到的時間,其實不是正確的格式
# 改成 Gossiping 版,發生錯誤,因為八卦版會跳轉到一個「十八歲的同意驗證頁面」導致錯誤。
# 參考圖片下載時的解法,加上 cookies 繞過驗證(後面課程會再進行補充)
import requests
from bs4 import BeautifulSoup
from datetime import datetime
url = 'https://www.ptt.cc/bbs/Gossiping/index.html'
r = requests.get(url, cookies={'over18': '1'})
soup = BeautifulSoup(r.text, "html5lib")
posts = []
for d in soup.find_all(class_="title"):
try:
post = {}
post['標題'] = d.text.replace('\t', '').replace('\n', '')
r = BeautifulSoup(requests.get('https://www.ptt.cc'+d.find('a')['href'], cookies={'over18': '1'}).text, "html5lib")
post['作者'] = r.find(class_='article-meta-value').text
post['時間'] = r.find_all(class_='article-meta-value')[-1].text
post['時間'] = datetime.strptime(post['時間'], "%a %b %d %H:%M:%S %Y")
# 時間轉換:https://stackoverflow.com/questions/10256093/how-to-convert-ctime-to-datetime-in-python
posts.append(post)
except:
continue
posts = sorted(posts, key= lambda x: x['時間'])
posts[-1]{'標題': '[新聞] 中國駐法大使館推特轉發疫情來源涉美...',
'作者': 'observer0117 (神奇ob)',
'時間': datetime.datetime(2020, 3, 24, 11, 2, 11)}關於第二個問題也是承接第一個問題
因為 datetime 設置失效,所以所排列輸出的為 PTT 預先的輸出排列
(官方排列置頂文章為最後一個 List [-1])
所以使用 datetime 後置頂文章會隨著時間重新排列
以上!