Pico Tech - Python Code For Amedas List

Radiation Detection / English Documents ... Francais ... 日本語ページインデックス / Survey Links ... 掲示板 / 放射線量グラフの読み方

アメダス番号、カタカナ名、漢字名、ローマ字のcsvリストを作るPythonスクリプト

鮫川村周辺のモニタリングポストや気象観測点の情報マップを作った際に、利用していたアメダスのデータベースが古いのに気づき、
最新のリストは、あちこち探したのですが、csv形式やテキスト形式など、直ぐ使えるものは無かったので、「デジタル台風」サイトのHTMLリストからcsvファイルを作りました。

このサイトは、アメダスのグラフ表示もそうですが、非常に助かります。

http://agora.ex.nii.ac.jp/digital-typhoon/amedas/search/index.html.ja

こちらの方が作っているようで、電力統計とか原発付近の風向風速マップ、そして雨量マップを含め、興味深いプロジェクトを沢山やっている様です。

http://agora.ex.nii.ac.jp/~kitamoto/index.html.ja

 
その時に使ったコードをここに置いておきます。

可読性は無視して、短く書いているので、Pythonに慣れてないと分かり難いかもしれないですが、
(ありがちな)正規表現を使ったやり方でなく、単純な文字列検索と文字列の分割(split)に含まれる文字列の検索と削除を使って処理しています。
日本語版と英語版の両方のリストを引っ張ってきて、それを合成し、ズレとかがないか確認した後、ダブっているアメダス番号を取り除いて
ファイルを保存し、次回からはそのファイルを使いまわしますし、変数にリストを保存しておいて、あればそっちを使います。

まず、HTMLを取ってきて、delim で指定された文字列でリストに分割し、その最初の部分は要らないので残りを使う、というのが、

urllib2.urlopen(url % '.ja').read().split(delim)[1:] の部分です。

次に、その残りの各行の、'</'から後をとった文字列( s[:s.find('</')] )で、「/" title="」 と 「">」をカンマに置き換えて
日本語版を作っているのが先ほどの部分を含む行の左側。
 [ s[:s.find('</')].replace('/" title="',',').replace('">',',') .... ]

英語版も同じ様な感じですが、英語名だけで、フィールドが一つ少ないので、replace が少なくなっています。

後は、zip() で日本語版と英語版をくっ付けて、その各行を(同時にカンマを入れて)文字列に変換し、
各行の最初のアメダス番号が2番目のものと一致しているのを確認し、一致してなかったら、
一行づつ確かめながら日本語版と英語版の張り合わせを行います。(この部分はテストしてません)

で、最後に重複したアメダス番号を取り除いて完成。

普通は、HTMLパーサーとかを通して、要素を抽出し、それをくっ付けたりするのですが、私は、こういう原始的なやり方が好きで、
HTML処理は大抵この方法です。


 
ame_list = []
def get_amelist(force = 0):
    global ame_list
    # アメダス番号と観測点名のリストが既に読み込まれていれば、それを返し、
    # 無ければ、デジタル台風プロジェクトのサイトから、アメダスのリストの画面を取ってきて、
    # アメダス番号、カタカナ名、漢字名、ローマ字の並んだcsvリストを作ります。
    import urllib2
    if force or not ame_list:
        fn = 'ja/met/ame_list.csv'
        if force or not os.path.exists(fn):
            url = 'http://agora.ex.nii.ac.jp/digital-typhoon/amedas/search/index.html%s'
            delim = '<li><nobr><a href="/digital-typhoon/amedas/'
            j = [ s[:s.find('</')].replace('/" title="',',').replace('">',',') for s in urllib2.urlopen(url % '.ja').read().split(delim)[1:] ]
            e = [ s[:s.find('</')].replace('/">',',')  for s in urllib2.urlopen(url % '.en').read().split(delim)[1:] ]
            je = [ ','.join(a) for a in zip(j,e) ]
            check = [ s for s in je if not s[:5] in s[7:] ]
            if check:
                je =  [ji + ',' + [ s for s in e if s[:5] == ji[:5] ][0]   for ji in j]
            ame_list = [ s.replace(','+s[:5],'') for s in je] # if not s[:5] in ('40905', '14161', '14162','14913','41915')]
            file(fn,'w').write('\n'.join(ame_list))
        else: #
            ame_list = file(fn).readlines()
    return ame_list
def search_amedas(s): # 検索したい文字列の(前や後ろや両方に)コンマを付けたものを与えることで、 # 検索するフィールドを特定したり、正確な検索が出来るようになります。 # 曖昧な検索をして、複数が合致すると、最初のものを返します。 global ame_list l = [v for v in get_amelist() if s in v] return l[0] if l else ''
#========== 以下、強化版検索
# アメダス観測所で http://washitake.com/weather/amedas/obs_stations.md # このファイルを取ってきて、http://washitake.com/weather/amedas/ame_master.xlsx # csvに変換したものを使用。 http://pico.dreamhosters.com/raddata/ja/met/ame_master.csv def s_master(): # Create the list of 'amedas-code,block-code' fn = 'ja/met/ame_master.csv' fna = 'ja/met/s_amedas.csv' l = file(fn).readlines() l = [a[:6]+a[-7:-2] for a in l if a[-8:-5] == ',47'] file(fna,'w').write('\n'.join(l))
# 名称が変わった地点。 exc_d = { '新町':',小鎚,', '奥日光':',中宮祠,', '守門':',入広瀬,', '南大東(南大東島)':',南大東,', }
# この5件は、気象庁の過去データ検索にも入っていないか、アメダス情報も # 無かったりするので、気象庁がリストに追加するのを待つ。 exc_n = { '大島泉津': '44176,大島泉津,オオシマセンヅ,Oshimasenzu', '大島差木地': '44186,大島差木地,オオシマサシキジ,Oshimasashikiji', '剣山': '0,剣山,ツルギサン,Tsurugisan', '伊吹山': '0,伊吹山,イブキヤマ,Ibukiyama', '昭和': '0,昭和,ショウワ,SHOWA' }
s_amedas = [] def search_amedas_x(s,block=''): # 過去情報検索のブロック番号を与えたり、他のリストも活用して、 # 検索漏れを極力少なくした強化版。 global s_amedas, ame_list global ame_list if not ame_list: get_amelist() if block and block.startswith('47'): if not s_amedas: fna = 'ja/met/s_amedas.csv' s_amedas = file(fna).readlines() l = [v for v in s_amedas if block == v[-6:-1]] if l : ss = l[0][:5] l = [v for v in ame_list if ss == v[:5]] if l: return l[0].strip('\n') ss = ",%s," % s l = [v for v in ame_list if ss in v] if l: return l[0].strip('\n') ss = "/ %s," % s l = [v for v in ame_list if ss in v] if l: ll = l[0].split(',') ll[-1] = ll[-1].split(' / ')[1] l[0] = ','.join(ll) return l[0].strip('\n') ss = ",%s /" % s l = [v for v in ame_list if ss in v] if l: ll = l[0].split(',') ll[-1] = ll[-1].split(' / ')[1] l[0] = ','.join(ll) return l[0].strip('\n') if exc_d.has_key(s): ss = exc_d[s] l = [v for v in ame_list if ss in v] if l: return l[0].strip('\n') else: print ss.decode('utf-8') print 'failed' if exc_n.has_key(s): return exc_n[s] print s.decode('utf-8'),block, 'Not found ... 2' return ''



関連するページ


幾つかの地点の線量の推移と気象データ


Radiation Detection / English Documents ... Francais ... 日本語ページインデックス / Survey Links ... 掲示板

Last modified : Fri Jul 18 20:25:06 2014 Maintained by nkom AT pico.dreamhosters.com