2017-11-25 6 views
0

하스켈과 관련하여 문제가 많은 소규모 과제를 다룹니다. 정수가리스트의 일부인지 아닌지를 찾기위한 재귀 적 메소드를 만들려고합니다. 나는 그 요지를 안다. 그러나 haskell 문법을 올바르게 작동시키지 못한다. 현재 목록이 비어 있는지 확인한 다음 False이면 정수가 현재 목록의 머리글과 같은지 확인하고 True이면 해당 값을 가진 멤버를 다시 호출하고 그 목록. 이 기능을 제대로 수행하려면 어떻게해야합니까?하스켈의 멤버 함수

member ::Int -> [Int] -> Bool 
member x y 
if y [] then False 
else if x == head y then True 
else member x tail y 

나는 또한 시작 라인으로

member :: (Eq x) => x -> [x] -> Bool 

를 사용하여 시도했다, 또한 훨씬 더 간단 :

let member x y = if null y then False 
else if x == head y then True 
else member x tail y 

어떤 도움

현재이 내가 가진 무엇 감사하겠습니다. 좀 더 명확하게 쓸 수 있습니다 일치하는 패턴

+0

꼬리 앞에 $를 추가하면 원래 버전이 작동합니다. 응용 프로그램은 왼쪽 연관입니다. – bipll

+0

나는이 오류를 추가하고있다. 구문 분석 오류 : 상위 수준의 노출 표현 아마도 TemplateHaskell을 사용하려고했습니다. – Elmangos

+0

들여 쓰기를 잊어 버리지 않았습니까? – bipll

답변

3

member :: (Eq a) => a -> [a] -> Bool 
member x [] = False 
member x (y:ys) | x==y = True 
       | otherwise = member x ys 
+0

이것을 사용할 때 예상되는 타입 'IO t2'를 실제 타입 'Bool'과 일치시킬 수 없다. expression : main IO 액션 'main'의 타입을 검사 할 때 – Elmangos

+0

이것은'main '을 잘못 작성했기 때문입니다. 이 'element'구현은 정상입니다. – HTNW

+0

주 기능은 어떻게해야합니까? 나는 현재 main = do member 1을 가지고있다. [1 2 3] – Elmangos

3
element _ [] = False 
element e (x:xs) = e == x || e `element` xs 
-- OR 
element e xs = if xs == [] then False 
       else if e == head xs then True 
        else e `element` tail xs 
-- OR 
element e xs = xs /= [] && (e == head xs || e `element` tail xs) 
-- x `op` y = op x y 

-- If you're feeling cheeky 
element = elem 
귀하의 구문은 매우 혼란 나타납니다,하지만 당신의 논리는 기억하는 것들의 버킷리스트를, 그래서 여기에 의미가있어

:

  • 함수는 여러 방정식으로 정의 할 수 있습니다. 방정식은 위에서 아래로 검사됩니다. 이는 =을 사용한다는 것을 의미합니다.

  • 패턴 일치 평등 테스트가 아닙니다. 패턴 일치는 값이 일치하면 해당 구성 요소로 값을 나눕니다. 그렇지 않으면 실패합니다. 동등성 테스트 x == yxy의 동등성에 대해 Bool을 반환합니다.

  • 패턴 매칭은

    element _ []  = ... 
    element e (x:xs) = ... 
    

    주처럼

    case xs of { 
        [] -> ... 
        x:xs' -> ... 
    } 
    
  • 여러 방정식처럼 ... 통해 흐름 제어

    • case 문을 사용하는 당신을 _으로 패턴의 값을 무시할 수 있습니다. 다중 인수를 갖는 함수의 여러 방정식을 사용하면 모든 인수에 대한 패턴 매칭을 한꺼번에 수행 할 수 있습니다.

  • Boolif _ then _ else _을 통해 흐름 제어에 사용되는 : 정말

    if xs == [] then False 
          else True 
    

    단지

    case x == y of { 
        True -> False 
        False -> True 
    } 
    

    Bool s는 일반 사업자 (&&) (infixr 3)와 (||)을 사용할 수 있습니다 (infixr 2)

  • 차이점은 특히 목록에 있습니다. instance Eq a => Eq [a]이므로 목록에 ==을 사용하려면 목록의 요소를 동일하게 비교할 수 있어야합니다. (== [])을 확인하는 경우에도 마찬가지입니다. [] == []은 컴파일러가 요소의 유형을 알 수 없기 때문에 실제로 오류가 발생합니다. 여기에서는 중요하지 않지만, 말하면, 예. nonEmpty xs = xs /= [] 일 경우 nonEmpty :: [a] -> Bool 대신 nonEmpty :: Eq a => [a] -> Bool이 표시되므로 일 때 nonEmpty [not]은 유형 오류를 발생시킵니다.

  • 기능 응용 프로그램은 왼쪽 연관을 가장 높은 우선 순위를 가지고 있으며, 다음과 같습니다 ((element x) xs)

  • element x tail xs 여기에 의미
  • 하지 않는, (((element x) tail) xs)로 읽는

    • element x xs 읽기 f $ x = f x이지만, 그것은 infixr 0입니다. 이는 기본적으로 규칙을 뒤집어서 큰 괄호처럼 사용하는 것을 의미합니다. 너무

      • x `element` tail xs((element x) (tail xs))을 의미
    • :
  • 중위 기능 항상 접두사 응용 프로그램보다 낮은 우선 순위가 작동

    • element x $ tail xs((element x) (tail xs))로 읽는 오른쪽 인수, 주위의
    • let decls in expr이고 표현식은입니다. decls은 범위가 expr이며 전체가 expr으로 평가됩니다. 최상위 레벨에서는 의미가 없습니다.

    • 하스켈은 파이썬처럼 코드를 구조화하기 위해 들여 쓰기를 사용합니다. Reference