Ошибка при попытке сворачивания (foldr()) в Haskell

#haskell

#haskell

Вопрос:

Я пытаюсь реализовать функцию foldr() , функцию, которую я создал в коде, показанном ниже, которая представляет собой функцию для умножения каждого элемента в массиве на 2, но она выдала мне сообщение об ошибке (тоже показано ниже), и я не совсем знаю, как это исправить. Я открыт для предложений, поэтому любые советы или исправления очень помогут. Спасибо, вот исходный код

 multwo ::[a] -> [a]
multwo = foldr(x acc-> (2*x):acc)[]
 

Вот сообщение об ошибке

No instance for (Num a) arising from a use of ‘*’
      Possible fix:
        add (Num a) to the context of
          the type signature for:
            multwo :: forall a. [a] -> [a]
    • In the first argument of ‘(:)’, namely ‘(2 * x)’
      In the expression: (2 * x) : acc
      In the first argument of ‘foldr’, namely
        ‘( x acc -> (2 * x) : acc)’

  |
9 | multwo = foldr(x acc-> (2*x):acc)[]
  |                          ^^^
 

Комментарии:

1. вы могли бы закомментировать сигнатуру типа, и она сработала бы и даже сама указала вам тип.

Ответ №1:

Ваша multwo функция направлена на умножение всех элементов на два, но это возможно только в том случае, если это список чисел. В Haskell есть Num класс типов для группировки всех типов чисел. Таким образом, вы должны добавить ограничение типа к подписи:

 multwo :: Num a => [a] -> [a]
multwo = foldr (x acc-> (2*x) : acc) [] 

Вы можете сократить функцию сворачивания до:

 x -> (2*x :)
 

и далее к:

 (:) . (2 *)
 

итак, более короткая реализация выглядит так:

 multwo :: Num a => [a] -> [a]
multwo = foldr ((:) . (2*)) []