2
나는 다음과 같은 구문 분석됩니다 파섹를 사용하여 파서 쓰기를 시도하고있어와 하스켈의 하위 집합을 구문 분석 다음 data
표현파섹
data Nat = Z | S Nat
plusNat :: Nat -> Nat -> Nat
plusNat Z m = m
plusNat (S n) m = S (plusNat n m)
을, 나는 다음과 같은 파서 있습니다
parseData = reserved "data" >> DataDefn
<$> identifier
<*> parseCnstr `sepBy` reservedOp "|"
parseCnstr = DataCnstr <$> identifier <*> many parseTypeTerm
parseType = buildExpressionParser table parseTypeTerm
where table = [[function]]
function = Infix (Function <$ reservedOp "->") AssocRight
parseTypeTerm = TypeVar <$> identifier
<|> parens parseType
을
그러나 위의 텍스트에서이 파서를 사용하는 경우 parseType
그래머는 plusNat
이고 오류는 다음과 같습니다.
"test.hs" (line 3, column 9):
unexpected ':'
expecting "|" or end of input
plusNat
이 dataCnstr
의 일부로 인식 되었기 때문에 문제가 무엇인지 압니다. dataCnstr
파서가 들여 쓰기되지 않은 새 줄을 가져올 때 멈추도록하려면 어떻게합니까? 나는뿐만 아니라 다음과 같은 구문 분석 할 수 있도록하려면
참고 :
data ReallyLongData reallyLongTypeVariable
= ReallyLongConstructor1
| ReallyLongConstructor2
reallyLongTypeVariable
(ReallyLongData reallyLongTypeVariable)
concat :: ReallyLongData a -> ReallyLongData a -> ReallyLongData a
concat = ...
'buildExpressionParser'는 * 표현식 만 이해합니다 *. 여러분은 입력 문자열을'buildExpressionParser'에 넣을 수있는 문자열로 들여 쓰기 할 수있는 들여 쓰기 파서가 필요합니다 (아마 라이브러리가 있습니다). (실제로 입력 자체를 제한하는 것 외에는 블랙 박스 파서가 취하는 것을 "제한"할 수는 없습니다.) – Rufflewind
감사합니다. 입력을 들여 쓰기 블록으로 나누는 파서를 작성했습니다. –
잠깐, 작동하지 않습니다. 들여 쓰기 된 블록을 나누는 String -> [String] 함수가 있지만 이제 SourcePos를 올바르게 유지하면서 각 블록을 구문 분석 할 수있는 방법을 찾을 수 없습니다. mapM을 사용하면 작동하지 않습니다. –