OCaml中多分隔符分割字符串后遍历筛选及match语句应用
OCaml 多分隔符字符串分割与筛选实现
问题描述
给定字符串:
"ab bc cdv gf ed aqb ahf sd abcdef需求:
a) 使用' '、'\r\n'、'\t'作为分隔符分割该字符串;
b) 筛选出分割结果中以'a'开头的子串(预期结果:["ab", "ahf", "abcdef"])。
注意:禁止使用Str或其他额外库。
现有错误代码:
let f g = String.split_on_char ' ' g |> List.iter (fun x -> x);;问题:仅能按空格分割,无法处理换行符;且
List.iter仅执行无返回值的副作用,无法得到处理后的列表。需了解如何用match语句实现,或调整管道符与列表函数的使用方式,以及其他可行方案。
实现方案
1. 多分隔符分割字符串
OCaml标准库的String.split_on_char仅支持单个分隔符,我们可以通过递归遍历字符串+match匹配的方式实现多分隔符分割,同时自动跳过连续分隔符产生的空串:
let split_multisep s = (* 判断字符是否为分隔符 *) let is_sep c = c = ' ' || c = '\n' || c = '\r' || c = '\t' in (* 递归辅助函数:acc存储已完成的子串,current存储正在构建的子串 *) let rec aux acc current = function | [] -> (* 遍历结束,把最后一个非空子串加入列表后反转(保持原顺序) *) List.rev (if current = "" then acc else current :: acc) | c :: cs -> match is_sep c with | true -> (* 遇到分隔符:若当前正在构建的子串非空,就加入结果列表,重置current *) let new_acc = if current = "" then acc else current :: acc in aux new_acc "" cs | false -> (* 非分隔符:拼接到current上继续构建 *) aux acc (current ^ String.make 1 c) cs in (* 把字符串转为字符序列列表,传入递归函数 *) aux "" "" (List.of_seq (String.to_seq s))
2. 筛选以'a'开头的子串
用List.filter结合match判断字符串首字符,同时处理空串避免越界:
let starts_with_a s = match s with | "" -> false (* 空串直接排除 *) | _ -> s.[0] = 'a' let process_string s = s |> split_multisep |> List.filter starts_with_a
3. 调用示例
let test_str = "ab bc cdv gf\ned aqb ahf sd\nabcdef" let result = process_string test_str (* 输出结果:["ab"; "ahf"; "abcdef"] *)
原代码问题说明
List.iter仅用于执行打印、修改外部变量等副作用操作,不会返回新列表,筛选需求应使用List.filter;- 多次嵌套
split_on_char会产生大量空串,后续还需额外过滤,递归遍历的方式可以在分割阶段直接跳过空串,逻辑更简洁高效。
内容的提问来源于stack exchange,提问作者Juser
相关产品推荐
相关产品推荐

