user12366705
user12366705

Reputation: 11

Haskell error: Couldn't match expected type

I am writing a Haskell code to a list of the k nearest neighbours, in distance order, according to metric d to point p in the list xs of points. Below is my code:

import Data.List

type Point a = (a,a)
type Metric a = (Point a) -> (Point a) -> Double

neighbours ::  Int -> Metric a -> Point a -> [Point a] -> [Point a]
neighbours k d p [] = []
neighbours k d p ps = take k (sortOn distance(p ps))

distance :: Metric Double
distance (x1,y1) (x2,y2) = sqrt(((x1-x2)^2)+((y1-y2)^2))

The error is

    • Couldn't match expected type ‘[Point a] -> [Point Double]’
                  with actual type ‘(a, a)’
    • The function ‘p’ is applied to one argument,
      but its type ‘(a, a)’ has none
      In the second argument of ‘sortOn’, namely ‘(p ps)’
      In the second argument of ‘take’, namely ‘(sortOn distance (p ps))’
    • Relevant bindings include
        ps :: [Point a] (bound at A4.hs:21:18)
        p :: Point a (bound at A4.hs:21:16)
        d :: Metric a (bound at A4.hs:21:14)
        neighbours :: Int -> Metric a -> Point a -> [Point a] -> [Point a]
          (bound at A4.hs:20:1)
   |
23 |                     | otherwise = take k (sortOn distance(p ps))

Please can someone tell me how to solve it?

Upvotes: 1

Views: 141

Answers (1)

chi
chi

Reputation: 116139

This part

(sortOn distance(p ps))

means:

  • call function p with argument ps, name the result res;
  • call function sortOn with two arguments: distance (the 2-arguments function), and res.

This is not what you wanted. Indeed, p is a pair, and not a function, as the error states:

 The function ‘p’ is applied to one argument,
 but its type ‘(a, a)’ has none

What you probably wanted is

(sortOn (distance p) ps)

which would sort all the points in ps according to the 1-argument function distance p, providing the distance from p.

Upvotes: 7

Related Questions