String 将字符列表拆分为单词列表

String 将字符列表拆分为单词列表,string,list,function,sml,chars,String,List,Function,Sml,Chars,我目前正在学习SML函数式语言,我正在尝试创建一个函数,该函数获取一个字符列表,然后它搜索列表中的任何空格。当它找到一个空格时,它会在空格之前包含字符,然后生成一个字符串。之后,它返回一个字符串列表,这些字符串由被白色分割的字符组成空间 这是我的代码,但有点问题,编译器说,有一个错误在eof fun sepWords ([]) = [] | sepWords (x :: xs) = let val word = "" val list sepW

我目前正在学习SML函数式语言,我正在尝试创建一个函数,该函数获取一个字符列表,然后它搜索列表中的任何空格。当它找到一个空格时,它会在空格之前包含字符,然后生成一个字符串。之后,它返回一个字符串列表,这些字符串由被白色分割的字符组成空间

这是我的代码,但有点问题,编译器说,有一个错误在eof

fun sepWords ([]) = []
  | sepWords (x :: xs) =
    let 
      val word = "" 
      val list
      sepWords (xs)
    in 
      if (Char.isSpace (x)) then (word = "")
      else (word ^ x)
      word :: list
    end;
  • val列表
    sepWords(xs)
    行周围出现语法错误。也许你想写
    val list=sepWords(xs)
    ?在
    if…
    word::list
    行周围也有语法错误。我不确定这里的意图是什么,但也许你认为
    word::list
    会产生在“list”中添加“word”的副作用

  • 您的
    if…
    中存在类型错误,因为“then”分支具有类型为bool的表达式
    word=”“
    ,而“else”分支具有类型为字符串的表达式
    word^x
    。if-then-else必须在每个分支上具有相同的类型,类型检查器才能接受该程序

  • 与其使用char list->string list类型创建函数,为什么不使用string->string list类型创建函数呢?如果这样做,您甚至可以通过跟踪原始字符串中的字符索引(例如,通过使用子字符串类型),避免将字符串转换为字符列表的中间步骤

    该函数的一个好名字可以是“words”

  • 您尚未定义多个空格连续出现时的行为。
    单词“hello world”
    是否应该产生
    [“hello”,“world”]
    [“hello”,“world”]

  • 实际上,有一些内置的库函数可以做到这一点:

    - String.tokens Char.isSpace "hello  world";
    > val it = ["hello", "world"] : string list
    
    - String.fields Char.isSpace "hello  world";
    > val it = ["hello", "", "world"] : string list
    
  • 在列表递归中,将字符串转换为字符列表是一个很好的选择,即使这种策略不是很有效。您可以通过解决从输入中提取单个单词以及字符串其余部分的问题来实现这一点:

    fun firstWord [] = ([], [])
      | firstWord (c::cs) =
        if Char.isSpace c
        then ([], cs)  (* throw away the space c *)
        else case firstWord cs of
               (fw, remainder) => (c::fw, remainder)
    
    你可以这样称呼它:

    - firstWord (explode "hello  world");
    > val it =
        ([#"h", #"e", #"l", #"l", #"o"], [#" ", #"w", #"o", #"r", #"l", #"d"])
            : char list * char list
    
    只要余数不是空的,就可以递归调用它:

    fun words [] = []
      | words cs =
        let val (fw, remainder) = firstWord cs
        in implode fw :: words remainder end
    
    使用这个:

    - allWords (explode "hello  world");
    > val it = ["hello", "", "world"] : string list
    

  • 非常感谢你。你的回答不仅解决了我的问题,还教会了我很多我不知道的事情。你是最棒的!