2013-05-14 2 views
5

후속 작업 : How do I test for exactly 2 characters with fparsec?파서 식별자 및 자유 형식 텍스트 FParsec으로이 작업을 수행 할 수 있습니까?

자유형 텍스트 뒤에 식별자 쌍으로 구성된 문자열을 구문 분석해야합니다. 나는 개행 문자의 형태를 띠고 정확한 두 개의 대문자와 공백이 뒤 따르는 식별자를 찾는 파서를 쉽게 만들 수있다. 앞의 식별자와 관련된 자유형 텍스트는 다음 식별자까지 포함하지만 그 다음 식별자를 제외한 모든 것입니다. 그래서 예를 들면

:

AB Now is the 
time for all good 
men. 
CD Four score and seven years ago EF our. 

두 식별자 ABCD 및 자유 텍스트의 두 조각을 포함

Now is the \ntime for all good men.
Four score and seven years ago EF our.

내 문제는 내가 구성하는 방법을 모른다됩니다 자유형 텍스트와 일치하지만 식별자와 일치하지 않는 파서. 이것이 내가 백 트랙킹을 할 필요가있는 경우인가?

이렇게 할 수 있습니까?

답변

3

내 생각에 notFollowedBy이 (가) 찾고 있습니다. 이 트릭을 수행해야합니다 :

// adapted from the other question 
let identifier = skipNewline >>. manyMinMaxSatisfy 2 2 CharParsers.isUpper 

let freeform = manyChars (notFollowedBy identifier >>. anyChar) 
4

Tarmil은 간단한 해결책을 게시했습니다. 여기

는 시작 부분에 줄 바꿈을 필요로하지 않는 다른 변종 만 라인의 끝 부분에 다음과 같은 식별자를 확인합니다 : 당신이 함께 사용되는 두 번째 파서를 최적화하고 싶었다면

let id = manyMinMaxSatisfyL 2 2 isUpper "ID" .>> pchar ' ' 

let text = 
    stringsSepBy (restOfLine true) 
       ((notFollowedBy ((id >>%()) <|> skipNewline <|> eof)) >>% "\n") 

let parser = many (id .>>. text) 

stringsSepBy 콤비, 다음 버전으로 대체 할 수 :

let notFollowedByIdOrEmptyLineOrEof : Parser<string,_> = 
    fun stream -> 
     let cs = stream.Peek2() 
     let c0, c1 = cs.Char0, cs.Char1 
     if c0 = '\r' || c0 = '\n' || c0 = EOS 
      || (isUpper c0 && isUpper c1 && stream.Peek(2) = ' ') 
     then Reply(Error, NoErrorMessages) 
     else Reply("\n") 

let text2 = stringsSepBy (restOfLine true) 
         notFollowedByIdOrEmptyLineOrEof 
+0

안녕, 당신은이 질문에 대해 언급하시기 바랍니다 수 : https://bitbucket.org/fparsec/main/issue/29/portable-version-of- 팔콘 – Den