Haskell - 在函数中交换单词

时间:2014-12-02 14:34:51

标签: string haskell swap

我正在尝试创建一个函数,它将句子中的字符串(w1)与另一个字符串(w2)交换。以下是我到目前为止的情况:

swapwords :: String -> String -> String -> String 
swapwords w1 w2 [] = [] 
swapwords w1 w2 (x:xs) 
    | length (x:xs) < n = (x:xs) 
    | otherwise = do 
if w1 == take n (x:xs) then w2 ++ swapwords w1 w2 (drop n (x:xs)) 
else x:swapwords w1 w2 xs 
where 
    n = length w1 

但是,我得到一个'undefined variable“main”'错误,'警告:定义但未使用:'w1''和'w2'。我做错了什么?

2 个答案:

答案 0 :(得分:0)

该错误是由于您尝试从未定义函数main的模块构建可执行文件。警告是由你的代码有点笨拙缩进造成的(我假设你使用的是Haskell 98编译器;如果你在Haskell 2010模式下编译它,GHC 7.8.3会接受你的代码。)

虽然您可以使用do - 表示法构造类型为String的表达式(因为字符串是列表而列表的类型构造函数是monad),但在此处执行它有点奇怪上下文(你并没有真正对你正在构建的字符串做任何monadic,不是吗?)。

稍微重新格式化代码并添加函数main将使您的代码编译(也作为Haskell 98)为可执行文件:

swapwords :: String -> String -> String   -> String 
swapwords    w1        w2        []       =  [] 
swapwords    w1        w2        (x : xs)
  | length (x:xs) < n                     = x : xs  
  | otherwise                             =
      if   w1 == take n (x:xs)
      then w2 ++ swapwords w1 w2 (drop n (x:xs)) 
      else x : swapwords w1 w2 xs 
  where 
    n = length w1

main :: IO ()
main =  putStrLn (swapwords "bar" "qux" "foo bar baz")

运行此可执行文件然后允许您测试代码:

$ ghc --version
The Glorious Glasgow Haskell Compilation System, version 7.8.3

$ ghc -XHaskell98 Test.hs -o test.exe
[1 of 1] Compiling Main             ( Test.hs, Test.o )
Linking test.exe ...

$ ./test.exe 
foo qux baz

答案 1 :(得分:0)

虽然这与编译问题无关,但这是使用Text.Regex.PCRE实现函数的另一种方法:

module Swap where

import Text.Regex.PCRE ((=~))

swap :: String -> String -> String -> String
swap orig toSwap ws =
  case ws =~ orig :: (String,String,String) of
   (_,"","") -> ws
   (b,_,a) -> b ++ toSwap ++ a

虽然this text-icu library现在可能更好,但Text.Regex不支持Text.Data.Text