(** Module for handling phonological features and segments *) (* module Feature = struct *) (** Type representing a phonological feature value *) type feature_value = Plus | Minus | Zero (** Type representing a phonological feature *) type feature = | Syllabic | Sonorant | Consonantal | Continuant | DelayedRelease | Lateral | Nasal | Strident | Voiced | SpreadGlottis | ConstrictedGlottis | Anterior | Coronal | Distributed | Labial | High | Low | Back | Rounded | Velaric | Tense | Long | HighTone | HighReg (*high registry?*) type feature_spec = feature * feature_value (** Type representing a feature specification as a (value, feature) pair *) type segment = feature_spec list (** Convert a string feature value to the feature_value type *) let value_of_string = function | "+" -> Plus | "-" -> Minus | "0" -> Zero | s -> failwith (Printf.sprintf "Invalid feature value: %s" s) let string_of_value = function Plus -> "+" | Minus -> "-" | Zero -> "0" let feature_of_string = function | "syl" -> Syllabic | "son" -> Sonorant | "cons" -> Consonantal | "cont" -> Continuant | "delrel" -> DelayedRelease | "lat" -> Lateral | "nas" -> Nasal | "strid" -> Strident | "voi" -> Voiced | "sg" -> SpreadGlottis | "cg" -> ConstrictedGlottis | "ant" -> Anterior | "cor" -> Coronal | "distr" -> Distributed | "lab" -> Labial | "hi" -> High | "lo" -> Low | "back" -> Back | "round" -> Rounded | "velaric" -> Velaric | "tense" -> Tense | "long" -> Long | "hitone" -> HighTone | "hireg" -> HighReg | _ -> failwith "not a valid feature" let string_of_feature = function | Syllabic -> "syl" | Sonorant -> "son" | Consonantal -> "cons" | Continuant -> "cont" | DelayedRelease -> "delrel" | Lateral -> "lat" | Nasal -> "nas" | Strident -> "strid" | Voiced -> "voi" | SpreadGlottis -> "sg" | ConstrictedGlottis -> "cg" | Anterior -> "ant" | Coronal -> "cor" | Distributed -> "distr" | Labial -> "lab" | High -> "hi" | Low -> "lo" | Back -> "back" | Rounded -> "round" | Velaric -> "velaric" | Tense -> "tense" | Long -> "long" | HighTone -> "hitone" | HighReg -> "hireg" let string_of_segment segment = Base.List.fold segment ~init:"" ~f:(fun acc (feature, value) -> let item = Printf.sprintf "%s:%s" (string_of_feature feature) (string_of_value value) in Printf.sprintf "%s\n%s" acc item) (** Check if a segment has a specific feature with a given value *) let has_feature (value, feature_name) segment = List.exists (fun (v, f) -> v = value && f = feature_name) segment (** Create a feature test function for use in the decision tree *) let test feature_spec segment = has_feature feature_spec segment (* end *)