練習問題 10.3 fold コマンド

プログラミング in OCaml ~関数型プログラミングの基礎からGUI構築まで~のp.215より。
wc コマンドはなんか難しいのでこっちを先に。

UNIX の fold コマンドは,ファイル名の列を引数として,その内容を,長い行を複数の短い 行(デフォルトでは80文字)に分割しながら表示します。これを OCaml で実装し,実行可能 ファイルを作成しなさい。オプションとしては,行の長さを整数で指定する --width を実装 しなさい。

 let version = "0.1"
 let filenames = ref []
 let width = ref 80
 
 let spec = [("--width",
              Arg.Int (fun n -> width := n),
              "Set line width");
             ("--version",
               Arg.Unit (fun () -> Printf.printf "fold in OCaml ver.%s\n" version),
              "Display version")]
 
 
 let rec fold_line n str =
   let len = String.length str in
   if len > n then
     ( print_endline (String.sub str 0 n);
       fold_line n (String.sub str n (len - n)))
   else
     print_endline str
 
 let rec each_line ic =
   fold_line !width (input_line ic);
   each_line ic
 
 let fold_file filename =
   let infile = open_in filename in
   try
     each_line infile
   with
     End_of_file -> close_in infile
 
 
 let () =
   Arg.parse spec
             (fun s -> filenames := s :: !filenames)
             "Usage: fold [--width width] [--help] [--version] filename ...";
   List.iter fold_file (List.rev !filenames)
 ^o^ >ocamlc -o fold.exe fold.ml
 
 ^o^ >fold --width 40 fold.ml
 let version = "0.1"
 let filenames = ref []
 let width = ref 80
 
 let spec = [("--width",
              Arg.Int (fun n -> width :=
 n),
              "Set line width");
             ("--version",
               Arg.Unit (fun () -> Printf
 .printf "fold in OCaml ver.%s\n" version
 ),
              "Display version")]
 
 
 let rec fold_line n str =
   let len = String.length str in
   if len > n then
     ( print_endline (String.sub str 0 n)
 ;
 
 (以下略)