txqz memo

はてなキーワードクローラ

前から (半ばネタで) 作る作る言ってたはてなキーワードクローラを実際に作った。ぶっこぬきでバソコン蛾物故割れたとならないために、ページを取得する毎に8192ミリ秒おいて、UAをFirefoxライクなものにしてみた。FirefoxじゃないのにFirefoxって名乗るのはFirefoxの名誉を損ねるので、本当はあんまりやらないほうが良い。ていうかごめんなさい。ここは Hatena Keyword Crawler 2.0 - ILoveNaoyaMix とかにするべきでしたね(ぇ<

はてなキーワードは10月6日時点で14万近くあり、1日弱で取得できた。新着と更新されたキーワードはRSSで補足しているので、これで語彙のほうは万全? あとはシソーラス辞書をどうするかだなー。趣旨からすると、セクターから企業名とその通称を引ければ良いかなぁ。あとベクトル空間モデルの勉強を進めて。

作ったファイルは KeywordList と FuriganaList、あと実行用mainクラス。

import java.io.IOException;
import java.net.MalformedURLException;
import java.net.URL;
import java.util.HashSet;
import java.util.Set;

import net.txqz.html.parse.SimpleParser;

import org.apache.oro.text.perl.Perl5Util;

public class KeywordList{
  private String body;
  private String url;
  private int of = 0;
  public KeywordList(String url){
    this.url = "http://d.hatena.ne.jp"+url+"&amp;of=";
  }
  public boolean hasNext() throws MalformedURLException, IOException{
    getHTML();
    Perl5Util pu = new Perl5Util();
    String test = "#class=\"keyword\"#";
    return pu.match(test, body);
  }
  public Set<String> next() throws InterruptedException {
    Thread.sleep(8192);
    Perl5Util pu = new Perl5Util();
    Set<String> wordList = new HashSet<String>();
    String test = "#<tbody>(.+?)</tbody>#";
    String listStr = "";
    if(pu.match(test, body)) listStr = pu.group(1).replaceAll("</tr>","");
    String[] lists = listStr.split("<tr class=\"[a-z]+\">");
    for(String each : lists){
      String test2 = "#<td><a href=\"/keyword/[^\"]+\" class=\"keyword\">(.+?)</a></td>#";
      if(pu.match(test2, each)) wordList.add(pu.group(1));
    }
    of += 20;
    return wordList;
  }
  public void getHTML() throws MalformedURLException, IOException{
    String thisURL = url+of;
    System.out.print((of/20+1)+"ページ目("+thisURL+")取得中……");
    body = SimpleParser.getHTML(new URL(thisURL));
  }
}</code></pre>
<pre><code class="java">import java.io.IOException;
import java.net.MalformedURLException;
import java.net.URL;
import java.util.HashMap;
import java.util.Map;

import net.txqz.html.parse.SimpleParser;

import org.apache.oro.text.perl.Perl5Util;

public class FuriganaList{
  private String body;
  public FuriganaList(String url) throws MalformedURLException, IOException {
    body = SimpleParser.getHTML(new URL(url));
  }
  public Map<String,String> getURLs(){
    Perl5Util pu = new Perl5Util();
    Map<String,String> result = new HashMap<String,String>();
    String test = "";
    String pt1 = "#<table class=\"table-furigana\">(.+?)</table>#";
    if(pu.match(pt1, body)) test = (pu.group(1));
    test = test.replaceAll("</?tr>","").replaceAll("&nbsp;","").replaceAll("</td>","");
    String[] words = test.split("\\s*<td( class=\"main-word\")?>");
    for(String word : words){
      String pt2 = "#<a href=\"(.+?)\">(.+?)</a>#";
      if(pu.match(pt2, word)) result.put(pu.group(2), pu.group(1));
    }
    return result;
  }
}