関数的な写像

key_t のキーから型 itm_t の要素へマップを表わすのに、写像が必要だと考えます。 次のコードは本質的に、ATSLIB/libats にて平衡木で実装された写像に対する生成と操作のインターフェイスを作っています:

local // typedef key = key_t and itm = itm_t // staload FM = "libats/ML/SATS/funmap.sats" implement $FM.compare_key_key<key>(x, y) = compare(x, y) // in (* in-of-local *) #include "libats/ML/HATS/myfunmap.hats" end // end of [local]

関数的な写像を用いたプログラミングを単純化するためのラッパーである HATS ファイルは オンライン から入手できます。 シンボル compare をオーバーロードする型 key_tの値に対する比較関数があることを、ここでは仮定していることに注意してください。 存在しない場合、そのような関数を実装する必要があります。

key_tstringitm_tint であると仮定します。 コードの次の行では、要素を含まない (整数の) 関数的な写像を生成しています:

val mymap = myfunmap_nil()

次の数行では、キー/要素のペアを mymap に挿入しています:

// var mymap = mymap // val-~None_vt() = mymap.insert("a", 0) val-~Some_vt(0) = mymap.insert("a", 1) // val-~None_vt() = mymap.insert("b", 1) val-~Some_vt(1) = mymap.insert("b", 2) // val-~None_vt() = mymap.insert("c", 2) val-~Some_vt(2) = mymap.insert("c", 3) //

ドット表記 .insert は関数 myfunmap_insert によってオーバーロードされています。 上記コードの最初の行は謎めいて見えるかもしれません: その唯一の目的は、myfunmap_insert への最初の引数として渡される左辺値を生成することです。 キーと要素が与えられたとき、mymap.insert はキー/要素ペアを mymap に挿入します。 もしそのキーが挿入前の写像 mymap の定義域であるなら、そのキーに関連する元の要素が返ります。 そうでない場合、なにも要素は返りません。 予想されることですが、この時点で mymap のサイズは 3 になります:

val () = assertloc (mymap.size() = 3)

ドット表記 .size は関数 myfunmap_size でオーバーロードされています。 この関数は与えられた写像に保管されたキー/要素のペアの数を返します。 デバッグのために、与えられた写像中のキー/要素ペアを印字したいと思うかもしれません:

// val () = fprintln! (stdout_ref, "mymap = ", mymap) //

このとき、シンボル fprintfprint_mymap でオーバーロードされています。 次の2行のコードは、与えられたキーで写像を検索する方法を示しています:

val-~None_vt() = mymap.search("") val-~Some_vt(1) = mymap.search("a")

The dot-symbol .search is overloaded with a function of the name myfunmap_search, which returns the item associated with a given key if it is found. The next few lines of code remove some key/item pairs from mymap:

// val-true = mymap.remove("a") val-false = mymap.remove("a") // val-~Some_vt(2) = mymap.takeout("b") val-~Some_vt(3) = mymap.takeout("c") //

ドット表記 .remove は、与えらえれたキーに対応するキー/要素ペアを削除を表わす関数 myfunmap_remove でオーバーロードされています。 もし、キー/要素ペアが削除された場合、この関数は true を返します。 そうでない場合、操作を行なった写像には与えられたキーに対応するキー/要素ペアが見つからなかったことを表わす false を返します。 ドット表記 .takeout は関数 myfunmap_takeout でオーバーロードされています。 この関数は、削除した要素を返す点を除いて、myfunmap_remove と同じです。

一般的な各種の写像操作は libats/ML/HATS/myfunmap.hats に見つかります。 これらの操作に割り当てられた型を見れば、それらをどのように呼び出すべきなのか理解するのは難しくないでしょう。 この章で紹介したコード全体は オンライン から入手できます。