Last active
October 25, 2015 03:10
-
-
Save Nnwww/c0ef3edcb271b606f760 to your computer and use it in GitHub Desktop.
某課題のOCaml実装
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
open Core.Std;; | |
type car_query = | |
| And of car_query * car_query | |
| Or of car_query * car_query | |
| Term of string * string | |
let cons_exn arg = | |
let cons_term_exn item = | |
match String.split item '=' with | |
| tag :: param :: [] -> Term (tag, param) | |
| _ -> invalid_arg "format is 'tag=param'!" | |
in | |
let rec loop prev = function | |
| [] -> prev | |
| "or" :: r :: tl -> loop (Or (prev, cons_term_exn r)) tl | |
| "and" :: r :: tl -> loop (And (prev, cons_term_exn r)) tl | |
| _ :: _ -> | |
let () = Printf.printf | |
"error:Maybe you mistyped the number of arg, I'll return a result so far..." | |
in | |
prev | |
in | |
match arg with | |
| [] -> invalid_arg "there is no argment" | |
| hd :: tl -> loop (cons_term_exn hd) tl | |
let make_table size record_list = | |
let table = String.Table.create () ~size:size in | |
List.iter record_list (fun (key, data) -> Hashtbl.set table ~key ~data); | |
table | |
let tag_to_idx = make_table 7 [("buying", 0); ("maint", 1); ("doors", 2); ("persons", 3); ("luggage", 4); ("safety", 5); ("eval", 6)] | |
let match_query_exn query record = | |
let rec loop = function | |
| And (st, nd) -> loop st && loop nd | |
| Or (st, nd) -> loop st || loop nd | |
| Term (tag, param) -> | |
let idx = Hashtbl.find_exn tag_to_idx tag in | |
(List.nth_exn record idx) = param | |
in | |
loop query | |
let () = | |
let csv = In_channel.create "car.csv" in | |
let (_ :: query_src) = Array.to_list Sys.argv in | |
let rate_table = make_table 4 [("unacc", 0); ("acc", 0); ("good", 0); ("vgood", 0)] in | |
let delim = String.split ~on:',' in | |
let eval = match_query_exn (cons_exn query_src) in | |
let update record = Hashtbl.change rate_table (List.nth_exn record 6) | |
(function Some count -> Some (count + 1) | None -> Some 0) | |
in | |
let update_if_match record = if eval record then update record in | |
In_channel.iter_lines csv (fun line -> delim line |> update_if_match); | |
Hashtbl.iter rate_table (fun ~key ~data -> Printf.printf "%s = %d, " key data); |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment