Pythonクックブック(2章)
2章はファイル操作について
特定の行を読む(linecacheモジュール)
linecacheモジュールを使うと、テキストファイルの各行にランダムにアクセスできる。
linecache.getline(filename, line_number)はline_number行目のデータを返す。
もし、line_number行目がなければ、''を返す。
[kobakoba0723@fedora13-intel64 ~]$ tail -n 1 /etc/passwd kobakoba0723:x:501:501::/home/kobakoba0723:/bin/bash [kobakoba0723@fedora13-intel64 ~]$ wc -l /etc/passwd 39 /etc/passwd [kobakoba0723@fedora13-intel64 ~]$ python Python 2.6.4 (r264:75706, Apr 1 2010, 02:55:51) [GCC 4.4.3 20100226 (Red Hat 4.4.3-8)] on linux2 Type "help", "copyright", "credits" or "license" for more information. >>> import sys >>> import linecache >>> sys.stdout.write(linecache.getline('/etc/passwd', 39)) kobakoba0723:x:501:501::/home/kobakoba0723:/bin/bash >>> >>> for line_num, line_data in enumerate(open('/etc/passwd', 'rU')): ... if line_num == 38: ... sys.stdout.write(line_data) ... break ... else: ... sys.stdout.write('') ... kobakoba0723:x:501:501::/home/kobakoba0723:/bin/bash >>> >>> sys.stdout.write(linecache.getline('/etc/passwd', 40)) >>> for line_num, line_data in enumerate(open('/etc/passwd', 'rU')): ... if line_num == 39: ... sys.stdout.write(line_data) ... break ... else: ... sys.stdout.write('') ... >>>
ファイルの行数を数える(enumerate, timeit)
enumerate(sequence)を使うと、カウント(0スタート)とデータのタプルを返すので、
自分でカウンターの操作をしなくてもよい。
>>> print len(open('/etc/passwd', 'rU').readlines()) 39 >>> count = -1 >>> for count, data in enumerate(open('/etc/passwd', 'rU')): ... pass ... >>> count += 1 >>> print count 39 >>>
timeitモジュールを使うと、実行時間を手軽に計測することが出来る。
クックブックではpopen()を使っていたが、どうも2.6ではpopenが廃止され、subporcessを使うことになっているそうな。
シェルプロセスを新しく起こすと遅いとは思ってたけど、2桁近く遅いとは。。。
>>> import timeit >>> import shlex, subprocess >>> def linecount_process(): ... return subprocess.Popen(["wc -l /etc/passwd"], shell=True, stdout=subprocess.PIPE).stdout.read().split()[0] ... >>> def linecount_len(): ... return len(open("/etc/passwd", "rU").readlines()) ... >>> def linecount_enumerate(): ... count = -1 ... for count, data in enumerate(open("/etc/passwd", "rU")): ... pass ... return count + 1 ... >>> >>> linecount_process() '39' >>> linecount_len() 39 >>> linecount_enumerate() 39 >>> >>> timeit.Timer("linecount_process()", "from __main__ import linecount_process").timeit(number=10) 0.10188198089599609 >>> timeit.Timer("linecount_len()", "from __main__ import linecount_len").timeit(number=10) 0.00042796134948730469 >>> timeit.Timer("linecount_enumerate()", "from __main__ import linecount_enumerate").timeit(number=10) 0.00047612190246582031 >>>
正規表現モジュール(re)
以下の2つは同じ結果を返す。
その場でパターンを指定するか、あらかじめコンパイルしたパターンを使うか、が違うみたい。
なんでわざわざ2種類の方法があるのかなぁと思ってたけど、複数回使う場合を考えてのことらしい。
re_object=re.compile(pattern) re_object.finditer(string)
re.finditer(pattern, string)
その他
入門GNU Emacsを読み終わったけど、CEDETが動かない理由は依然としてよくわからない。
Emacs Lispもさらっと眺めてみたけど、よくわからない状態。
python.elじゃなくて、python-mode.elを使ってるのが関係してるのかな。hookがうまく動かないとか*1。
Cのソースでサンプル通りやってうまくいくか試してみようかなぁ。
- 作者: Alex Martelli,Anna Martelli Ravenscroft,David Ascher,鴨澤眞夫,當山仁健,吉田聡,吉宗貞紀
- 出版社/メーカー: オライリー・ジャパン
- 発売日: 2007/06/26
- メディア: 大型本
- 購入: 11人 クリック: 423回
- この商品を含むブログ (85件) を見る
*1:ってそんなことはないんだろうな、たくさんの人が使ってるメジャーモードだし。