Search code examples
functionhaskellpattern-guards

Haskell--Defining function with Guards


I am fairly new to Haskell and am working on an assignment simulating checkers currently. I am having a bit of difficulty determining the proper method of conditionally checking an expression and updating the values of a tuple. I have a function called getPos that will return the Char at a specific location on the board to determine its state.

    onemove :: (Int,[Char],[[Char]],(Int,Int)) -> (Int,[Char],[[Char]])

    onemove     (a,b,c,(d,e)) 
       | e <= 0 =(a-30,b,c)
       | e > 50 =(a-30,b,c)
       | (((posTo == 'r') || (posTo == 'i')) &&((posFrom == 'w')||(posFrom == 'k'))) == 'true'  =(a-20,b,c)
       | (((posTo == 'w')||(posTo == 'k')) && ((posFrom == 'r') || (posFrom == 'i')))== 'true' =(a-20,b,c)
       | otherwise = (1000,b,c)
       where posFrom = getPos (d, c)
             posTo =  getPos (e,c)

Is it correct to use a function to define a variable within my where clause? I receive the following error on my last line:

    parse error on input `='

Solution

  • Your immediate problem is mostly just caused by indentation. Guards need to be indented w.r.t the definition they're associated with.

    onemove :: (Int,[Char],[[Char]],(Int,Int)) -> (Int,[Char],[[Char]])
    onemove     (a,b,c,(d,e)) 
      | e <= 0 =(a-30,b,c)
      | e > 50 =(a-30,b,c)
      | (((posTo == 'r') || (posTo == 'i')) &&((posFrom == 'w')||(posFrom == 'k'))) =(a-20,b,c)
      | (((posTo == 'w')||(posTo == 'k')) && ((posFrom == 'r') || (posFrom == 'i'))) =(a-20,b,c)
      | otherwise = (1000,b,c)
      where posFrom = getPos (d, c)
            posTo =  getPos (e,c)
    

    Notice I also removed the == 'true' in your original code. That was wrong for three separate reasons.

    1. Single quotes denote a Char. Double quotes for String.
    2. You can't compare a Boolean value to a String just because that String happens to say "true". You would have to say == True.
    3. There's no reason to ever write bool == True, because that's exactly the same as just writing bool.

    Also, a, b, c, and (d,e) should probably all be separate arguments, not a single tuple. You lose all the advantages of currying that way.