Phân tích cú pháp Python AST

Phân tích cú pháp và sửa đổi cấu trúc mã chắc chắn có thể thực hiện được với sự trợ giúp của mô-đun

>>> import ast
>>> tree = ast.parse["print 'Hello Python!!'"]
>>> ast.dump[tree]
"Module[body=[Print[dest=None, values=[Str[s='Hello Python!!']], nl=True]]]"
4 và tôi sẽ trình bày nó trong một ví dụ trong giây lát. Tuy nhiên, không thể ghi lại mã nguồn đã sửa đổi chỉ với mô-đun
>>> import ast
>>> tree = ast.parse["print 'Hello Python!!'"]
>>> ast.dump[tree]
"Module[body=[Print[dest=None, values=[Str[s='Hello Python!!']], nl=True]]]"
4. Có các mô-đun khác có sẵn cho công việc này, chẳng hạn như một ở đây

GHI CHÚ. Ví dụ dưới đây có thể được coi là hướng dẫn giới thiệu về cách sử dụng mô-đun

>>> import ast
>>> tree = ast.parse["print 'Hello Python!!'"]
>>> ast.dump[tree]
"Module[body=[Print[dest=None, values=[Str[s='Hello Python!!']], nl=True]]]"
4 nhưng hướng dẫn toàn diện hơn về cách sử dụng mô-đun
>>> import ast
>>> tree = ast.parse["print 'Hello Python!!'"]
>>> ast.dump[tree]
"Module[body=[Print[dest=None, values=[Str[s='Hello Python!!']], nl=True]]]"
4 có tại đây tại Hướng dẫn về rắn cây xanh và tài liệu chính thức về mô-đun
>>> import ast
>>> tree = ast.parse["print 'Hello Python!!'"]
>>> ast.dump[tree]
"Module[body=[Print[dest=None, values=[Str[s='Hello Python!!']], nl=True]]]"
4

Giới thiệu về

>>> import ast
>>> tree = ast.parse["print 'Hello Python!!'"]
>>> ast.dump[tree]
"Module[body=[Print[dest=None, values=[Str[s='Hello Python!!']], nl=True]]]"
4

>>> import ast
>>> tree = ast.parse["print 'Hello Python!!'"]
>>> exec[compile[tree, filename="", mode="exec"]]
Hello Python!!

Bạn có thể phân tích cú pháp mã python [được biểu thị bằng chuỗi] bằng cách gọi API

>>> import ast
>>> tree = ast.parse["print 'Hello Python!!'"]
>>> ast.dump[tree]
"Module[body=[Print[dest=None, values=[Str[s='Hello Python!!']], nl=True]]]"
1. Điều này trả về tay cầm cho cấu trúc Cây cú pháp trừu tượng [AST]. Điều thú vị là bạn có thể biên dịch lại cấu trúc này và thực thi nó như hình trên

Một API rất hữu ích khác là

>>> import ast
>>> tree = ast.parse["print 'Hello Python!!'"]
>>> ast.dump[tree]
"Module[body=[Print[dest=None, values=[Str[s='Hello Python!!']], nl=True]]]"
2 kết xuất toàn bộ AST ở dạng chuỗi. Nó có thể được sử dụng để kiểm tra cấu trúc cây và rất hữu ích trong việc gỡ lỗi. Ví dụ,

Trên Python 2. 7

>>> import ast
>>> tree = ast.parse["print 'Hello Python!!'"]
>>> ast.dump[tree]
"Module[body=[Print[dest=None, values=[Str[s='Hello Python!!']], nl=True]]]"

Trên Python 3. 5

>>> import ast
>>> tree = ast.parse["print ['Hello Python!!']"]
>>> ast.dump[tree]
"Module[body=[Expr[value=Call[func=Name[id='print', ctx=Load[]], args=[Str[s='Hello Python!!']], keywords=[]]]]]"

Lưu ý sự khác biệt về cú pháp cho câu lệnh in trong Python 2. 7 so với. Trăn 3. 5 và sự khác biệt về loại nút AST trong các cây tương ứng

Cách sửa đổi mã bằng cách sử dụng

>>> import ast
>>> tree = ast.parse["print 'Hello Python!!'"]
>>> ast.dump[tree]
"Module[body=[Print[dest=None, values=[Str[s='Hello Python!!']], nl=True]]]"
4

Bây giờ, hãy xem một ví dụ về sửa đổi mã python bằng mô-đun

>>> import ast
>>> tree = ast.parse["print 'Hello Python!!'"]
>>> ast.dump[tree]
"Module[body=[Print[dest=None, values=[Str[s='Hello Python!!']], nl=True]]]"
4. Công cụ chính để sửa đổi cấu trúc AST là lớp
>>> import ast
>>> tree = ast.parse["print 'Hello Python!!'"]
>>> ast.dump[tree]
"Module[body=[Print[dest=None, values=[Str[s='Hello Python!!']], nl=True]]]"
5. Bất cứ khi nào một người cần sửa đổi AST, anh ấy/cô ấy cần phân lớp từ nó và viết [các] Chuyển đổi nút tương ứng

Ví dụ của chúng ta, hãy thử viết một tiện ích đơn giản để chuyển đổi các câu lệnh in của Python 2 thành lệnh gọi hàm của Python 3

In sao kê sang tiện ích chuyển đổi cuộc gọi Fun. in2to3. py

#!/usr/bin/env python
'''
This utility converts the python [2.7] statements to Python 3 alike function calls before running the code.

USAGE:
     python print2to3.py 
'''
import ast
import sys

class P2to3[ast.NodeTransformer]:
    def visit_Print[self, node]:
        new_node = ast.Expr[value=ast.Call[func=ast.Name[id='print', ctx=ast.Load[]],
            args=node.values,
            keywords=[], starargs=None, kwargs=None]]
        ast.copy_location[new_node, node]
        return new_node

def main[filename=None]:
    if not filename:
        return

    with open[filename, 'r'] as fp:
        data = fp.readlines[]
    data = ''.join[data]
    tree = ast.parse[data]

    print "Converting python 2 print statements to Python 3 function calls"
    print "-" * 35
    P2to3[].visit[tree]
    ast.fix_missing_locations[tree]
    # print ast.dump[tree]

    exec[compile[tree, filename="p23", mode="exec"]]

if __name__ == '__main__':
    if len[sys.argv] >> import ast
>>> tree = ast.parse["print 'Hello Python!!'"]
>>> ast.dump[tree]
"Module[body=[Print[dest=None, values=[Str[s='Hello Python!!']], nl=True]]]"
4 và trong tình huống thực tế, người ta sẽ phải xem xét tất cả các tình huống khác nhau, chẳng hạn như
>>> import ast
>>> tree = ast.parse["print 'Hello Python!!'"]
>>> ast.dump[tree]
"Module[body=[Print[dest=None, values=[Str[s='Hello Python!!']], nl=True]]]"
7

AST là viết tắt của Abstract Syntax Tree, là một công cụ mạnh mẽ của ngôn ngữ lập trình Python. Nó cho phép chúng ta tương tác với chính mã Python và có thể sửa đổi nó

Bạn đã bao giờ nghĩ về cách mã Python được chạy chưa?

Dành cho những ai chưa biết, trình thông dịch Python chịu trách nhiệm chạy mã Python. Nó tuân theo các hướng dẫn được viết sẵn để dịch mã Python thành các hướng dẫn mà máy có thể chạy

Sau đây là quá trình chuyển đổi mã Python thành mã máy

  • Khi chúng tôi chạy mã, mã được phân tích cú pháp thành các phần nhỏ hơn được gọi là mã thông báo. Các mã thông báo này được tạo theo các hướng dẫn được xác định trước sẽ xử lý khác nhau. Ví dụ: từ khóa khác là một từ khóa khác với giá trị số như
  • Các mã thông báo được lưu trữ trong danh sách được chuyển đổi để xây dựng cây Cú pháp trừu tượng, AST. AST là tập hợp của hai hoặc nhiều nút được liên kết với nhau dựa trên ngữ pháp của ngôn ngữ Python
  • Trình biên dịch có thể tạo ra lệnh cấp thấp hơn được gọi là mã nhị phân từ AST. Code này rất chung chung để máy tính dễ chạy
  • Khi trình thông dịch nhận được mã byte giống như hướng dẫn, trình thông dịch hiện có thể chạy mã. Mã byte chịu trách nhiệm gọi hàm trong hệ điều hành, cuối cùng sẽ tương tác với CPU và bộ nhớ để chạy chương trình

Mô tả ở trên là một bản phác thảo sơ bộ về cách trình thông dịch chạy mã Python bằng AST

Chế độ biên dịch mã

Có ba chế độ có sẵn để biên dịch mã. Chúng được đưa ra dưới đây

  • exec - Chế độ này được sử dụng để thực thi mã Python bình thường
  • eval - Chế độ này được sử dụng để đánh giá biểu thức của Python và sẽ trả về kết quả sau khi đánh giá
  • single - Chế độ này hoạt động như trình bao Python thực thi một câu lệnh tại một thời điểm

Thực thi mã Python

Sử dụng mô-đun AST, chúng ta có thể chạy mã Python. Hãy hiểu ví dụ sau

Ví dụ -

đầu ra

Hello Learner! Welcome to JavaTpoint

Đánh giá biểu thức Python

Mô-đun AST cho phép chúng tôi đánh giá biểu thức Python và trả về kết quả từ biểu thức. Hãy hiểu ví dụ sau

Ví dụ -

đầu ra

>>> import ast
>>> tree = ast.parse["print 'Hello Python!!'"]
>>> ast.dump[tree]
"Module[body=[Print[dest=None, values=[Str[s='Hello Python!!']], nl=True]]]"
0

Tạo AST nhiều dòng

Trong ví dụ trước, chúng ta đã thấy AST dòng đơn và cách kết xuất chúng. Bây giờ, chúng ta sẽ tìm hiểu cách tạo AST nhiều dòng. Đầu tiên, hãy hiểu ví dụ sau

Ví dụ -

đầu ra

>>> import ast
>>> tree = ast.parse["print 'Hello Python!!'"]
>>> ast.dump[tree]
"Module[body=[Print[dest=None, values=[Str[s='Hello Python!!']], nl=True]]]"
1

NodeTransformer và NodeVisitor

Lớp NodeTransformer được sử dụng để lấy các loại khác nhau và sửa đổi theo yêu cầu của chúng tôi. Module ast cũng cung cấp lớp NodeVisitor giúp chúng ta gọi hàm visit mỗi khi lướt qua cây. Để chúng ta có thể kiểm soát nhiều hơn trên các nút, hãy hiểu ví dụ sau

Ví dụ 1

đầu ra

>>> import ast
>>> tree = ast.parse["print 'Hello Python!!'"]
>>> ast.dump[tree]
"Module[body=[Print[dest=None, values=[Str[s='Hello Python!!']], nl=True]]]"
2

Giải trình -

Trong đoạn mã trên, chúng tôi đã nhập mô-đun ast để phân tích mã. Sau đó, chúng tôi đã xác định lớp Khách truy cập kế thừa lớp NodeVisitor. Mỗi khi tìm thấy nút chuỗi;

Chúng ta cũng có thể sử dụng module khi chạy trực tiếp mã nguồn. Hãy hiểu ví dụ sau

Ví dụ - 2

đầu ra

>>> import ast
>>> tree = ast.parse["print 'Hello Python!!'"]
>>> ast.dump[tree]
"Module[body=[Print[dest=None, values=[Str[s='Hello Python!!']], nl=True]]]"
3

Giải trình -

Đoạn mã trên chuyển đổi tệp Python thành cây cú pháp trừu tượng. Sau đó, chúng tôi phân tích cây để có được thông tin hữu ích

Chúng tôi đã mở tệp Python ở chế độ đọc và sau đó tạo AST có tên là ast_tree. Sau đó, hàm parse[] đã xử lý tất cả các mã thông báo, tuân theo tất cả các quy tắc ngôn ngữ và xây dựng cấu trúc dữ liệu dạng cây bao gồm nhiều thông tin hữu ích

Cây không là gì ngoài một tập hợp các nút, trong đó một biến cây được tham chiếu đến nút "gốc". Như vậy, chúng ta có thể thăm từng nút trong cây và thực hiện các thao tác. Nhưng, trước tiên, chúng tôi truy cập từng nút và xử lý dữ liệu

Phân tích AST

Khi chúng tôi có được cây, bây giờ Trình phân tích sẽ tuân theo mẫu khách truy cập. Sử dụng lớp NodeVisitor, chúng ta có thể theo dõi bất kỳ nút nào trong Python. Chúng ta cần triển khai một phương thức visit_để truy cập một loại nút cụ thể. Trong ví dụ trước, chúng tôi đã sử dụng tập lệnh bên dưới

Ví dụ -

Mã chấp nhận tên của mô-đun và lưu trữ nó trong danh sách thống kê. Với sự trợ giúp của lớp NodeVisitor, chúng ta có thể phân tích cây

Phương thức visit[] sẽ hoạt động giống như phương thức visit_method

Sử dụng AST làm Công cụ phân tích

Sau khi mã Python biến thành mã byte, con người không thể đọc được. Nhưng nó làm cho trình thông dịch nhanh, có nghĩa là mã byte được thiết kế cho máy chứ không phải cho con người

AST bao gồm đủ thông tin có cấu trúc, giúp chúng hữu ích trong việc tìm hiểu về mã Python. Tuy nhiên, AST vẫn không thân thiện với người dùng, nhưng chúng dễ hiểu hơn nhiều so với biểu diễn mã byte

Khi nào sử dụng mô-đun Python AST?

Cây cú pháp trừu tượng khá hữu ích cho các công cụ bảo hiểm mã. Nó phân tích cú pháp mã nguồn và tìm ra các lỗi và sai sót có thể có trong mã. Nó cũng có thể sử dụng trong -

  • Nó được sử dụng như một trình thông dịch Python tùy chỉnh
  • Nó được sử dụng để phân tích mã tĩnh
  • Nó làm cho các IDE trở nên thông minh, được gọi là IntelliSense

Phần kết luận

Chúng ta đã tìm hiểu về mô-đun ast trong Python, mô-đun chịu trách nhiệm chạy mã Python. Sau đó, chúng tôi đã xây dựng cây AST từ mã Python và thực hiện phân tích trên AST bằng lớp NodeVisitor

Làm cách nào để sử dụng AST trong Python?

Ví dụ - .
nhập khẩu ast
biểu thức = '6 + 8'
mã = ast. phân tích cú pháp [biểu thức, chế độ = 'eval']
in [eval [biên dịch [mã, '', chế độ = 'eval']]]
in [ast. kết xuất [mã]]

phân tích cú pháp trong Python là gì?

Mô-đun trình phân tích cú pháp cung cấp giao diện cho trình biên dịch mã byte và trình phân tích cú pháp nội bộ của Python . Mục đích chính của giao diện này là cho phép mã Python chỉnh sửa cây phân tích cú pháp của biểu thức Python và tạo mã thực thi từ đây.

AST có được tích hợp vào Python không?

Python có thư viện mô-đun “AST”. AST [cây cú pháp trừu tượng] cung cấp cấu trúc cây cho mã nguồn của bạn [Python hoặc bất kỳ ngôn ngữ lập trình nào khác]. Trong Python, AST được biên dịch thành một đối tượng mã bằng cách sử dụng hàm “compile[]” tích hợp sẵn .

AST có phải là thư viện Python chuẩn không?

ast là một mô-đun trong thư viện chuẩn của python . Mã Python cần được chuyển đổi thành Cây cú pháp trừu tượng [AST] trước khi trở thành “mã byte”[. tệp pyc]. Tạo AST là chức năng quan trọng nhất của ast, nhưng có nhiều cách hơn để người ta có thể sử dụng mô-đun.

Chủ Đề