-2

I'm having trouble cause I can't define a function to do this:

Input: "(case (+ 5 5) ((4 9 1) 'd64)\\n((1 2) 'pepito)\\n((10) 'jorgito)"
Output: "(case (+ 5 5) ((4 9 1) 'd64)\n((1 2) 'pepito)\n((10) 'jorgito)"

I've tried this and many other, without success:

import Data.List.Split (splitOn)
import Data.List (intersperse)
import Data.Char

replace :: String -> String -> String -> [String]
replace current next [] = []
replace current next xs = intersperse [chr 92] $ splitOn current xs

I know the last function is not well coded looking their arguments, but I tried to do a replace function for "all strings" but I can't by now.

Then, my parser can't work cause is something like this:

parseCaseResult :: Parser LispVal
parseCaseResult = do
    char '\''
    first <- (letter <|> symbol) --de momento será una String
    rest <- many (digit <|> letter <|> symbol)
    return $ String (first:rest)

parseCasePair :: Parser CasePair
parseCasePair = do
    list <- lexeme (char '(') >> (lexeme (char '(')) *> parseList <* (lexeme $ char ')')
    result <- lexeme $ parseCaseResult <* char ')'
    return (list, result)

parseCaseExpr :: Parser LispVal
parseCaseExpr = do
    lexeme $ char '('
    lexeme $ string "case"
    conditional_expr <- lexeme (char '(') *> parseList <* lexeme (char ')')
    -- armada en las nuevas líneas, solucionado con un parser más trabajado
    lista <- sepBy parseCasePair newline -- $ try (string "\\\\\n") <|> try (string "\n") <|> string "\r"
    return $ CaseExpr conditional_expr lista

New info:

Complete code in github.com

Example that works in GHCi:

*Main> eval $ fromRight $ parse parseExpr "jaja" "(case (+ 5 5) ((4 9 1)   'd64\n((1 2) 'pepito\n((10) 'jorgito)"  
10 (4 9 1)
10 (1 2)
10 (10)
Right "jorgito"

But if I compile and run the main function, the code does not work I think because the parser doesn't match those \\n.

Sorry for the bad explanation in earlier versions of this question.

freinn
  • 1,049
  • 5
  • 14
  • 23
  • The escaping makes this a bit confusing. Are you looking for a function that turns a \ followed by an n into an actual newline character? – David Young May 09 '15 at 19:57
  • @DavidYoung Now it's edited and I think that is more clear. When I do `getArgs`, that getArgs give me a `String` with those `\\n`, so my parser can't parse that and my program fails. – freinn May 09 '15 at 20:23
  • Note that when you `print` a string that contains a single backslash, Haskell will quote that backslash. Are you sure that the string actually contains a double backslash, or might it just have a `\n` in it? The confusing thing about your question is that in Haskell syntax, the first string contains a `\n`, whereas the second contains a literal ascii newline character. – lpsmith May 09 '15 at 21:08
  • @lpsmith yes, I edit and include the link to github.com for you to see the entire code and some comments with examples. – freinn May 09 '15 at 21:36

1 Answers1

2

The needed function is:

foo :: String -> String
foo s = read $ "\"" ++ s ++ "\""

That achieves what I wanted, transform:

"(case (+ 5 5) ((4 9 1) 'd64)\\n((1 2) 'pepito)\\n((10) '789.456)"

into

"(case (+ 5 5) ((4 9 1) 'd64)\n((1 2) 'pepito)\n((10) '789.456)"

and now my parser is working like a charm

freinn
  • 1,049
  • 5
  • 14
  • 23