최근에 술어 함수를 다른 함수에 전달해야하는 상황이 발생했습니다. 필자가 자주 찾는 논리는 본질적으로 “이 값이이 패턴과 일치합니까?”입니다.
패턴 일치는 선언, do
블록 및 목록 이해 에서 선호되는 것처럼 보이지만 술어를 취하는 많은 함수가 있습니다. a -> Bool
여기서 패턴을 전달하는 것이 매우 편리합니다. 예를 들어, takeWhile
, until
, find
, span
, 등
지금까지 나는 \a -> case a of MyCons _ -> True; otherwise -> False
명명 된 함수 a la를 작성 let myPred (MyCons _) = True; myPred _ = False in
했지만, 둘 다 아주 추악하고 관용적이지 않은 것처럼 보입니다. “명백한”(그리고 잘못된) 방법은 비슷 \(MyCons _) -> True
하지만 부분적이고 자연스럽게 오류를 발생 시키며 심지어 더 깨끗한 방법이 있어야한다고 생각합니다.
이런 종류의 일을하는 간결하고 깨끗한 방법이 있습니까? 아니면 완전히 잘못된 방향으로 가고 있습니까?
답변
언어 확장 LambdaCase를 사용하여을 (를) 사용할 수 \case MyCons _ -> True; _ -> False
있지만 문자를 많이 저장하지는 않습니다.
난 당신이 일련의 기능을 쓸 수있는 생각 constructedWith :: (Generic a) => (b -> a) -> a -> Bool
, constructedWith2 :: (Generic a) => (b -> c -> a) -> a -> Bool
하지만 몇 시간이 물건을 테스트하지 않고 그것을 구현하는 제네릭과 능력이 충분하지 않다. 나는 이것을 시도하고, 그것을 알아낼 수 있거나 막 다른 곳이면 대답을 편집 할 것입니다.
편집 : 네, 할 수 있습니다! 내 코드에 대한 링크는 다음과 같습니다.
https://repl.it/@lalaithion/ConstructedWith
그러나 모든 일반 코드 배관에 http://hackage.haskell.org/package/generic-deriving-1.13.1/docs/Generics-Deriving-ConNames.html 과 같은 것을 사용하는 것이 좋습니다.