Все это начинается с простой идеи: как написать строку в формате Python в ocaml.
питонцы могут инициализировать строку как:
str = "this var: %s" % this_var
str2 = "this: %s; that: %s" % (this_var, that_var)
но форматированный строковый код ocaml выглядит следующим образом:
let str = Printf.sprintf "this var: %s" this_var
let str2 = Printf.sprintf "this: %s; that: %s" this_var that_var
Я считал, что могу сделать что-то, чтобы код формирования строки ocaml был похож на Python. Сначала я определил функцию, как показано ниже:
let (%) s x = Printf.sprintf s x
тогда я могу написать прямо как:
let str = "this: %s" % "sth"
но простая функция не может обрабатывать более сложные ситуации как две или более переменных. поэтому я хотел написать небольшую сложную функцию, чтобы она идеально имитировала путь Python. Я написал это так:
let (%) s li =
let split_list = Str.full_split (regexp "%[a-z]") s in
let rec fmt result_str s_list x_list = match s_list with
| [] -> result_str
| shd::stl -> match shd with
| Text t -> fmt (result_str^t) stl x_list
| Delim d -> match x_list with
| [] -> fmt result_str stl []
| xhd::xtl -> fmt (result_str^(Printf.sprintf d xhd)) stl xtl
in
fmt "" split_list li
Но функция просто НЕ МОЖЕТ работать, потому что ошибка типа, а также список ocaml не могут содержать несколько типов. если вы напишете что-то вроде: "name: %s; age: %d" % ["John"; 20]
мир компиляторов ocaml посмеется над кодом и скажет вам какую-то ОШИБКУ типа.
Очевидно, я должен использовать Tuple для замены List. но я просто НЕ знаю, как выполнять хвостовую рекурсию кортежа переменной длины.
любое предложение приветствуется. У меня действительно два вопроса.
- как написать питонический код ocaml для форматирования строки.
- # P10 # # P11 # # P12 #
# P13 #