Search code examples
haskellfunctional-programmingghci

parse error on input ‘::’ when making an explicit type definition for a function which accepts multiple arguments


I am working on a project in Haskell for the first time and I am working on translating over my ADT into the code properly, however when I am writing the explicit type definitions for my functions and I load my code in GHCi I get the following error:

Blockquote parse error on input ‘::’

The line in question is for a function called type which accepts a character and a tuple and returns a tuple as shown below:

type :: validChars -> tuple -> tuple

where validChars is the list of valid characters, the definitions for my lists are shown here if this helps:

tuple = (l, r, b, k)
l = [l | l <- validChars]
m = [m | m <- validChars]
b = [b | b <- validChars]
k = [k | k <- validChars]
validChars = [ chr c | c <-alphanumericChars , c >= 32, c <= 122]
alphanumericChars = [ a | a <- [0..255]]

I checked to make sure it wasn't validChars causing the error by replacing it with the Charstype as shown:

type :: Chars -> tuple -> tuple

But I still get the same error, I am a complete beginner at Haskell so I'm probably missing something important, but I am not sure what that would be exactly; I've looked at answers for similar questions I have been unsuccessful thus far. Any help with this would be appreciated.


Solution

  • type is a keyword in Haskell, so you can't use it as the name of your function.

    Furthermore type names start with a capital letter in Haskell and anything starting with a lower case letter in a type is a type variable. So if you define myFunction :: validChars -> tuple -> tuple, that defines a function that takes two arguments of arbitrary types and produces a result of the same type as the second argument. It's the same as myFunction :: a -> b -> b.

    If you write myFunction :: Chars -> tuple -> tuple, you get a function whose first argument needs to be of type Chars (which needs to exist) and the second argument is of an arbitrary type that is also the type of the result. Again it's the same as myFunction :: Chars -> a -> a.

    Note that for this to work, you'll actually have to have defined a type named Chars somewhere. If you want to take a list of Chars, the type should be [Char] instead.

    And if you want the second argument and result to actually be tuples (rather than just a type variable arbitrarily named tuple), you need to specify a tuple type like (a,b,c,d), which would accept arbitrary 4-tuples, or something specific like (Integer, String, String, String), which would accept 4-tuples containing an Integer and three Strings.