Python School 2.0.0 documentation

標準モジュール csv を使う

«  ファイルを読み込む   ::   Contents   ::   ユニコード文字列を考慮する  »

標準モジュール csv を使う

前の章のように自前で実装すると次の二点への対応が難しくなります。

標準 csv モジュールを使うとこうした問題点を回避できます。

ステップバイステップの使い方は、とりあえずこれを読んでください。

csv モジュール

csv モジュールを使って、 ファイルを読み込む と同様の処理を実装しましょう。 実行結果は一緒になりますね。

#!/usr/bin/env python
# -*- coding: utf-8 -*-

"""Parse daily Tokyo stock prices.
"""

import argparse
import csv  # import standard "csv" module
import logging


def parse_args():
    """Parse arguments and set up logging verbosity.

    :rtype: parsed arguments as Namespace object.
    """
    parser = argparse.ArgumentParser()
    parser.add_argument("-f", "--file", dest="filename",
                        help="setting file", metavar="FILE")
    parser.add_argument("-o", "--output", dest="output",
                        help="output file", metavar="FILE")
    parser.add_argument("-n", "--dryrun", dest="dryrun",
                        help="dry run", default=False, action="store_true")
    parser.add_argument("-v", "--verbose", dest="verbose", default=False,
                        action="store_true", help="verbose mode")
    parser.add_argument("-q", "--quiet", dest="quiet", default=False,
                        action="store_true", help="quiet mode")
    # Add this line from boilerplate.
    parser.add_argument("filename", nargs=1, help="CSV file path")

    args = parser.parse_args()

    if args.verbose:
        logging.basicConfig(level=logging.DEBUG)
    elif not args.quiet:
        logging.basicConfig(level=logging.INFO)

    return args


def process(args):
    """Parse daily Tokyo stock prices, and calculate up/down.
    """
    with open(args.filename[0]) as fp:
        reader = csv.reader(fp)  # Instantiate CSV reader with file pointer.
        for t in reader:
            # Assign each field on individual variables.
            day = t[0]
            price_begin = float(t[1])
            price_max = float(t[2])
            price_min = float(t[3])
            price_end = float(t[4])
            # Calculate the differenciate of the day.
            diff = price_end - price_begin
            if diff > 0:
                message = 'up'
            elif diff < 0:
                message = 'down'
            else:
                message = 'same'
            # Write out day, up/down/same, and diff.
            print('{}\t{:5}\t{}'.format(day, message, round(diff, 2)))


def main():
    args = parse_args()
    process(args)


def test():
    pass

if __name__ == '__main__':
    main()

# vim: set et ts=4 sw=4 cindent fileencoding=utf-8 :

このファイルを csv-2.py とすると、差分は以下の通りです。

@@ -5,6 +5,7 @@
 """

 import argparse
+import csv  # import standard "csv" module
 import logging


@@ -41,9 +42,8 @@
     """Parse daily Tokyo stock prices, and calculate up/down.
     """
     with open(args.filename[0]) as fp:
-        for line in fp:
-            l = line.rstrip('\r\n')
-            t = l.split(',')
+        reader = csv.reader(fp)  # Instantiate CSV reader with file pointer.
+        for t in reader:
             # Assign each field on individual variables.
             day = t[0]
             price_begin = float(t[1])

宿題

csv モジュールの reader() 関数は dialectdelimiter, quotechar という引数を解釈します。 これらを切り替えることで、エスケープ文字や区切り文字を変更できます。

  • 公式ドキュメントのコード例に目を通し、空白区切りやコロン区切りのデータを扱っている部分を確認してください。
  • コマンドラインのオプションを解釈し、区切り文字をオプション引数で与えられるようにしてください。

«  ファイルを読み込む   ::   Contents   ::   ユニコード文字列を考慮する  »