πŸ“ Как ΡΠΎΠ·Π΄Π°Ρ‚ΡŒ свой собствСнный компилятор Π½Π° Python: ΠΏΠΎΠ΄Ρ€ΠΎΠ±Π½ΠΎΠ΅ руководство 🐍

Π§Ρ‚ΠΎΠ±Ρ‹ Π½Π°ΠΏΠΈΡΠ°Ρ‚ΡŒ свой компилятор Π½Π° Python, Π²Π°ΠΌ понадобятся Π½Π΅ΠΊΠΎΡ‚ΠΎΡ€Ρ‹Π΅ знания ΠΎ парсингС ΠΈ Π³Π΅Π½Π΅Ρ€Π°Ρ†ΠΈΠΈ ΠΊΠΎΠ΄Π°. Π’ΠΎΡ‚ шаги, ΠΊΠΎΡ‚ΠΎΡ€Ρ‹Π΅ Π²Π°ΠΌ слСдуСт Π²Ρ‹ΠΏΠΎΠ»Π½ΠΈΡ‚ΡŒ:

  1. Π¨Π°Π³ 1: Π Π°Π·Π±Π΅Ρ€ΠΈΡ‚Π΅ΡΡŒ с Π°Π½Π°Π»ΠΈΠ·ΠΎΠΌ ΠΈ Ρ€Π°Π·Π±ΠΎΡ€ΠΎΠΌ исходного ΠΊΠΎΠ΄Π°. Π˜ΡΠΏΠΎΠ»ΡŒΠ·ΡƒΠΉΡ‚Π΅ Π±ΠΈΠ±Π»ΠΈΠΎΡ‚Π΅ΠΊΡƒ Python, Ρ‚Π°ΠΊΡƒΡŽ ΠΊΠ°ΠΊ ANTLR ΠΈΠ»ΠΈ PLY, Ρ‡Ρ‚ΠΎΠ±Ρ‹ ΡΠΎΠ·Π΄Π°Ρ‚ΡŒ Π³Ρ€Π°ΠΌΠΌΠ°Ρ‚ΠΈΠΊΡƒ ΠΈ лСксСр для вашСго языка.
  2. Π¨Π°Π³ 2: ΠΠ°ΠΏΠΈΡˆΠΈΡ‚Π΅ парсСр, ΠΊΠΎΡ‚ΠΎΡ€Ρ‹ΠΉ ΠΏΡ€Π΅ΠΎΠ±Ρ€Π°Π·ΡƒΠ΅Ρ‚ исходный ΠΊΠΎΠ΄ Π²ΠΎ Π²Π½ΡƒΡ‚Ρ€Π΅Π½Π½Π΅Π΅ прСдставлСниС, Ρ‚Π°ΠΊΠΎΠ΅ ΠΊΠ°ΠΊ абстрактноС синтаксичСскоС Π΄Π΅Ρ€Π΅Π²ΠΎ (AST).
  3. Π¨Π°Π³ 3: Π Π΅Π°Π»ΠΈΠ·ΡƒΠΉΡ‚Π΅ Π³Π΅Π½Π΅Ρ€Π°Ρ‚ΠΎΡ€ ΠΊΠΎΠ΄Π°, ΠΊΠΎΡ‚ΠΎΡ€Ρ‹ΠΉ ΠΏΡ€Π΅ΠΎΠ±Ρ€Π°Π·ΡƒΠ΅Ρ‚ AST Π² Ρ†Π΅Π»Π΅Π²ΠΎΠΉ язык, Ρ‚Π°ΠΊΠΎΠΉ ΠΊΠ°ΠΊ Python bytecode ΠΈΠ»ΠΈ ΠΌΠ°ΡˆΠΈΠ½Π½Ρ‹ΠΉ ΠΊΠΎΠ΄.
  4. Π¨Π°Π³ 4: ΠŸΡ€ΠΎΡ‚Π΅ΡΡ‚ΠΈΡ€ΡƒΠΉΡ‚Π΅ ваш компилятор, ΠΈΡΠΏΠΎΠ»ΡŒΠ·ΡƒΡ ΠΏΡ€ΠΈΠΌΠ΅Ρ€Ρ‹ исходного ΠΊΠΎΠ΄Π°. Π£Π±Π΅Π΄ΠΈΡ‚Π΅ΡΡŒ, Ρ‡Ρ‚ΠΎ ΠΎΠ½ ΠΏΡ€Π°Π²ΠΈΠ»ΡŒΠ½ΠΎ ΠΏΡ€Π΅ΠΎΠ±Ρ€Π°Π·ΡƒΠ΅Ρ‚ ΠΊΠΎΠ΄ ΠΈ Ρ€Π°Π±ΠΎΡ‚Π°Π΅Ρ‚ ΠΎΠΆΠΈΠ΄Π°Π΅ΠΌΡ‹ΠΌ ΠΎΠ±Ρ€Π°Π·ΠΎΠΌ.

Π’ΠΎΡ‚ ΠΏΡ€ΠΈΠΌΠ΅Ρ€ простого компилятора Π½Π° Python, ΠΊΠΎΡ‚ΠΎΡ€Ρ‹ΠΉ ΠΏΡ€Π΅ΠΎΠ±Ρ€Π°Π·ΡƒΠ΅Ρ‚ ΠΏΡ€ΠΎΡΡ‚ΡƒΡŽ Π°Ρ€ΠΈΡ„ΠΌΠ΅Ρ‚ΠΈΡ‡Π΅ΡΠΊΡƒΡŽ Π²Ρ‹Ρ€Π°ΠΆΠ΅Π½ΠΈΠ΅ Π² ΠΎΠ±Ρ€Π°Ρ‚Π½ΡƒΡŽ ΠΏΠΎΠ»ΡŒΡΠΊΡƒΡŽ запись:


import operator

OPERATORS = {
    '+': operator.add,
    '-': operator.sub,
    '*': operator.mul,
    '/': operator.truediv
}

def compile_expr(expr):
    stack = []
    tokens = expr.split()
    
    for token in tokens:
        if token in OPERATORS:
            op2 = stack.pop()
            op1 = stack.pop()
            result = OPERATORS[token](op1, op2)
            stack.append(result)
        else:
            stack.append(float(token))
    
    return stack[0]

expr = input("Π’Π²Π΅Π΄ΠΈΡ‚Π΅ арифмСтичСскоС Π²Ρ‹Ρ€Π°ΠΆΠ΅Π½ΠΈΠ΅: ")
result = compile_expr(expr)
print(result)
    

Π”Π΅Ρ‚Π°Π»ΡŒΠ½Ρ‹ΠΉ ΠΎΡ‚Π²Π΅Ρ‚

Как Π½Π°ΠΏΠΈΡΠ°Ρ‚ΡŒ свой компилятор Π½Π° Python

НаписаниС компилятора - это интСрСсноС ΠΈ слоТноС Π·Π°Π΄Π°Π½ΠΈΠ΅, ΠΊΠΎΡ‚ΠΎΡ€ΠΎΠ΅ Ρ‚Ρ€Π΅Π±ΡƒΠ΅Ρ‚ Π³Π»ΡƒΠ±ΠΎΠΊΠΎΠ³ΠΎ понимания языка программирования ΠΈ Π°Π»Π³ΠΎΡ€ΠΈΡ‚ΠΌΠΎΠ². Π’ этой ΡΡ‚Π°Ρ‚ΡŒΠ΅ ΠΌΡ‹ рассмотрим шаги, Π½Π΅ΠΎΠ±Ρ…ΠΎΠ΄ΠΈΠΌΡ‹Π΅ для создания своСго компилятора Π½Π° Python.

Π¨Π°Π³ 1: ΠžΠΏΡ€Π΅Π΄Π΅Π»Π΅Π½ΠΈΠ΅ Π³Ρ€Π°ΠΌΠΌΠ°Ρ‚ΠΈΠΊΠΈ

ΠŸΠ΅Ρ€Π²Ρ‹ΠΌ шагом Π² создании компилятора являСтся ΠΎΠΏΡ€Π΅Π΄Π΅Π»Π΅Π½ΠΈΠ΅ Π³Ρ€Π°ΠΌΠΌΠ°Ρ‚ΠΈΠΊΠΈ языка, ΠΊΠΎΡ‚ΠΎΡ€Ρ‹ΠΉ Π²Ρ‹ Ρ…ΠΎΡ‚ΠΈΡ‚Π΅ ΡΠΊΠΎΠΌΠΏΠΈΠ»ΠΈΡ€ΠΎΠ²Π°Ρ‚ΡŒ. Π“Ρ€Π°ΠΌΠΌΠ°Ρ‚ΠΈΠΊΠ° опрСдСляСт синтаксис ΠΈ ΠΏΡ€Π°Π²ΠΈΠ»Π° языка. НапримСр, Π³Ρ€Π°ΠΌΠΌΠ°Ρ‚ΠΈΠΊΠ° ΠΌΠΎΠΆΠ΅Ρ‚ ΠΎΠΏΡ€Π΅Π΄Π΅Π»ΡΡ‚ΡŒ структуру Π²Ρ‹Ρ€Π°ΠΆΠ΅Π½ΠΈΠΉ, ΠΎΠΏΠ΅Ρ€Π°Ρ‚ΠΎΡ€Ρ‹, Ρ‚ΠΈΠΏΡ‹ Π΄Π°Π½Π½Ρ‹Ρ… ΠΈ Ρ‚.Π΄.

Π’Ρ‹Π±ΠΎΡ€ ΠΏΡ€Π°Π²ΠΈΠ»ΡŒΠ½ΠΎΠΉ Π³Ρ€Π°ΠΌΠΌΠ°Ρ‚ΠΈΠΊΠΈ являСтся ΠΊΠ»ΡŽΡ‡Π΅Π²Ρ‹ΠΌ этапом, Ρ‚Π°ΠΊ ΠΊΠ°ΠΊ ΠΎΠ½Π° Π±ΡƒΠ΄Π΅Ρ‚ ΠΎΠΏΡ€Π΅Π΄Π΅Π»ΡΡ‚ΡŒ, ΠΊΠ°ΠΊΠΈΠ΅ конструкции языка Π²Ρ‹ смоТСтС ΠΊΠΎΠΌΠΏΠΈΠ»ΠΈΡ€ΠΎΠ²Π°Ρ‚ΡŒ. Π’Π°ΠΌ ΠΌΠΎΠ³ΡƒΡ‚ ΠΏΠΎΠ½Π°Π΄ΠΎΠ±ΠΈΡ‚ΡŒΡΡ знания ΠΎ Ρ„ΠΎΡ€ΠΌΠ°Π»ΡŒΠ½Ρ‹Ρ… Π³Ρ€Π°ΠΌΠΌΠ°Ρ‚ΠΈΠΊΠ°Ρ… ΠΈ Ρ‚Π΅ΠΎΡ€ΠΈΠΈ языков программирования.

Π¨Π°Π³ 2: ЛСксичСский Π°Π½Π°Π»ΠΈΠ·

ЛСксичСский Π°Π½Π°Π»ΠΈΠ·Π°Ρ‚ΠΎΡ€ (Ρ‚Π°ΠΊΠΆΠ΅ извСстный ΠΊΠ°ΠΊ сканСр) ΠΏΡ€Π΅ΠΎΠ±Ρ€Π°Π·ΡƒΠ΅Ρ‚ исходный ΠΊΠΎΠ΄ Π½Π° языкС программирования Π² ΠΏΠΎΡΠ»Π΅Π΄ΠΎΠ²Π°Ρ‚Π΅Π»ΡŒΠ½ΠΎΡΡ‚ΡŒ лСксСм. ЛСксСмы - это ΠΌΠΈΠ½ΠΈΠΌΠ°Π»ΡŒΠ½Ρ‹Π΅ логичСскиС Π±Π»ΠΎΠΊΠΈ, ΠΈΠ· ΠΊΠΎΡ‚ΠΎΡ€Ρ‹Ρ… состоит исходный ΠΊΠΎΠ΄, Ρ‚Π°ΠΊΠΈΠ΅ ΠΊΠ°ΠΊ ΠΈΠ΄Π΅Π½Ρ‚ΠΈΡ„ΠΈΠΊΠ°Ρ‚ΠΎΡ€Ρ‹, ΠΎΠΏΠ΅Ρ€Π°Ρ‚ΠΎΡ€Ρ‹ ΠΈ числа.

ЛСксичСский Π°Π½Π°Π»ΠΈΠ·Π°Ρ‚ΠΎΡ€ Ρ‚Π°ΠΊΠΆΠ΅ ΠΌΠΎΠΆΠ΅Ρ‚ ΠΎΡ‚ΡΠ΅ΠΈΠ²Π°Ρ‚ΡŒ ΠΊΠΎΠΌΠΌΠ΅Π½Ρ‚Π°Ρ€ΠΈΠΈ ΠΈ ΠΏΡ€ΠΎΠ±Π΅Π»ΡŒΠ½Ρ‹Π΅ символы. Π’Π°ΠΌ понадобится Π±ΠΈΠ±Π»ΠΈΠΎΡ‚Π΅ΠΊΠ° Python, такая ΠΊΠ°ΠΊ PLY (Python Lex-Yacc), которая прСдоставляСт инструмСнты для создания лСксичСского Π°Π½Π°Π»ΠΈΠ·Π°Ρ‚ΠΎΡ€Π°.


import ply.lex as lex

# ΠžΠΏΡ€Π΅Π΄Π΅Π»Π΅Π½ΠΈΠ΅ Ρ‚ΠΎΠΊΠ΅Π½ΠΎΠ²
tokens = (
    'NUMBER',
    'PLUS',
    'MINUS',
    'TIMES',
    'DIVIDE',
)

# ΠžΠΏΡ€Π΅Π΄Π΅Π»Π΅Π½ΠΈΠ΅ рСгулярных Π²Ρ‹Ρ€Π°ΠΆΠ΅Π½ΠΈΠΉ для Ρ‚ΠΎΠΊΠ΅Π½ΠΎΠ²
t_PLUS = r'\+'
t_MINUS = r'-'
t_TIMES = r'\*'
t_DIVIDE = r'/'

# ΠžΠ±Ρ€Π°Π±ΠΎΡ‚ΠΊΠ° чисСл
def t_NUMBER(t):
    r'\d+'
    t.value = int(t.value)
    return t

# ΠŸΡ€Π°Π²ΠΈΠ»Π° игнорирования ΠΏΡ€ΠΎΠ±Π΅Π»ΠΎΠ² ΠΈ табуляций
t_ignore = ' \t'

# ΠžΠ±Ρ€Π°Π±ΠΎΡ‚ΠΊΠ° ошибок
def t_error(t):
    print("ΠΠ΅Ρ€Π°Π·Ρ€Π΅ΡˆΠ΅Π½Π½Ρ‹ΠΉ символ '%s'" % t.value[0])
    t.lexer.skip(1)

# Π‘ΠΎΠ·Π΄Π°Π½ΠΈΠ΅ лСксичСского Π°Π½Π°Π»ΠΈΠ·Π°Ρ‚ΠΎΡ€Π°
lexer = lex.lex()

# ВСстированиС лСксичСского Π°Π½Π°Π»ΠΈΠ·Π°Ρ‚ΠΎΡ€Π°

data = '''
3 + 4 * 2 - 1
'''

lexer.input(data)

while True:
    tok = lexer.token()
    if not tok:
        break
    print(tok)
    

Π¨Π°Π³ 3: БинтаксичСский Π°Π½Π°Π»ΠΈΠ·

БинтаксичСский Π°Π½Π°Π»ΠΈΠ·Π°Ρ‚ΠΎΡ€ (ΠΈΠ»ΠΈ парсСр) ΠΏΡ€Π΅ΠΎΠ±Ρ€Π°Π·ΡƒΠ΅Ρ‚ ΠΏΠΎΡΠ»Π΅Π΄ΠΎΠ²Π°Ρ‚Π΅Π»ΡŒΠ½ΠΎΡΡ‚ΡŒ лСксСм Π² структуру Π΄Π°Π½Π½Ρ‹Ρ…, которая прСдставляСт ΡΠΈΠ½Ρ‚Π°ΠΊΡΠΈΡ‡Π΅ΡΠΊΡƒΡŽ структуру исходного ΠΊΠΎΠ΄Π°. ΠžΠ±Ρ‹Ρ‡Π½ΠΎ ΠΈΡΠΏΠΎΠ»ΡŒΠ·ΡƒΠ΅Ρ‚ΡΡ Π³Ρ€Π°ΠΌΠΌΠ°Ρ‚ΠΈΠΊΠ°, опрСдСлСнная Π½Π° ΠΏΡ€Π΅Π΄Ρ‹Π΄ΡƒΡ‰Π΅ΠΌ шагС.

Π’Π°ΠΌ понадобится инструмСнт для Π³Π΅Π½Π΅Ρ€Π°Ρ†ΠΈΠΈ синтаксичСского Π°Π½Π°Π»ΠΈΠ·Π°Ρ‚ΠΎΡ€Π° Π½Π° основС Π³Ρ€Π°ΠΌΠΌΠ°Ρ‚ΠΈΠΊΠΈ. НапримСр, Π²Ρ‹ ΠΌΠΎΠΆΠ΅Ρ‚Π΅ ΠΈΡΠΏΠΎΠ»ΡŒΠ·ΠΎΠ²Π°Ρ‚ΡŒ Π±ΠΈΠ±Π»ΠΈΠΎΡ‚Π΅ΠΊΡƒ PLY для создания синтаксичСского Π°Π½Π°Π»ΠΈΠ·Π°Ρ‚ΠΎΡ€Π° Π½Π° языкС Python.


import ply.yacc as yacc

# ΠžΠΏΡ€Π΅Π΄Π΅Π»Π΅Π½ΠΈΠ΅ Π³Ρ€Π°ΠΌΠΌΠ°Ρ‚ΠΈΠΊΠΈ
def p_expression_plus(p):
    'expression : expression PLUS term'
    p[0] = p[1] + p[3]

def p_expression_minus(p):
    'expression : expression MINUS term'
    p[0] = p[1] - p[3]

def p_expression_term(p):
    'expression : term'
    p[0] = p[1]

def p_term_times(p):
    'term : term TIMES factor'
    p[0] = p[1] * p[3]

def p_term_divide(p):
    'term : term DIVIDE factor'
    p[0] = p[1] / p[3]

def p_term_factor(p):
    'term : factor'
    p[0] = p[1]

def p_factor_number(p):
    'factor : NUMBER'
    p[0] = p[1]

# ΠžΠΏΡ€Π΅Π΄Π΅Π»Π΅Π½ΠΈΠ΅ ошибки Π² синтаксисС
def p_error(p):
    print("Ошибка Π² синтаксисС")

# Π‘ΠΎΠ·Π΄Π°Π½ΠΈΠ΅ синтаксичСского Π°Π½Π°Π»ΠΈΠ·Π°Ρ‚ΠΎΡ€Π°
parser = yacc.yacc()

# ΠŸΠΎΠ»ΡƒΡ‡Π΅Π½ΠΈΠ΅ Ρ€Π΅Π·ΡƒΠ»ΡŒΡ‚Π°Ρ‚Π° Ρ€Π°Π·Π±ΠΎΡ€Π°
result = parser.parse('3 + 4 * 2 - 1')

print(result)
    

Π¨Π°Π³ 4: ГСнСрация ΠΏΡ€ΠΎΠΌΠ΅ΠΆΡƒΡ‚ΠΎΡ‡Π½ΠΎΠ³ΠΎ ΠΊΠΎΠ΄Π°

ПослС ΡƒΡΠΏΠ΅ΡˆΠ½ΠΎΠ³ΠΎ синтаксичСского Π°Π½Π°Π»ΠΈΠ·Π° Π²Ρ‹ ΠΌΠΎΠΆΠ΅Ρ‚Π΅ Π³Π΅Π½Π΅Ρ€ΠΈΡ€ΠΎΠ²Π°Ρ‚ΡŒ ΠΏΡ€ΠΎΠΌΠ΅ΠΆΡƒΡ‚ΠΎΡ‡Π½Ρ‹ΠΉ ΠΊΠΎΠ΄. ΠŸΡ€ΠΎΠΌΠ΅ΠΆΡƒΡ‚ΠΎΡ‡Π½Ρ‹ΠΉ ΠΊΠΎΠ΄ прСдставляСт собой абстрактноС прСдставлСниС исходного ΠΊΠΎΠ΄Π°, ΠΊΠΎΡ‚ΠΎΡ€ΠΎΠ΅ Π»Π΅Π³Ρ‡Π΅ Π°Π½Π°Π»ΠΈΠ·ΠΈΡ€ΠΎΠ²Π°Ρ‚ΡŒ ΠΈ ΠΎΠΏΡ‚ΠΈΠΌΠΈΠ·ΠΈΡ€ΠΎΠ²Π°Ρ‚ΡŒ.

ΠŸΡ€ΠΎΠΌΠ΅ΠΆΡƒΡ‚ΠΎΡ‡Π½Ρ‹ΠΉ ΠΊΠΎΠ΄ ΠΌΠΎΠΆΠ΅Ρ‚ Π±Ρ‹Ρ‚ΡŒ прСдставлСн Π² Π²ΠΈΠ΄Π΅ Π΄Π΅Ρ€Π΅Π²Π° Ρ€Π°Π·Π±ΠΎΡ€Π° ΠΈΠ»ΠΈ трСхадрСсного ΠΊΠΎΠ΄Π°. Π’Π°ΠΌ понадобится Ρ€Π°Π·Ρ€Π°Π±ΠΎΡ‚Π°Ρ‚ΡŒ Π°Π»Π³ΠΎΡ€ΠΈΡ‚ΠΌΡ‹ для Π³Π΅Π½Π΅Ρ€Π°Ρ†ΠΈΠΈ ΠΈ ΠΎΠΏΡ‚ΠΈΠΌΠΈΠ·Π°Ρ†ΠΈΠΈ ΠΏΡ€ΠΎΠΌΠ΅ΠΆΡƒΡ‚ΠΎΡ‡Π½ΠΎΠ³ΠΎ ΠΊΠΎΠ΄Π°, ΠΎΡΠ½ΠΎΠ²Ρ‹Π²Π°ΡΡΡŒ Π½Π° синтаксичСском Π°Π½Π°Π»ΠΈΠ·Π΅.

Π¨Π°Π³ 5: ΠžΠΏΡ‚ΠΈΠΌΠΈΠ·Π°Ρ†ΠΈΡ ΠΏΡ€ΠΎΠΌΠ΅ΠΆΡƒΡ‚ΠΎΡ‡Π½ΠΎΠ³ΠΎ ΠΊΠΎΠ΄Π°

ПослС Π³Π΅Π½Π΅Ρ€Π°Ρ†ΠΈΠΈ ΠΏΡ€ΠΎΠΌΠ΅ΠΆΡƒΡ‚ΠΎΡ‡Π½ΠΎΠ³ΠΎ ΠΊΠΎΠ΄Π° ΠΌΠΎΠΆΠ½ΠΎ ΠΏΡ€ΠΈΡΡ‚ΡƒΠΏΠΈΡ‚ΡŒ ΠΊ Π΅Π³ΠΎ ΠΎΠΏΡ‚ΠΈΠΌΠΈΠ·Π°Ρ†ΠΈΠΈ. ΠžΠΏΡ‚ΠΈΠΌΠΈΠ·Π°Ρ†ΠΈΡ Π½Π°ΠΏΡ€Π°Π²Π»Π΅Π½Π° Π½Π° ΡƒΠ»ΡƒΡ‡ΡˆΠ΅Π½ΠΈΠ΅ ΠΏΡ€ΠΎΠΈΠ·Π²ΠΎΠ΄ΠΈΡ‚Π΅Π»ΡŒΠ½ΠΎΡΡ‚ΠΈ ΠΈ эффСктивности Π³Π΅Π½Π΅Ρ€ΠΈΡ€ΡƒΠ΅ΠΌΠΎΠ³ΠΎ ΠΊΠΎΠ΄Π°.

БущСствуСт мноТСство ΠΎΠΏΡ‚ΠΈΠΌΠΈΠ·Π°Ρ†ΠΈΠΎΠ½Π½Ρ‹Ρ… Ρ‚Π΅Ρ…Π½ΠΈΠΊ, Ρ‚Π°ΠΊΠΈΡ… ΠΊΠ°ΠΊ устранСниС Π»ΠΈΡˆΠ½ΠΈΡ… вычислСний, сокращСниС числа ΠΎΠΏΠ΅Ρ€Π°Ρ†ΠΈΠΉ, устранСниС дублирования ΠΊΠΎΠ΄Π° ΠΈ Ρ‚.Π΄. Π’Ρ‹ ΠΌΠΎΠΆΠ΅Ρ‚Π΅ ΠΈΠ·ΡƒΡ‡ΠΈΡ‚ΡŒ Ρ€Π°Π·Π»ΠΈΡ‡Π½Ρ‹Π΅ Π°Π»Π³ΠΎΡ€ΠΈΡ‚ΠΌΡ‹ ΠΎΠΏΡ‚ΠΈΠΌΠΈΠ·Π°Ρ†ΠΈΠΈ ΠΈ ΠΏΡ€ΠΈΠΌΠ΅Π½ΠΈΡ‚ΡŒ ΠΈΡ… ΠΊ ΠΏΡ€ΠΎΠΌΠ΅ΠΆΡƒΡ‚ΠΎΡ‡Π½ΠΎΠΌΡƒ ΠΊΠΎΠ΄Ρƒ.

Π¨Π°Π³ 6: ГСнСрация машинного ΠΊΠΎΠ΄Π°

ПослСдний шаг Π² создании компилятора - гСнСрация машинного ΠΊΠΎΠ΄Π°. ΠœΠ°ΡˆΠΈΠ½Π½Ρ‹ΠΉ ΠΊΠΎΠ΄ - это исполняСмый ΠΊΠΎΠ΄, ΠΊΠΎΡ‚ΠΎΡ€Ρ‹ΠΉ ΠΌΠΎΠΆΠ΅Ρ‚ Π±Ρ‹Ρ‚ΡŒ Π·Π°ΠΏΡƒΡ‰Π΅Π½ Π½Π° ΠΊΠΎΠ½ΠΊΡ€Π΅Ρ‚Π½ΠΎΠΉ Π°ΠΏΠΏΠ°Ρ€Π°Ρ‚Π½ΠΎΠΉ ΠΏΠ»Π°Ρ‚Ρ„ΠΎΡ€ΠΌΠ΅.

Π’Π°ΠΌ понадобится Π·Π½Π°Π½ΠΈΠ΅ Π°Ρ€Ρ…ΠΈΡ‚Π΅ΠΊΡ‚ΡƒΡ€Ρ‹ Ρ†Π΅Π»Π΅Π²ΠΎΠΉ ΠΏΠ»Π°Ρ‚Ρ„ΠΎΡ€ΠΌΡ‹, Ρ‡Ρ‚ΠΎΠ±Ρ‹ Π³Π΅Π½Π΅Ρ€ΠΈΡ€ΠΎΠ²Π°Ρ‚ΡŒ ΠΏΡ€Π°Π²ΠΈΠ»ΡŒΠ½Ρ‹ΠΉ ΠΌΠ°ΡˆΠΈΠ½Π½Ρ‹ΠΉ ΠΊΠΎΠ΄. Π’Ρ‹ ΠΌΠΎΠΆΠ΅Ρ‚Π΅ ΠΈΡΠΏΠΎΠ»ΡŒΠ·ΠΎΠ²Π°Ρ‚ΡŒ ΡΠΏΠ΅Ρ†ΠΈΠ°Π»ΡŒΠ½Ρ‹Π΅ Π±ΠΈΠ±Π»ΠΈΠΎΡ‚Π΅ΠΊΠΈ ΠΈΠ»ΠΈ инструмСнты, Ρ‚Π°ΠΊΠΈΠ΅ ΠΊΠ°ΠΊ LLVM ΠΈΠ»ΠΈ GCC, для Π³Π΅Π½Π΅Ρ€Π°Ρ†ΠΈΠΈ машинного ΠΊΠΎΠ΄Π° ΠΈΠ· ΠΏΡ€ΠΎΠΌΠ΅ΠΆΡƒΡ‚ΠΎΡ‡Π½ΠΎΠ³ΠΎ ΠΊΠΎΠ΄Π°.

Π’Ρ‹Π²ΠΎΠ΄

Π‘ΠΎΠ·Π΄Π°Π½ΠΈΠ΅ собствСнного компилятора Π½Π° Python - это слоТноС, Π½ΠΎ Π²ΠΎΠ»Π½ΡƒΡŽΡ‰Π΅Π΅ Π·Π°Π΄Π°Π½ΠΈΠ΅. Π’ этой ΡΡ‚Π°Ρ‚ΡŒΠ΅ ΠΌΡ‹ рассмотрСли основныС шаги, Π½Π΅ΠΎΠ±Ρ…ΠΎΠ΄ΠΈΠΌΡ‹Π΅ для создания компилятора: ΠΎΠΏΡ€Π΅Π΄Π΅Π»Π΅Π½ΠΈΠ΅ Π³Ρ€Π°ΠΌΠΌΠ°Ρ‚ΠΈΠΊΠΈ, лСксичСский ΠΈ синтаксичСский Π°Π½Π°Π»ΠΈΠ·, гСнСрация ΠΏΡ€ΠΎΠΌΠ΅ΠΆΡƒΡ‚ΠΎΡ‡Π½ΠΎΠ³ΠΎ ΠΊΠΎΠ΄Π°, оптимизация ΠΈ гСнСрация машинного ΠΊΠΎΠ΄Π°.

УспСшноС написаниС компилятора Ρ‚Ρ€Π΅Π±ΡƒΠ΅Ρ‚ Π³Π»ΡƒΠ±ΠΎΠΊΠΎΠ³ΠΎ понимания языка программирования ΠΈ Π°Π»Π³ΠΎΡ€ΠΈΡ‚ΠΌΠΎΠ², поэтому Π½Π΅ ΡΡ‚Π΅ΡΠ½ΡΠΉΡ‚Π΅ΡΡŒ ΡƒΡ‡ΠΈΡ‚ΡŒΡΡ ΠΈ ΠΈΡΡΠ»Π΅Π΄ΠΎΠ²Π°Ρ‚ΡŒ Π΄ΠΎΠΏΠΎΠ»Π½ΠΈΡ‚Π΅Π»ΡŒΠ½Ρ‹Π΅ рСсурсы, Ρ‚Π°ΠΊΠΈΠ΅ ΠΊΠ°ΠΊ ΠΊΠ½ΠΈΠ³ΠΈ ΠΈ ΠΎΠ½Π»Π°ΠΉΠ½-курсы. Π£Π΄Π°Ρ‡ΠΈ Π² вашСм ΠΏΡƒΡ‚Π΅ΡˆΠ΅ΡΡ‚Π²ΠΈΠΈ Π² ΠΌΠΈΡ€ компиляторов!

Π’ΠΈΠ΄Π΅ΠΎ ΠΏΠΎ Ρ‚Π΅ΠΌΠ΅

Написал язык программирования с нуля. Как Ρ€Π°Π±ΠΎΡ‚Π°Π΅Ρ‚ компилятор ΠΈ прСпроцСссор - IT_школьник.

Winderton / Написал нСсколько Π―Π·Ρ‹ΠΊΠΎΠ² ΠŸΡ€ΠΎΠ³Ρ€Π°ΠΌΠΌΠΈΡ€ΠΎΠ²Π°Π½ΠΈΡ, Π²ΠΎΡ‚ Ρ‡Ρ‚ΠΎ я ΡƒΠ·Π½Π°Π»

Π‘ΠΎΠ·Π΄Π°Π΅ΠΌ свой Π―Π—Π«Πš ΠŸΠ ΠžΠ“Π ΠΠœΠœΠ˜Π ΠžΠ’ΠΠΠ˜Π―. ЛСксСр, ΠŸΠ°Ρ€ΡΠ΅Ρ€, АбстрактноС синтаксичСскоС Π΄Π΅Ρ€Π΅Π²ΠΎ (AST)

ΠŸΠΎΡ…ΠΎΠΆΠΈΠ΅ ΡΡ‚Π°Ρ‚ΡŒΠΈ:

πŸ” Как ΠΈΠ·Π±Π°Π²ΠΈΡ‚ΡŒΡΡ ΠΎΡ‚ ошибки None Π² Python: ПолноС руководство с простыми шагами

πŸ” Как ΠΎΠΏΡ€Π΅Π΄Π΅Π»ΠΈΡ‚ΡŒ ΠΏΠΎΠ΄Π»ΠΈΠ½Π½ΠΎΡΡ‚ΡŒ ΠΊΠΎΠΆΠΈ ΠΏΠΈΡ‚ΠΎΠ½Π°? 🐍 Π£Π·Π½Π°ΠΉΡ‚Π΅ сСйчас!

🐍 Как Π·Π°Π²Π΅Ρ€Π½ΡƒΡ‚ΡŒ python ΠΏΡ€ΠΈΠ»ΠΎΠΆΠ΅Π½ΠΈΠ΅ Π² Docker - ΠŸΠΎΠ»Π΅Π·Π½Ρ‹Π΅ совСты ΠΈ инструкции

πŸ“ Как ΡΠΎΠ·Π΄Π°Ρ‚ΡŒ свой собствСнный компилятор Π½Π° Python: ΠΏΠΎΠ΄Ρ€ΠΎΠ±Π½ΠΎΠ΅ руководство 🐍

πŸ”Ž Как ΡΠΎΠ·Π΄Π°Ρ‚ΡŒ класс Π² Python: ΠΏΠΎΠ΄Ρ€ΠΎΠ±Π½ΠΎΠ΅ руководство для Π½Π°Ρ‡ΠΈΠ½Π°ΡŽΡ‰ΠΈΡ…

πŸ“š Как ΡΠΎΡ…Ρ€Π°Π½ΠΈΡ‚ΡŒ ΡΠ»ΠΎΠ²Π°Ρ€ΡŒ Π² Ρ„Π°ΠΉΠ» python: простой ΠΈ понятный ΠΌΠ΅Ρ‚ΠΎΠ΄

πŸ”’ Как Ρ€Π°ΡΡΡ‡ΠΈΡ‚Π°Ρ‚ΡŒ Ρ„Π°ΠΊΡ‚ΠΎΡ€ΠΈΠ°Π» Π² ΠΏΠΈΡ‚ΠΎΠ½Π΅? 🐍 ΠŸΡ€ΠΎΡΡ‚ΠΎΠΉ способ πŸ‘¨β€πŸ’»