2015-04-03 2 views
0

Итак, у меня есть этот кусок кода, который возвращает ошибку на ожидаемом типе.

не мог соответствовать ожидается тип [(Char, b0)]
с фактическим типом '(Char, Int)'
В выражении: NewList
В виде зЬтЬ элемент списка понимания: (а, b) < - newList

Haskell Не удалось совместить ожидаемый тип '[(Char, b0)]' с фактическим типом '(Char, Int)'

Я хочу вернуть местоположение символа, так что это будет «b». Я просто не понимаю, почему это дает мне ошибку типа. Всякий раз, когда я запускаю код один за другим внутри WinGHCI, я верну правильную информацию. Когда вы помещаете его в файл .hs, он не будет.

word = "apple" 
isPart :: Char -> a 
isPart x = do 
      newList <- zip word [0..length word] 
      result <- [b | (a,b) <- newList, a == x] 
      return result 

ответ

6

Внутри вашего do блока

newList <- zip word [0..length word] 

является обессахаренная в нечто вроде

zip word [0..length] >>= \newList -> ... 

Тип >>= является (Monad m) => m a -> (a -> m b) -> m b.

С zip возвращает список, вы используете список monad, и поэтому тип newList на самом деле является (Int, Char). Затем вы не можете использовать это как источник для последующего понимания списка.

Однако вам не нужно использовать do вообще:

isPart :: Char -> Int 
isPart x = let newList = zip word [0..length word] 
       result = [b | (a,b) <- newList, a == x] 
      in head result 

хотя бы знать, это вызовет ошибку, если данный символ не в word

Вы также можете написать это более просто в

import Data.List (elemIndex) 
import Data.Maybe (fromJust) 

isPart x = fromJust $ elemIndex x word 

хотя лучшим решением было бы изменить тип возвращаемого значения Maybe Int вместо fromJust.

Смежные вопросы