2013-05-13 7 views
2

나는 ANTLRWorks에 EBNF 문법에 문제가있어 :EBNF 문법 (ANTLR은)

line 37:  
upper_lower_case 
: LOWER_CASE 
| UPPER_CASE 
; 

line 42: 
CLASSNAME 
: UPPER_CASE (DIGITS | upper_lower_case)* 
; 

line 51: 
UPPER_CASE 
: 'A'..'Z' 
; 

line 55: 
LOWER_CASE 
: 'a'..'z' 
; 

line 60: 
DIGITS : '0'..'9' 
; 

내가 CLASSNAME 항상 대문자로 시작하고 숫자, 대소 문자 구성이 할 수있는 것보다 할 .

오류 로그 :

[13:11:59] warning(200): classgenerator.g:43:42: 
Decision can match input such as "'0'..'9'" using multiple alternatives: 1, 2 

As a result, alternative(s) 2 were disabled for that input 
[13:11:59] warning(200): classgenerator.g:43:42: 
Decision can match input such as "<EOT>" using multiple alternatives: 2, 3 

As a result, alternative(s) 3 were disabled for that input 
[13:11:59] error(201): classgenerator.g:43:42: The following alternatives can never be 
matched: 3 

[13:11:59] error(208): classgenerator.g:60:1: The following token definitions can never 
be matched because prior tokens match the same input: UPPER_CASE,DIGITS 

은 누구도 날이 문제를 해결하는 데 도움이 있을까요? 미리 감사드립니다.

감사합니다, Hladeo

편집 :이 토큰에하지를 의미 않을 경우

그래서 나는 조각 키워드를 사용해야합니까? 조각 키워드를 사용하는 이런 식으로 잘못 될 것입니까?

tokens { 
PUBLIC = '+'; 
PRIVATE = '-'; 
PROTECTED = '='; 
} 

fragment ACCESSOR 
: PUBLIC 
| PRIVATE 
| PROTECTED 
; 

및 다른 질문.

OBJECTNAME 
: UPPER_LOWER_CASE (UPPER_LOWER_CASE | DIGIT)* 
; 

OBJECTNAME해야는 (상단 또는 중요하지 않습니다 맡았다 이하) 적어도 하나 개의 문자로 구성되어 있으며 선택적으로 다른 문자 또는 숫자의 - 코드의 일부 뭐가 잘못? - 내가 예를 variable에 대한 입력하려고 할 때 나는 오류를 받고 있어요 Variable 대문자로 시작하면 괜찮아,하지만 :

line 1:15 mismatched input 'Variable' expecting OBJECTNAME 

답변

2

귀하의 렉서 규칙 CLASSNAME 현재 파서 규칙 upper_lower_case을 (렉서 규칙은 대문자로 시작 참조 파서 규칙은 소문자로 시작합니다. 렉서 규칙은 렉서 규칙 만 참조 할 수 있습니다.

또한 UPPER_CASE, LOWER_CASEDIGITS은 토큰 자체를 만들지 않아야하므로 fragment 규칙으로 표시되어야합니다. 다음 예에서는 DIGITSDIGIT으로 변경 했으므로 하나의 숫자 만 일치합니다.

CLASSNAME : UPPER_CASE (DIGIT | UPPER_LOWER_CASE)*; 

fragment UPPER_LOWER_CASE : LOWER_CASE | UPPER_CASE; 
fragment UPPER_CASE : 'A'..'Z'; 
fragment LOWER_CASE : 'a'..'z'; 
fragment DIGIT : '0'..'9'; 

편집 1 (질문의 편집에 대한) :

  • 입력 텍스트의 조각은 하나 개의 토큰 유형을 가질 수 있습니다. 예를 들어, 입력 텍스트 X3을 고려하십시오. 이 텍스트는 CLASSNAME 또는 OBJECTNAME과 일치 할 수 있기 때문에 렉서는 결국 문법에 나타나는 첫 번째 규칙 유형을 할당하게됩니다. 즉, CLASSNAME 문법에 OBJECTNAME 전에 입력이 X3항상CLASSNAME 토큰되며 결코OBJECTNAME 토큰 될 것입니다 나타나는 경우. OBJECTNAME 문법에 CLASSNAME 전에 나타나는 경우, 입력 X3항상OBJECTNAME결코이 될 수있을 것입니다 CLASSNAME (사실,이 경우에는 토큰이 적 CLASSNAME 수 없습니다).이 같은 파서 규칙해야처럼

  • 귀하의 ACCESSOR 규칙 보이는 다음

    :합니다 (CLASSNAME을 구별에 대한 의견 및 OBJECTNAME에 대한)

    accessor : PUBLIC | PROTECTED | PRIVATE; 
    

편집 2 CLASSNAMEOBJECTNAME을 구별하려면 둘 중 하나와 일치하는 렉서 규칙 IDENTIFIER을 만들 수 있습니다.

IDENTIFIER : UPPER_LOWER_CASE (DIGIT | UPPER_LOWER_CASE)*; 

그런 구분을 처리하는 파서 규칙을 만들 수 있습니다 :

classname : IDENTIFIER; 
objectname : IDENTIFIER; 

은 분명히이 언어에서 유효하지 않은 classname 될 수 있습니다. 가능하면 항상 파서 규칙을 약간 완화하고 나중에 더 나은 오류 메시지를 제공 할 수있는 추가 유효성 검사를 수행하는 것을 선호합니다. 예를 들어 이 classname과 일치하도록 허용 한 경우 입력을 구문 분석하고 AST (ANTLR 3) 또는 구문 분석 트리 (ANTLR 4)를 사용하면 classname의 모든 인스턴스를 찾고 일치하는 IDENTIFIER이 필요한 대문자. 파서의 자동 오류보고에 의해 생산

예 오류 메시지 : 별도의 검증에 의해 생산

line 1:15 mismatched input 'variable' expecting CLASSNAME

예 오류 메시지 : 응답

line 1:15 class name variable must start with an upper case letter

+0

감사합니다. 내 새로운 질문에 대답 해 주시겠습니까? 첫 번째 게시물을 수정했습니다. – Hladeo

+0

CLASSNAME과 OBJECTNAME을 구분할 수 있습니까? 간단한 자바 클래스 생성기를 쓰고 있는데,'create ClassName + name : String, -age : int;'변수, age, String 및 int는 OBJECTNAME입니다. – Hladeo

+0

@Hladeo 편집 내 대답 2를 참조하십시오 :) –