Применение функции к произвольно длинному списку аргументов

Я хочу создать функцию применения, которая принимает функцию с произвольным количеством аргументов, а также список целых чисел и возвращает результат функции (где каждое целое число в списке является аргументом по порядку.

Я думал что-то вроде:

apply :: ([Int] -> Int) -> [Int] -> Int
apply f x:xs = apply (f x) xs
apply f [] = f

Но я знаю, что это не сработает, потому что сигнатура типа неверна — функция не принимает список целых чисел, она просто принимает некоторое количество аргументов типа int.

Кроме того, когда я доберусь до базового случая, применяемый аргумент f должен быть целым числом, что в любом случае нарушает сигнатуру типа.

Кто-нибудь знает, как справиться с такой проблемой?


person oadams    schedule 10.05.2010    source источник


Ответы (2)


Я хочу создать функцию apply, которая принимает функцию с произвольным количеством аргументов, а также список целых чисел,

почему ты хочешь сделать это? Возможно, ваша структура аргументов должна передаваться как структура данных, но до сих пор вы чрезмерно ограничивали проблему, чтобы гарантировать, что она не приведет к идиоматическому решению Haskell.

person Don Stewart    schedule 10.05.2010

Вы можете сделать это с помощью некоторых классов причудливого типа

{-# LANGUAGE FlexibleInstances #-}
-- for ApplyType (Int -> r)

class ApplyType t where
    apply :: t -> [Int] -> Int

instance ApplyType Int where
    apply f _ = f

instance (ApplyType r) => ApplyType (Int -> r) where
    apply f (x:xs) = apply (f x) xs

main :: IO ()
main = do print $ apply ((+) :: Int->Int->Int) [1, 2]
          print $ apply ((\x y z w -> x*y - z`div`w) :: Int->Int->Int->Int->Int) [3,5,8,2]
person newacct    schedule 10.05.2010
comment
Вам просто нужны FlexibleInstances и вы можете обойти весь класс IsInt и написать ApplyType (Int -> r) напрямую. - person Edward KMETT; 10.05.2010