Skip to content

Instantly share code, notes, and snippets.

@akimacho
Last active August 29, 2015 14:16
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save akimacho/2df2698305237b6bd277 to your computer and use it in GitHub Desktop.
Save akimacho/2df2698305237b6bd277 to your computer and use it in GitHub Desktop.
メトロネットワーク最短路問題その1
(* --- 問題8.5 --- *)
(* 駅名の情報を表すデータ型 *)
type ekimei_t = {
kanji : string; (* 漢字の駅名 *)
kana : string; (* ひらがなの駅名 *)
romaji : string; (* ローマ字の駅名 *)
shozoku : string; (* その駅が所属する線路名 *)
}
(* --- 問題8.6 --- *)
(* 目的 : ekimei_t型のデータを受け取ったら,「路線名,駅名(かな)」の形式の文字列を返す *)
(* hyoji : ekimei_t -> string *)
let hyoji e = match e with
{kanji = kj; kana = kn; romaji = rm; shozoku = sz}
-> sz ^ "," ^ kj ^ "(" ^ kn ^ ")"
(* --- 問題8.7 --- *)
(* 駅と駅の接続情報を表すデータ型 *)
type ekikan_t = {
(* 以下の文字列はいずれも漢字 *)
kiten : string; (* 起点の駅名 *)
shuhten : string; (* 終点の駅名 *)
keiyu : string; (* 経由する路線名 *)
kyori : float; (* 上の2駅間の距離 *)
jikan : int; (* 所要時間 *)
}
(* --- 問題9.9 --- *)
(* メトロネットワークのすべての駅のデータ *)
(* --- 問題9.10 --- *)
(* メトロネットワークのすべての駅間のデータ *)
(* http://pllab.is.ocha.ac.jp/~asai/book-data/metro.ml を参照 *)
(* --- 問題10.10 --- *)
(* ekimei_t listは *)
(* [] - 空リスト,あるいは *)
(* first :: rest - 最初の要素がfirstで残りの要素がrest *)
(* firstはekimei_t,restはekimei_t list(自己参照のケース) *)
(* という形 *)
(* 目的 : ローマ字の駅名と駅名リストを受け取ったら,その駅名の漢字表記を文字列で返す *)
(* romaji_to_kanji : string -> ekimei_t list -> string *)
let rec romaji_to_kanji e lst = match lst with
[] -> ""
| { kanji = kj; kana = kn; romaji = rm; shozoku = sz } :: rest ->
if e = rm
then kj
else romaji_to_kanji e rest
(* テスト *)
let test1 = romaji_to_kanji "hoge" global_ekimei_list = ""
let test2 = romaji_to_kanji "otemachi" global_ekimei_list = "大手町"
let test3 = romaji_to_kanji "myogadani" global_ekimei_list = "茗荷谷"
let test4 = romaji_to_kanji "ochanomizu" global_ekimei_list = "御茶ノ水"
# #use "metro.ml" ;;
# #use "romaji_to_kanji.ml" ;;
val romaji_to_kanji : string -> ekimei_t list -> string = <fun>
val test1 : bool = true
val test2 : bool = true
val test3 : bool = true
val test4 : bool = true
(* --- 問題10.11 --- *)
(* 目的 : 漢字の駅名を2つと駅間リストを受け取ったら,駅間リストの中からその2駅間の距離を返す *)
(* get_ekikan_kyori : string -> string -> ekikan_t list -> float *)
let rec get_ekikan_kyori e1 e2 lst = match lst with
[] -> infinity
| { kiten = kt; shuten = st; keiyu = ky; kyori = kr; jikan = jk } :: rest ->
if ( ( kt = e1 && st = e2 ) || ( kt = e2 && st = e1 ) )
then kr
else get_ekikan_kyori e1 e2 rest
(* テスト *)
let test1 = get_ekikan_kyori "hoge" "foo" global_ekikan_list = infinity
let test2 = get_ekikan_kyori "茗荷谷" "新大塚" global_ekikan_list = 1.2
let test3 = get_ekikan_kyori "新大塚" "茗荷谷" global_ekikan_list = 1.2
let test4 = get_ekikan_kyori "四ツ谷" "永田町" global_ekikan_list = 1.3
let test5 = get_ekikan_kyori "築地" "東銀座" global_ekikan_list = 0.6
# #use "metro.ml" ;;
# #use "get_ekikan_kyori.ml" ;;
val get_ekikan_kyori : string -> string -> ekikan_t list -> float = <fun>
val test1 : bool = true
val test2 : bool = true
val test3 : bool = true
val test4 : bool = true
val test5 : bool = true
(* --- 問題10.12 --- *)
(* 目的 : 駅名(ローマ字)を2つ受け取ったら,その間の距離を表示する *)
(* kyori_wo_hyoji : string -> string -> ekimei_t list -> ekikan_t list -> string *)
let rec kyori_wo_hyoji e1 e2 mlst klst = (
(* ek1にe1の漢字名,ek2にe2の漢字名を代入 *)
let (ek1, ek2) = ( ( romaji_to_kanji e1 mlst ), ( romaji_to_kanji e2 mlst )) in (
if ( ek1 = "" )
then e1 ^ "という駅は存在しません"
else if ( ek2 = "" )
then e2 ^ "という駅は存在しません"
else (
let rslt = ( get_ekikan_kyori ek1 ek2 klst ) in (
if ( rslt = infinity )
then ek1 ^ "駅と" ^ ek2 ^ "駅はつながっていません"
else ek1 ^ "駅と" ^ ek2 ^ "駅までは" ^ (string_of_float rslt) ^ "kmです"
)
)
)
)
(* テスト *)
let test1 = kyori_wo_hyoji "shinotsuka" "myogadani" global_ekimei_list global_ekikan_list
= "新大塚駅と茗荷谷駅までは1.2kmです"
let test2 = kyori_wo_hyoji "myogadani" "shinotsuka" global_ekimei_list global_ekikan_list
= "茗荷谷駅と新大塚駅までは1.2kmです"
let test3 = kyori_wo_hyoji "myogadani" "tsukiji" global_ekimei_list global_ekikan_list
= "茗荷谷駅と築地駅はつながっていません"
let test4 = kyori_wo_hyoji "tsukiji" "myogadani" global_ekimei_list global_ekikan_list
= "築地駅と茗荷谷駅はつながっていません"
let test5 = kyori_wo_hyoji "hoge" "myogadani" global_ekimei_list global_ekikan_list
= "hogeという駅は存在しません"
let test6 = kyori_wo_hyoji "myogadani" "hoge" global_ekimei_list global_ekikan_list
= "hogeという駅は存在しません"
# #use "romaji_to_kanji.ml" ;;
# #use "get_ekikan_kyori.ml" ;;
# #use "kyori_wo_hyoji.ml" ;;
val kyori_wo_hyoji :
string -> string -> ekimei_t list -> ekikan_t list -> string = <fun>
val test1 : bool = true
val test2 : bool = true
val test3 : bool = true
val test4 : bool = true
val test5 : bool = true
val test6 : bool = true
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment