Добавил:
Опубликованный материал нарушает ваши авторские права? Сообщите нам.
Вуз: Предмет: Файл:
Теория языков программирования и методы трансляции..pdf
Скачиваний:
28
Добавлен:
05.02.2023
Размер:
3.41 Mб
Скачать

128

4.2.2.2 Множество последующих символов

Множество терминальных последующих символов (от англ. follow)

определяется следующим образом:

a F(A) αAβ * αAaγ,

где:

a – терминал или признак конца цепочки, а Σ{ };

α, β и γ – произвольные цепочки терминалов и/или нетерминалов, α,

β, γ(N Σ)*;

А – нетерминал, A N;

F(A) – множество последующих символов для нетерминала A.

Множество последующих символов включает в себя символы, которые могут следовать в выводимых цепочках за нетерминалом A. При этом данное множество не может содержать пустую цепочку. Но если при выводе после нетерминала A входная цепочка может заканчиваться, то множество F(A) бу-

дет содержать специальный символ – маркер конца цепочки. Это может быть любой символ, не входящий в алфавит языка Σ, а также не совпадающий по написанию с нетерминалами грамматики N и символом пустой цепочки e.

Для нахождения множества последующих символов некоторого нетерминала A также строятся деревья вывода. При этом:

1)деревья строятся для правой части порождающего правила грамма-

тики, содержащего нетерминал A, т.е. для правил вида B αAβ;

2)используются не самые левые выводы, как это было при нахожде-

нии множества символов-предшественников, а вывод из первого элемента цепочки β;

3)если после нереминала A в цепочке появился терминал, дальнейшее поддерево строить не следует, а терминал включается в искомое множество;

129

4)если после нетерминала A цепочка β может заканчиваться (β * e),

тогда дальнейшее поддерево строится для всех цепочек правых ча-

стей правил грамматики, содержащих нетерминал B, причем в них B

заменяется полученной ранее при выводе цепочкой;

5)если после нетерминала A цепочка β может заканчиваться (β * e) и

A = S (т.е. A – это стартовый нетерминал), то в искомое множество включается маркер конца цепочки.

· · · · · · · · · · · · · · · · · · · · · · · ·

 

Пример · · · · · · · · · · · · · · · · · · · · · · ·

 

 

 

Например, найдем для грамматики:

A BCD

B aCx | bCd | F C zBD | c | e

D Fx | e F y

символы, следующие за нетерминалом B (рис. 4.2). Стрелкой «↑» показаны позиции, в которых должны выводиться искомые терминалы. Жирным выде-

лены найденные последующие символы.

130

BCD

zBD

BD

zBFx

zB

BzBDD BcD

BFx

B

BzBD

zByx

azBx

bzBd

BzBFx

BzB

 

Byx

BzByx

Рисунок 4.2 – Деревья вывода для F(B) и F(zB)

Для первого дерева, используя пункты 1–3, получаем:

BCD 1 BzBDD BCD 1 BcD BCD 3 Byx

Но BCD 2 B (или CD 2 e), т.е. нетерминал B оказывается в конце цепочки. В левой части правила A BCD находится нетерминал A, но в пра-

вых частях правил он не встречается, поэтому пункт 4 неприменим. Так как при этом A является стартовым символом, то добавляем к множеству F(B)

маркер конца цепочки согласно пункту 5. Получили F(B) = {c, y, z, }.

Во втором дереве по пунктам 1–3 получаем вывод zBD 2 zByx

131

Далее, т.к. zBD 1 zB(или D 1 e) и в левой части правила C zBD

находится нетерминал C, находим все правые части порождающих правил,

содержащих данный нетерминал. Таких правил три:

A BCD

B aCx

B bCd

Используя пункт 4, подставляем в них вместо C цепочку zB и продол-

жаем процесс. Таким образом, для первого вхождения C получаем:

BCD * BzBD BzBFx BzByx BCD * BzBD BzB

Снова, как и выше, получается ситуация, когда во множество F(B) сле-

дует добавить маркер конца цепочки (в левой части правила A BCD нахо-

дится стартовый символ). Для второго и третьего вхождения C в грамматику: aCx * azBx

bCd * bzBd

В результате, учитывая полученные ранее элементы, F(B) = {d, x, y, } {c, y, z, } = {c, d, x, y, z, }.

· · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · · ·

По сути, для правила грамматики вида B αAβ во множество F(A)

входят элементы множества S(β), кроме e, а если после нетерминала A цепоч-

ка β может заканчиваться (β * e), то также и элементы множества F(B):

 

 

 

 

 

 

 

 

 

 

 

 

 

B

 

β e e S β ,

 

 

 

 

 

 

 

 

 

 

 

 

 

F

 

A

 

 

 

S

 

β

 

e

 

F

 

 

 

 

 

 

 

 

 

 

 

 

 

 

β e e S β .

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

Для нахождения множества последующих символов для нетерминалов грамматики G = (N, Σ, P, S) существует следующий нерекурсивный алгоритм:

1.Для всех нетерминалов грамматики A N положить F(A) = . Для стартового нетерминала положить F(S) = { }.

132

2.Для каждого вхождения нетерминала A в правую часть порождаю-

щих правил грамматики вида (B αAβ) P добавить к множеству

F(A) новые элементы, найденные по приведенной выше формуле:

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

B

 

β e e S β ,

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

F

 

A

 

F

 

A

 

 

 

S

 

β

 

e

 

F

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

β e e S β .

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

3.Если при выполнении шага 2 хотя бы в одном множестве F(A) по-

явился хотя бы один новый элемент, вернуться на шаг 2. Иначе ал-

горитм заканчивает свою работу.

· · · · · · · · · · · · · · · · · · · · · · · ·

 

Пример · · · · · · · · · · · · · · · · · · · · · · ·

 

 

 

Рассмотрим работу этого алгоритма на примере грамматики:

E T E

E′ + T E′ | e T F T

T′ * F T′ | e F ( E ) | a

В табл. 4.8 приведены результаты последовательных проходов второго шага алгоритма.

Таблица 4.8 – Результаты проходов алгоритма поиска последующих символов

 

F

1-й проход

2-й проход

N

 

 

 

 

 

 

 

 

E

 

, )

, )

 

 

 

 

E

 

,

, )

 

 

 

 

T

 

, +

, +, )

 

 

 

 

T

 

, +

, +, )

 

 

 

 

F

 

, +, *

, +, *, )