6

मैं एएसटी पायथन मॉड्यूल का उपयोग कर पोस्टफिक्स नोटेशन में पाइथन गणित अभिव्यक्तियों को परिवर्तित करने की कोशिश कर रहा हूं। मैं समझता हूँ कि कैसे पोस्टफ़िक्स भाव को जटिल इन्फ़िक्स गणित अभिव्यक्ति कन्वर्ट करने के लिए एक बड़ा घूँट ग आवरण के लिए भेजा जाना, कि मैं एएसटी उपयोग करने के लिए कोशिश कर रहा हूँ करने के लिए कोशिश कर रहा हूँएएसटी पायथन मॉड्यूल का उपयोग करके इंफिक्स से पोस्टफिक्स/उपसर्ग में कैसे परिवर्तित करें?

import parser 
import ast 
from math import sin, cos, tan 

formulas = [ 
    "1+2", 
    "1+2*3", 
    "1/2", 
    "(1+2)*3", 
    "sin(x)*x**2", 
    "cos(x)", 
    "True and False", 
    "sin(w*time)" 
] 


class v(ast.NodeVisitor): 

    def __init__(self): 
     self.tokens = [] 

    def f_continue(self, node): 
     super(v, self).generic_visit(node) 

    def visit_Add(self, node): 
     self.tokens.append('+') 
     self.f_continue(node) 

    def visit_And(self, node): 
     self.tokens.append('&&') 
     self.f_continue(node) 

    def visit_BinOp(self, node): 
     # print('visit_BinOp') 
     # for child in ast.iter_fields(node): 
      # print(' child %s ' % str(child)) 

     self.f_continue(node) 

    def visit_BoolOp(self, node): 
     # print('visit_BoolOp') 
     self.f_continue(node) 

    def visit_Call(self, node): 
     # print('visit_Call') 
     self.f_continue(node) 

    def visit_Div(self, node): 
     self.tokens.append('/') 
     self.f_continue(node) 

    def visit_Expr(self, node): 
     # print('visit_Expr') 
     self.f_continue(node) 

    def visit_Import(self, stmt_import): 
     for alias in stmt_import.names: 
      print('import name "%s"' % alias.name) 
      print('import object %s' % alias) 
     self.f_continue(stmt_import) 

    def visit_Load(self, node): 
     # print('visit_Load') 
     self.f_continue(node) 

    def visit_Module(self, node): 
     # print('visit_Module') 
     self.f_continue(node) 

    def visit_Mult(self, node): 
     self.tokens.append('*') 
     self.f_continue(node) 

    def visit_Name(self, node): 
     self.tokens.append(node.id) 
     self.f_continue(node) 

    def visit_NameConstant(self, node): 
     self.tokens.append(node.value) 
     self.f_continue(node) 

    def visit_Num(self, node): 
     self.tokens.append(node.n) 
     self.f_continue(node) 

    def visit_Pow(self, node): 
     self.tokens.append('pow') 
     self.f_continue(node) 

for index, f in enumerate(formulas): 
    print('{} - {:*^76}'.format(index, f)) 
    visitor = v() 
    visitor.visit(ast.parse(f)) 
    print(visitor.tokens) 
    print() 


# 0 - ************************************1+2************************************* 
# [1, '+', 2] 

# 1 - ***********************************1+2*3************************************ 
# [1, '+', 2, '*', 3] 

# 2 - ************************************1/2************************************* 
# [1, '/', 2] 

# 3 - **********************************(1+2)*3*********************************** 
# [1, '+', 2, '*', 3] 

# 4 - ********************************sin(x)*x**2********************************* 
# ['sin', 'x', '*', 'x', 'pow', 2] 

# 5 - ***********************************cos(x)*********************************** 
# ['cos', 'x'] 

# 6 - *******************************True and False******************************* 
# ['&&', True, False] 

# 7 - ********************************sin(w*time)********************************* 
# ['sin', 'w', '*', 'time'] 

: यहाँ मैं अब तक क्या मिला है मॉड्यूल।

क्या कोई यहां सलाह दे सकता है? उपरोक्त जानकारी के साथ

>>> import ast 
>>> node = ast.parse("sin(x)*x**2") 
>>> ast.dump(node) 
"Module(body=[Expr(value=BinOp(left=Call(func=Name(id='sin', ctx=Load()), args=[Name(id='x', ctx=Load())], keywords=[]), op=Mult(), right=BinOp(left=Name(id='x', ctx=Load()), op=Pow(), right=Num(n=2))))])" 

आप नोड के बच्चों के आने के क्रम में आप पोस्टफ़िक्स या उपसर्ग अभिव्यक्ति उत्पन्न करने के लिए अनुमति देता है जो बदल सकते हैं:

उत्तर

3

आप नोड्स और AST संरचना के बारे में और अधिक जानकारी प्राप्त करने के लिए ast.dump उपयोग कर सकते हैं। आदेश पोस्टफ़िक्स अभिव्यक्ति परिवर्तन visit_BinOp, visit_BoolOp और visit_Call उत्पन्न करने के लिए इतना है कि वे ऑपरेटर/समारोह से पहले बहस की यात्रा में:

def visit_BinOp(self, node): 
    self.visit(node.left) 
    self.visit(node.right) 
    self.visit(node.op) 

def visit_BoolOp(self, node): 
    for val in node.values: 
     self.visit(val) 
    self.visit(node.op) 

def visit_Call(self, node): 
    for arg in node.args: 
     self.visit(arg) 
    self.visit(node.func) 
ऊपर परिवर्तनों के साथ

आप निम्नलिखित मिल उत्पादन:

0 - ************************************1+2************************************* 

[1, 2, '+'] 

1 - ***********************************1+2*3************************************ 

[1, 2, 3, '*', '+'] 

2 - ************************************1/2************************************* 

[1, 2, '/'] 

3 - **********************************(1+2)*3*********************************** 

[1, 2, '+', 3, '*'] 

4 - ********************************sin(x)*x**2********************************* 

['x', 'sin', 'x', 2, 'pow', '*'] 

5 - ***********************************cos(x)*********************************** 

['x', 'cos'] 

6 - *******************************True and False******************************* 

[True, False, '&&'] 

7 - ********************************sin(w*time)********************************* 

['w', 'time', '*', 'sin'] 

यदि आप चाहते हैं उपसर्ग अभिव्यक्ति के बजाय बस ऑर्डर को स्वैप करें ताकि ऑपरेटर/फ़ंक्शन का दौरा किया जा सके:

def visit_BinOp(self, node): 
    self.visit(node.op) 
    self.visit(node.left) 
    self.visit(node.right) 

def visit_BoolOp(self, node): 
    self.visit(node.op) 
    for val in node.values: 
     self.visit(val) 

def visit_Call(self, node): 
    self.visit(node.func) 
    for arg in node.args: 
     self.visit(arg) 

आउटपुट:

0 - ************************************1+2************************************* 

['+', 1, 2] 

1 - ***********************************1+2*3************************************ 

['+', 1, '*', 2, 3] 

2 - ************************************1/2************************************* 

['/', 1, 2] 

3 - **********************************(1+2)*3*********************************** 

['*', '+', 1, 2, 3] 

4 - ********************************sin(x)*x**2********************************* 

['*', 'sin', 'x', 'pow', 'x', 2] 

5 - ***********************************cos(x)*********************************** 

['cos', 'x'] 

6 - *******************************True and False******************************* 

['&&', True, False] 

7 - ********************************sin(w*time)********************************* 

['sin', '*', 'w', 'time'] 
+0

आपके उत्तर के लिए बहुत बहुत धन्यवाद, मैंने इसके बारे में सोचा नहीं था, अच्छा। क्या आप कृपया थोड़ा आगे विस्तार कर सकते हैं जब आप कहते हैं कि 'यदि आप उपसर्ग नोटेशन चाहते हैं तो बस ऑर्डर को स्वैप करें ताकि ऑपरेटर/फ़ंक्शन पहले विज़िट किया जा सके।', इसका मतलब क्या है? +1 – BPL

+0

@ बीपीएल उपसर्ग अभिव्यक्ति का जोड़ा गया उदाहरण, उम्मीद है कि यह मदद करता है! – niemmi

+0

बहुत बढ़िया, धन्यवाद – BPL

संबंधित मुद्दे