LoginSignup
2
12

More than 3 years have passed since last update.

Pythonでテキストマイニング ~スクレイピング編~

Last updated at Posted at 2019-11-12

 仕事柄機械学習とかそのあたりを扱っていて、何となくテキストマイニングの方に興味がわいたので、取り組んでみた内容の備忘録として投稿します。
 今回はスクレイピング編なんですが、最終的にはスクレイピングしたテキスト情報を解析していくなんてことを考えているので、そのあたりもまとまったら随時投稿していきます。

実行環境

Python でスクレイピングを行おうと思ったら真っ先に思いついたのがrequests BeautifulSoup だったので、今回はこの組み合わせでいこうと思います。

ちなみに私は普段はJSerなので、スクレイピング関係はよくpuppeteerを利用します。
まぁそれはいいとして、実際にスクレイピングを始めてみましょう。

まずは動くか確認

 pythonでコードを書くとき、もちろん直接「~.py」ファイルに書いて構いませんが、Jupyter Notebookを利用すると出力された結果が見やすいなど色々と便利な部分があるのでテスト程度ならJupyter Notebookを利用することをお勧めします。
 特に今回は、Googleが提供しているGoogle Colaboratoryを使ってテストしてみます。ライブラリのインストールも不要で、Googleのアカウントだけあれば動かせます。

Colaboratoryを開いて新規ノートブック作成
ウェブブラウザでColaboratoryを開いて、
「ファイル」>「Python3の新しいノートブック」から新しいノートブックを作成します。

スクリーンショット (49).png

もはや説明はいらないかと思いますが、中央のエリアにあるセルにコードを記述していきます。
2.png

ライブラリのインポート

import
import  requests
from bs4 import BeautifulSoup

URLの指定
今回は私の職業柄、建築xコンピューテーションのポータルサイトであるArchiFuture Web のヘッドラインニュース 最新10行ニュースをスクレイピングしてみようと思います。
(ArchiFuture)

urlを指定
url = "http://www.archifuture-web.jp/headline/457.html"

requestsを使ってページにアクセス
実際にページにアクセスできるか見てみましょう。

ページにアクセス
res = requests.get(url)
res

これを実行すると、おそらく

レスポンス
<Response [200]>

が返ってくると思います。
HTTPレスポンスコードについて知りたい方はこちらをご参照ください。

ページの中身を見たい場合は、

res.text
レスポンス
'<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">\n<html xmlns="http://www.w3.org/1999/xhtml" lang="ja" xml:lang="ja" dir="ltr" xmlns:og="http://ogp.me/ns#" xmlns:fb="http://www.facebook.com/2008/fbml">\n<head>\n<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />\n<meta http-equiv="Content-Style-Type" content="text/css" />\n<meta http-equiv="Content-Script-Type" content="text/javascript" />\n<!-- [if lt IE]><meta http-equiv="imagetoolbar" content="no" /><![endif] -->\n<title>「Archi Future 2019」が史上最高の来場者数を集めて盛況に開催|Headline(ヘッドライン)|建築 × コンピュテーションのポータルサイト\u3000Archi Future Web</title>\n<meta name="Description" content="建築 × コンピュテーションのポータルサイト「Archi Future Web」です。" />\n<meta name="keywords" content="建築,コンピュテーション,Archi Future">\n<meta property="og:site_name" content="建築 × コンピュテーションのポータルサイト\u3000Archi Future Web">\n<meta property="og:title" content="「Archi Future 2019」が史上最高の来場者数を集めて盛況に開催">\n<meta property="og:type" content="article">\n<meta property="og:description" content="第12回目となる「Archi Future 2019」が、先週の10月25日(金)に開催された。開催当日は、強烈な雨と風のあいにくの天候にも関わらず、来場者数は...">\n<meta property="og:url" content="http://www.archifuture-web.jp/headline/457.html" />\n<meta property="og:image" content="http://www.archifuture-web.jp/headline/img/4/c/4c57dc333a5c9d674ef327289a500800.jpg" />\n<meta property="og:image:width"  content="700" />\n<meta property="og:image:height" content="467" />\n<meta property="og:locale" content="ja_JP">\n<link rel="stylesheet" type="text/css" href="../common/css/import.css" />\n<!-- [if lt IE 9]><link rel="stylesheet" type="text/css" href="../common/css/ie.css" /><![endif] -->\n<script type="text/javascript" src="../common/js/jquery.js"></script>\n<script type="text/javascript" src="../common/js/init.js"></script>\n<script type="text/javascript" src="../common/js/Nav.js"></script>\n</head>\n\n<body id="headline">\n<div id="container">\n<script type="text/javascript">header(\'../\');</script>\n<hr class="hide" />\n\n<h2><img src="img/title.jpg" width="960" height="60" alt="Headline(ヘッドライン)"/></h2>\n\n<div id="content">\n<div class="section">\n<div id="mainContent">\n\n<!--========\u3000SNS\u3000========-->\n<div id="sns" class="clearfix">\n<div class="facebook"><div id="fb-root"></div>\n<script>(function(d, s, id) {\n  var js, fjs = d.getElementsByTagName(s)[0];\n  if (d.getElementById(id)) return;\n  js = d.createElement(s); js.id = id;\n  js.src = "//connect.facebook.net/ja_JP/sdk.js#xfbml=1&appId=152808698121811&version=v2.0";\n  fjs.parentNode.insertBefore(js, fjs);\n}(document, \'script\', \'facebook-jssdk\'));</script><div class="fb-share-button" data-href="http://www.archifuture-web.jp/headline/457.html" data-layout="button"></div></div>\n<div class="twitter"><a href="https://twitter.com/share" class="twitter-share-button" data-lang="ja" data-count="none">ツイート</a> <script>!function(d,s,id){var js,fjs=d.getElementsByTagName(s)[0],p=/^http:/.test(d.location)?\'http\':\'https\';if(!d.getElementById(id)){js=d.createElement(s);js.id=id;js.src=p+\'://platform.twitter.com/widgets.js\';fjs.parentNode.insertBefore(js,fjs);}}(document, \'script\', \'twitter-wjs\');</script></div>\n<!-- /#sns --></div>\n\n<!--========\u3000本文\u3000========-->\n\n<div class="page-title">\n<p><img src="img/icon_new.gif" width="112" height="20" alt="最新10行ニュース"/></p>\n<h2>「Archi Future 2019」が史上最高の来場者数を<br />\r\n集めて盛況に開催</h2>\n</div>\n<p class="page-data">2019.10.28</p>\n\n<p>第12回目となる「Archi Future 2019」が、先週の10月25日(金)に開催された。<br />\r\n開催当日は、強烈な雨と風のあいにくの天候にも関わらず<span style="font-size:12px;">、</span>来場者数は前回比で5.4%の増加の<br />\r\n5,509人となり、史上最高となる来場者数を集める盛況な開催となった。<br />\r\n米国の著名な設計事務所のDiller Scofidio + Renfroによる基調講演や、大手ゼネコンの現場所<br />\r\n長クラス5人によるパネルデ<span style="font-size:12px;">ィ</span>スカ<span style="font-size:12px;">ッ</span>シ<span style="font-size:12px;">ョ</span>ンは<span style="font-size:12px;">、</span>600席に拡大した会場が満席となり<span style="font-size:12px;">、</span>パネルデ<span style="font-size:12px;">ィ</span><br />\r\nスカッションは席をさらに100席増設するほどの盛況ぶりだ<span style="font-size:12px;">っ</span>た。講演会・セミナーはどの講座<br />\r\nもほぼ満席となり<span style="font-size:12px;">、</span>展示会場も大変多くの来場者が訪れ<span style="font-size:12px;">、</span>会場全体が大変活気に満ちた、大盛況<br />\r\nな開催となった。岡田氏と山梨氏の特別対談1、豊田氏と松島氏の特別対談2をはじめ、どの<br />\r\nセッシ<span style="font-size:12px;">ョ</span>ンも建築の新しい方向性と明るい未来を感じさせてくれる、充実した内容であった。<br />\r\nArchi Future 2019のレポートについては、今後、当サイトで紹介する予定だ。<br />\r\n<br />\r\n<a href="http://www.archifuture.jp/2019/" target="_blank"><p class="image al_center"><img src="./img/4/c/4c57dc333a5c9d674ef327289a500800.jpg" alt="\u3000「Archi Future 2019」オフィシャルサイトのトップページ" width="600" height="400"  /></p><p class="caption">\u3000「Archi Future 2019」オフィシャルサイトのトップページ</p></a></p>\n\n<!--========\u3000ナビゲーション\u3000========-->\n<div id="page-navi" class="clearfix clr">\n<ul>\n<li class="go-top"><a href="../index.html"><span>&gt;</span> トップページに戻る</a></li>\n<li class="go-list"><a href="index.html"><span>&gt;</span> 記事一覧に戻る</a></li>\n</ul>\n</div>\n\n<!--========\u3000最新の記事\u3000========-->\n<div id="page-new" class="clr">\n<h2>最新の記事</h2>\n<ul class="list01">\n<li><a href="457.html" target="">「Archi Future 2019」が史上最高の来場者数を集めて盛況に開催<br />\n2019.10.28\u3000<img src="img/icon_new.gif" width="112" height="20" alt="最新10行ニュース"/></a></li>\n<li><a href="456.html" target="">過去最大のスケールでいよいよ明日25日にArchi Future 2019が開催<br />\n2019.10.24\u3000<img src="img/icon_new.gif" width="112" height="20" alt="最新10行ニュース"/></a></li>\n<li><a href="455.html" target="">今週の10月25日(金)に「Archi Future 2019」が開催<br />\n2019.10.21\u3000<img src="img/icon_new.gif" width="112" height="20" alt="最新10行ニュース"/></a></li>\n</ul>\n</div>\n\n<!--========\u3000プレミアムバナー\u3000========-->\n\r\n<div id="premiumbanner" class="al_center clr">\r\n<a href="http://www.archifuture.jp/2019/" class="premiumbanner-left banner" target="_blank" id="premium-24"><img src="../img_banner/premium/img/8/2/8280d8bb17d4c09e872441a1ba21eae0.png" width="270" height="180" alt="Archi Future 2019"/></a>\r\n<a href="http://www.archifuture.jp/2019/" class="premiumbanner-right banner" target="_blank" id="premium-25"><img src="../img_banner/premium/img/6/a/6ad8af52988f0560acbb6c08377d79f3.png" width="270" height="180" alt="Archi Future 2019"/></a>\r\n</div>\r\n\n\n<!--========\u3000レクタングルスーパーバナー\u3000========-->\n\r\n<p id="superbanner" class="al_center"><a href="http://www.archifuture.jp/2019/" class="banner" id="super-14"><img src="../img_banner/super/img/9/9/99ae81e84701bf687561a0ca026bdef0.png" width="600" height="90" alt="Archi Future 2019"/></a></p>\r\n\n\n<!-- /#mainContent --></div>\n\n<div id="sidebar">\n<!--========\u3000広告バナー\u3000========-->\n\r\n<ul id="banner" class="clr">\r\n<li><a href="https://www.cradle.co.jp/" target="_blank" class="banner" id="default-5"><img src="../img_banner/default/img/2/f/2f1b60f601b0f99e6094e32d7fd0b26d.gif" width="270" height="80" alt="ソフトウェアクレイドル"/></a></li>\r\n<li><a href="https://product.metamoji.com/gemba/eyacho/" target="_blank" class="banner" id="default-24"><img src="../img_banner/default/img/2/8/280e8426c1fb78ee0e67b2d009d7c9d2.gif" width="270" height="80" alt="MetaMoJi様"/></a></li>\r\n<li><a href="https://www.izumi-soft.jp/product-category/bim-%E7%A9%BA%E8%AA%BF%E8%A8%AD%E5%82%99%E8%A8%AD%E8%A8%88/" target="_blank" class="banner" id="default-16"><img src="../img_banner/default/img/1/8/18ef602ddf1e9f1e3c5f00a7674725a2.gif" width="270" height="80" alt="イズミシステム設計様"/></a></li>\r\n<li><a href="http://www.nyk-systems.co.jp/" target="_blank" class="banner" id="default-6"><img src="../img_banner/default/img/3/b/3b747d65472ce7be37b8235fc703432d.gif" width="270" height="80" alt="NYKシステムズ様"/></a></li>\r\n<li><a href="http://www.pivot.co.jp/" target="_blank" class="banner" id="default-12"><img src="../img_banner/default/img/6/d/6d10409aeb0b2d23bd73b9ccc70cc08d.gif" width="270" height="80" alt="建築ピボット様"/></a></li>\r\n<li><a href="http://www.applicraft.com/" target="_blank" class="banner" id="default-20"><img src="../img_banner/default/img/9/0/90cc824aac1eda2ba2c37046e55dd79c.gif" width="270" height="80" alt="アプリクラフト様"/></a></li>\r\n<li><a href="http://bit.ly/2Bw8tEc" target="_blank" class="banner" id="default-3"><img src="../img_banner/default/img/7/d/7dbe65f17a1bf153277ba5b466580556.jpg" width="270" height="80" alt="グラフィソフトジャパン様"/></a></li>\r\n<li><a href="https://autode.sk/2TXDSqE" target="_blank" class="banner" id="default-11"><img src="../img_banner/default/img/e/c/ecb06a6b95c9e79935b6a7df88384ab3.jpg" width="270" height="80" alt="オートデスク様"/></a></li>\r\n<li><a href="https://licensecounter.jp/aec-collection-bim/" target="_blank" class="banner" id="default-22"><img src="../img_banner/default/img/1/0/10bcd30f085e6ce4dab4b824c64817a6.gif" width="270" height="80" alt="SB C&S様"/></a></li>\r\n<li><a href="https://www.nvidia.com/ja-jp/design-visualization/industries/architecture-engineering-construction/?nvid=nv-int-pcjp12rrdsfrqr-44523" target="_blank" class="banner" id="default-21"><img src="../img_banner/default/img/d/5/d53b3fe7fec2bc10858a26f88556c8fb.jpg" width="270" height="80" alt="エヌビディア様"/></a></li>\r\n<li><a href=" https://www.aanda.co.jp/Vectorworks2019/index.html?utm_source=af&utm_medium=banner&utm_campaign=bnr_20190921" target="_blank" class="banner" id="default-9"><img src="../img_banner/default/img/7/2/72745a704c3abe2513357559102be116.jpg" width="270" height="80" alt="エーアンドエー様"/></a></li>\r\n<li><a href="http://j-bim.gloobe.jp/" target="_blank" class="banner" id="default-4"><img src="../img_banner/default/img/a/9/a9f022f44cac2878ac5936fcf4b26175.gif" width="270" height="80" alt="福井コンピュータアーキテクト様"/></a></li>\r\n<li><a href="http://www.env-simulation.com" target="_blank" class="banner" id="default-18"><img src="../img_banner/default/img/e/3/e3d7f1694a53705271dc5e751519d0d8.gif" width="270" height="80" alt="環境シミュレーション様"/></a></li>\r\n<li><a href="http://www.f-cadewa.com/" target="_blank" class="banner" id="default-8"><img src="../img_banner/default/img/f/0/f0a5e6fe83e322a2d62a2461855a6c2a.gif" width="270" height="80" alt="富士通四国インフォテック様"/></a></li>\r\n<li><a href="https://www.photoruction.com/?utm_source=afw&utm_medium=banner&utm_campaign=201903" target="_blank" class="banner" id="default-23"><img src="../img_banner/default/img/2/8/28dba36bb5e98ff9a4514ae00e93844b.png" width="270" height="80" alt="フォトラクション様"/></a></li>\r\n</ul>\r\n<script type="text/javascript">\r\n<!--\r\nvar top_url = \'/\';\r\n//-->\r\n</script>\r\n<script type="text/javascript" src="../common/js/banner_track.js"></script>\r\n\n\n<!-- /#sidebar --></div>\n<!-- /#section --></div>\n<!-- /#content --></div>\n\n<script type="text/javascript">footer(\'../\');</script>\n\n<!-- /#container --></div>\n</body>\n</html>'

ただしこれだと、テキストデータとしてぎっしり詰まったHTMLが返ってきて、何が何やらいまいちわかりません。
そこでBeautifulSoupを利用して、HTMLをパースしてあげましょう。

BeautifulSoupを使う

htmlのパース
soup = BeautifulSoup(res.text, 'html.parser')
soup

こちらの結果を見てみましょう

レスポンス
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">

<html dir="ltr" lang="ja" xml:lang="ja" xmlns="http://www.w3.org/1999/xhtml" xmlns:fb="http://www.facebook.com/2008/fbml" xmlns:og="http://ogp.me/ns#">

---(省略)---

<!--======== 本文 ========-->
<div class="page-title">
<p><img alt="最新10行ニュース" height="20" src="img/icon_new.gif" width="112"/></p>
<h2>「Archi Future 2019」が史上最高の来場者数を<br/>
集めて盛況に開催</h2>
</div>
<p class="page-data">2019.10.28</p>
<p>第12回目となる「Archi Future 2019」が、先週の10月25日(金)に開催された。<br/>
開催当日は、強烈な雨と風のあいにくの天候にも関わらず<span style="font-size:12px;">、</span>来場者数は前回比で5.4%の増加の<br/>
5,509人となり、史上最高となる来場者数を集める盛況な開催となった。<br/>
米国の著名な設計事務所のDiller Scofidio + Renfroによる基調講演や、大手ゼネコンの現場所<br/>
長クラス5人によるパネルデ<span style="font-size:12px;">ィ</span>スカ<span style="font-size:12px;">ッ</span>シ<span style="font-size:12px;">ョ</span>ンは<span style="font-size:12px;">、</span>600席に拡大した会場が満席となり<span style="font-size:12px;">、</span>パネルデ<span style="font-size:12px;">ィ</span><br/>
スカッションは席をさらに100席増設するほどの盛況ぶりだ<span style="font-size:12px;">っ</span>た。講演会・セミナーはどの講座<br/>
もほぼ満席となり<span style="font-size:12px;">、</span>展示会場も大変多くの来場者が訪れ<span style="font-size:12px;">、</span>会場全体が大変活気に満ちた、大盛況<br/>
な開催となった。岡田氏と山梨氏の特別対談1、豊田氏と松島氏の特別対談2をはじめ、どの<br/>
セッシ<span style="font-size:12px;">ョ</span>ンも建築の新しい方向性と明るい未来を感じさせてくれる、充実した内容であった。<br/>
Archi Future 2019のレポートについては、今後、当サイトで紹介する予定だ。<br/>
<br/>
<a href="http://www.archifuture.jp/2019/" target="_blank"><p class="image al_center"><img alt=" 「Archi Future 2019」オフィシャルサイトのトップページ" height="400" src="./img/4/c/4c57dc333a5c9d674ef327289a500800.jpg" width="600"/></p><p class="caption"> 「Archi Future 2019」オフィシャルサイトのトップページ</p></a></p>

---(省略)---

</html>

いい具合にhtmlを解析して表示してくれています。

取りたい情報にありつく

それではいよいよ本題ですね。
今回は10行記事の内容を取得したいので、まずは記事本文がどこにあるかを探しましょう。
書かれている内容と照らし合わせて見つけても構いませんが、Web系ならここはディベロッパーツールを使って探しましょう。

3.png

こんな感じですね。
(うむむ……idもクラスも振られていないなぁ……)

idやクラスが振られている場合は、cssセレクターを利用して指定すれば簡単に取れるのですが、今回は特にそういったものはないので記事が書かれているpタグをすべて取得することにします。

pタグを取得
p_tags = soup.select('p')
p_tags
pタグの取得結果
[<p><img alt="最新10行ニュース" height="20" src="img/icon_new.gif" width="112"/></p>,
 <p class="page-data">2019.10.28</p>,
 <p>第12回目となる「Archi Future 2019」が、先週の10月25日(金)に開催された。<br/>
 開催当日は、強烈な雨と風のあいにくの天候にも関わらず<span style="font-size:12px;">、</span>来場者数は前回比で5.4%の増加の<br/>
 5,509人となり、史上最高となる来場者数を集める盛況な開催となった。<br/>
 米国の著名な設計事務所のDiller Scofidio + Renfroによる基調講演や、大手ゼネコンの現場所<br/>
 長クラス5人によるパネルデ<span style="font-size:12px;">ィ</span>スカ<span style="font-size:12px;">ッ</span>シ<span style="font-size:12px;">ョ</span>ンは<span style="font-size:12px;">、</span>600席に拡大した会場が満席となり<span style="font-size:12px;">、</span>パネルデ<span style="font-size:12px;">ィ</span><br/>
 スカッションは席をさらに100席増設するほどの盛況ぶりだ<span style="font-size:12px;">っ</span>た。講演会・セミナーはどの講座<br/>
 もほぼ満席となり<span style="font-size:12px;">、</span>展示会場も大変多くの来場者が訪れ<span style="font-size:12px;">、</span>会場全体が大変活気に満ちた、大盛況<br/>
 な開催となった。岡田氏と山梨氏の特別対談1、豊田氏と松島氏の特別対談2をはじめ、どの<br/>
 セッシ<span style="font-size:12px;">ョ</span>ンも建築の新しい方向性と明るい未来を感じさせてくれる、充実した内容であった。<br/>
 Archi Future 2019のレポートについては、今後、当サイトで紹介する予定だ。<br/>
 <br/>
 <a href="http://www.archifuture.jp/2019/" target="_blank"><p class="image al_center"><img alt=" 「Archi Future 2019」オフィシャルサイトのトップページ" height="400" src="./img/4/c/4c57dc333a5c9d674ef327289a500800.jpg" width="600"/></p><p class="caption"> 「Archi Future 2019」オフィシャルサイトのトップページ</p></a></p>,
 <p class="image al_center"><img alt=" 「Archi Future 2019」オフィシャルサイトのトップページ" height="400" src="./img/4/c/4c57dc333a5c9d674ef327289a500800.jpg" width="600"/></p>,
 <p class="caption"> 「Archi Future 2019」オフィシャルサイトのトップページ</p>,
 <p class="al_center" id="superbanner"><a class="banner" href="http://www.archifuture.jp/2019/" id="super-14"><img alt="Archi Future 2019" height="90" src="../img_banner/super/img/9/9/99ae81e84701bf687561a0ca026bdef0.png" width="600"/></a></p>]

どうやらpタグの中では2番目(0から数えて)にあるようですので、この中から2番目の要素のテキストを抽出していきます。

記事の取得
article = p_tags[2].get_text()
atricle
記事取得結果
'第12回目となる「Archi Future 2019」が、先週の10月25日(金)に開催された。\r\n開催当日は、強烈な雨と風のあいにくの天候にも関わらず、来場者数は前回比で5.4%の増加の\r\n5,509人となり、史上最高となる来場者数を集める盛況な開催となった。\r\n米国の著名な設計事務所のDiller Scofidio + Renfroによる基調講演や、大手ゼネコンの現場所\r\n長クラス5人によるパネルディスカッションは、600席に拡大した会場が満席となり、パネルディ\r\nスカッションは席をさらに100席増設するほどの盛況ぶりだった。講演会・セミナーはどの講座\r\nもほぼ満席となり、展示会場も大変多くの来場者が訪れ、会場全体が大変活気に満ちた、大盛況\r\nな開催となった。岡田氏と山梨氏の特別対談1、豊田氏と松島氏の特別対談2をはじめ、どの\r\nセッションも建築の新しい方向性と明るい未来を感じさせてくれる、充実した内容であった。\r\nArchi Future 2019のレポートについては、今後、当サイトで紹介する予定だ。\n\n\u3000「Archi Future 2019」オフィシャルサイトのトップページ'

近づいてきましたね。
ということで、不要な改行コードたちは消しちゃいましょう。

記事のテキストのみ抽出
lines = [line.strip() for line in text.splitlines()]  # タグを排して文字だけ取得
ten_lines_news = lines[0:10]  # 不要部分の削除
ten_lines_news
10行ニュースの中身
['第12回目となる「Archi Future 2019」が、先週の10月25日(金)に開催された。',
 '開催当日は、強烈な雨と風のあいにくの天候にも関わらず、来場者数は前回比で5.4%の増加の',
 '5,509人となり、史上最高となる来場者数を集める盛況な開催となった。',
 '米国の著名な設計事務所のDiller Scofidio + Renfroによる基調講演や、大手ゼネコンの現場所',
 '長クラス5人によるパネルディスカッションは、600席に拡大した会場が満席となり、パネルディ',
 'スカッションは席をさらに100席増設するほどの盛況ぶりだった。講演会・セミナーはどの講座',
 'もほぼ満席となり、展示会場も大変多くの来場者が訪れ、会場全体が大変活気に満ちた、大盛況',
 'な開催となった。岡田氏と山梨氏の特別対談1、豊田氏と松島氏の特別対談2をはじめ、どの',
 'セッションも建築の新しい方向性と明るい未来を感じさせてくれる、充実した内容であった。',
 'Archi Future 2019のレポートについては、今後、当サイトで紹介する予定だ。']

うまく取れましたね。
配列の個数が10個ってところが興奮ポイントですね。

最後に、1行のテキストにまとめます。

1つのテキストに
ten_lines_news_text = ""
for line in ten_lines_news:
  ten_lines_news_text += line
ten_lines_news_text

記事の周辺情報も拾っておく

スクレイピングの醍醐味はたくさんの情報を一気にとってくることですよね。
そうなったとき、現状では取得してきた情報を識別することができません。

今回は2段構えとして、記事が投稿された日付と、記事のURLに割り当てられている番号を取得して記事IDとしようと思います。
先ほどpタグを一括取得したときに出てきたデータを見るとわかる通り、日付の部分にはクラスが割り当てられています。
これを利用して今度は日付を取得しておきましょう。

投稿日の取得
date = soup.select('.page-data')[0].string
date
取得結果
'2019.10.28'

あとは記事のidですが、記事ページのURL
"http://www.archifuture-web.jp/headline/457.html"
のhtmlファイルの名前の部分を利用するようにしておきます。
(今回は面倒だから一旦直書きでIDをつけておきましょう)

記事のID
id = 457

処理の関数化

ここまでで作成した処理を一旦関数にしましょう。

  • ページにアクセス
  • htmlのパース
  • pタグを取得
  • 記事の取得
  • 記事のテキストのみ抽出
  • 1つのテキストに

の4つの処理を一つの関数にまとめ、URLを入れたら10行記事のテキストを返すように作成します。

処理の関数化

def get_article(url):
  res = requests(url)
  soup = BeautifulSoup(res.text, html.parser)

  # 記事の取得
  p_tags = soup.select(p)
  article = p_tags[2].get_text()
  lines = [line.strip() for line in text.splitlines()]  # タグを排して文字だけ取得
  ten_lines_news = lines[0:10]  # 不要部分の削除

  # 一つのテキストデータに格納
  ten_lines_news_text = ""
  for line in ten_lines_news:
    ten_lines_news_text += line

  date = soup.select('.page-data')[0].string  # 投稿日時
  id = 457 # 記事のID

  return ten_lines_news_text

これがpythonスクリプトファイル(.py)で実行可能かを確認し、実行できたら以降のステップはpythonスクリプトファイル内に記載していきましょう。

CSVファイルに保存してみる

取得した情報を取得しっぱなしではもったいないので、csvファイルに書き込んでみましょう。
pythonでcsvデータを扱うライブラリはいくつかありますが、今回はpandasを使います。
行と列のデータを扱う時に非常に便利なので、個人的に気に入っているライブラリです。

先に書き込み先のcsvファイルを準備しておきましょう(今回はtxt_data.csvの名前で作成)。
arricles.csvとかの方がしっくりきたな……

txt_data.csv
id,date,text

pandasを利用してファイルの読み書きを行います。

csvへの書き込み

 csv_file = 'csv/txt_data.csv' 
 df = pd.read_csv(csv_file)
 text = value
 results = pd.DataFrame([id, date, text], columns=['id', 'date', 'text'])
 df = pd.concat([df, results])
 df.to_csv(csv_file, index=False)
 print("success writing to %s" % csv_file)

書き込み完了後のcsvデータ
id,date,text
457,2019.10.28,第12回目となる「Archi Future 2019」が、先週の10月25日(金)に開催された。開催当日は、強烈な雨と風のあいにくの天候にも関わらず、来場者数は前回比で5.4%の増加の5,509人となり、史上最高となる来場者数を集める盛況な開催となった。米国の著名な設計事務所のDiller Scofidio + Renfroによる基調講演や、大手ゼネコンの現場所長クラス5人によるパネルディスカッションは、600席に拡大した会場が満席となり、パネルディスカッションは席をさらに100席増設するほどの盛況ぶりだった。講演会・セミナーはどの講座もほぼ満席となり、展示会場も大変多くの来場者が訪れ、会場全体が大変活気に満ちた、大盛況な開催となった。岡田氏と山梨氏の特別対談1、豊田氏と松島氏の特別対談2をはじめ、どのセッションも建築の新しい方向性と明るい未来を感じさせてくれる、充実した内容であった。Archi Future 2019のレポートについては、今後、当サイトで紹介する予定だ。

これで取得した情報をcsvデータとして保存することができました。
次回は、これまでに投稿された記事を全て取りに行って、そのテキストデータを保存する仕組みの作成を解説します。

参考

Qiita: Pythonのスクレイピングで文字だけを抜き出す汎用的な方法

2
12
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
2
12