답변

1

FIRST 집합을 계산하려면 일반적으로 고정 소수점 반복을 수행합니다. 즉, 작은 값 집합으로 시작한 다음 집합이 수렴 될 때까지 FIRST 집합을 반복적으로 다시 계산합니다.

이 경우, 생산 A → s는 FIRST (A)가 {s}을 포함해야한다는 것을 의미하는 것으로 시작합니다. 처음에는 FIRST (A) = {s}를 설정했습니다.

이제 각 산출물을 반복하고 지금까지 계산 한 FIRST 세트에 대한 지식을 기반으로 FIRST를 업데이트합니다. 예를 들어, 규칙

→ AAB

수단 먼저 (AAB)의 모든 요소를 ​​포함하는 FIRST (A)를 업데이트해야하는. 이로 인해 FIRST (A)가 변경되지 않습니다. 그런 다음 방문

→ Ab의

당신은 또 다시 어떤 조합입니다 FIRST (AB)를 포함하는 FIRST (A)를 업데이트합니다. 마지막으로,

을의 방문 →의

그리고 FIRST (A)가 이미의를 포함하기 때문에,이 변화가 발생하지 않습니다

.

이 반복에서 변경된 사항이 없으므로 FIRST (A) = {s}로 끝납니다. A에서 시작하는 파생은 궁극적으로 s을 첫 번째 문자로 생성하기 때문에 실제로 맞습니다.

자세한 내용은 these lecture slides (여기 part two)을 참조하십시오. 그들은 하향식 파싱이 어떻게 작동하는지 그리고 FIRST 집합을 반복적으로 계산하는 방법을 자세히 설명합니다.

희망이 도움이됩니다.

+0

@ Apalala-이 점에 대해 확실합니까? 'b'기호는 FIRST (A)에 분명히 없습니다. FIRST 집합을 계산하기 위해 알고있는 알고리즘은 FIRST 집합을 터미널로 시작하는 모든 제작물에 시드 한 다음 거기에서부터 진행하여 작동합니다. – templatetypedef

+0

@ Apalala- 또는 그런 식으로 모든 것을 시드하지 않으면, 비 터미널이 엡실론을 생성 할 수 없다면 첫 번째 세트의 비 터미널을 조사하여 FIRST 세트를 계산하지 않아도됩니다. 이는 업데이트 규칙이 FIRST (A)를 FIRST (A)에 추가하여 빈 세트를 자체에 추가하게됨을 의미합니다. – templatetypedef

+0

'A -> b '형식의 규칙에 대해 터미널에 FIRST를 시드 할 수는 있지만 일반적으로 충분하지는 않습니다. 하지만 내 downvote에 대한 이유는 당신이 'A -> AAb'에서 FIRST를 계산할 때 첫 번째 A 만보아야한다는 것이고 이것이 잘못된 것입니다. 왜냐하면이 경우가 아니더라도 ' A = * => ε' 일 경우'FIRST (A)'에'b '가 들어갑니다. * FIRST *에 대한 일반적인 해결책은 내 대답을 참조하십시오. – Apalala

-2

문법 규칙은 이미 실현 했으므로 left recursion이고 LL 파서는 are not able to parse grammars with left recursion입니다.

그래서 왼쪽 재귀를 먼저 제거해야합니다. 그런 다음 규칙의 첫 번째 집합을 계산할 수 있어야합니다.

+0

이것이 사실이지만, OP의 질문은 문법이 왼쪽 재귀 적 일지라도 가능한 FIRST 집합을 계산하는 문제라고 생각합니다. – templatetypedef

+0

질문은 * FIRST * 집합을 계산하는 것에 관한 것이며, 이것은 왼쪽 재귀 문법에 대해 수행 할 수 있습니다. – Apalala

-1

teaching notes은 스페인어로되어 있지만 알고리즘은 영어로되어 있습니다., ε가 널 (null) 문자열, P이 제작 (규칙)의 집합입니다, N 비 터미널의 집합입니다,

foreach a ∈ Σ do 
    F(a) := {a} 
for each A ∈ N do 
    if A→ε ∈ P then 
      F(A) := {ε} 
    else 
      F(A) := ∅ 
repeat 
    for each A ∈ N do 
      F'(A) := F(A) 
    for each A → X1X2...Xn ∈ P do 
      if n > 0 then 
       F(A) := F(A) ∪ F'(X1) ⋅k F'(X2) ⋅k ... ⋅k F'(Xn) 
until F(A) = F'(A) forall A ∈ N 
FIRSTk(X) := F(X) forall X ∈ (Σ ∪ N) 

Σ 알파벳 (터미널)입니다 :이 FIRST을 계산하는 방법 중 하나입니다 ⋅kk 위치로 트림 된 연결입니다. ∅ ⋅k x = ∅에 주목하고 두 세트를 연결하면 데카르트 제품의 요소가 연결됩니다.

FIRST을 손으로 계산하는 가장 쉬운 방법은 알고리즘 반복 당 하나의 테이블을 사용하는 것입니다.

F(A) = ∅ 

F'(A) = F(A) ⋅1 F(A) .1 F(b) U F(A) .1 F(b) U F(s) 
F'(A) = ∅ ⋅1 ∅ ⋅1 {b} U ∅ ⋅1 {b} U {s} 
F'(A) = ∅ U ∅ U {s} 
F'(A) = {s} 

F''(A) = F'(A) ⋅1 F'(A) .1 F'(b) U F'(A) .1 F'(b) U F'(s) 
F''(A) = {s} ⋅1 {s} ⋅1 {b} U {s} ⋅1 {b} U {s} 
F''(A) = {s} U {s} U {s} 
F''(A) = {s} 

그리고 우리가 완료 때문에 F' = F'', 그래서 FIRST = F''FIRST(A) = {s}.