IronPython: как получить имена из выражения Python? - PullRequest
1 голос
/ 02 мая 2011

У меня есть строка с выражением Python, например:

"x + y * 2 > z"

Как получить список имен, используемых в выражении?В приведенном выше примере список:

x, y, z

В Python я думаю, что я мог бы использовать модуль синтаксического анализа, но как это сделать в IronPython, где модуль синтаксического анализатора кажется недоступным?

Ответы [ 3 ]

2 голосов
/ 03 июня 2011

Эта страница может вам помочь: http://www.ironpython.info/index.php/The_IronPython_2_Parser

На ней приведен пример создания AST из выражения python с использованием базового компилятора IronPython, а затем печати имен найденных там объектов.

Я пошел дальше и применил это к вашей проблеме.Я использую IronPython 2.0.1 здесь, на случай, если вы используете более новую версию, и они что-то изменили ...

# run this with IronPython 2
import clr
clr.AddReference('IronPython')
clr.AddReference('Microsoft.Scripting')

from IronPython.Hosting import Python
from IronPython.Compiler import Parser
from IronPython.Compiler.Ast import PythonWalker
from IronPython.Compiler.Ast import NameExpression
from Microsoft.Scripting import ErrorSink
from Microsoft.Scripting import SymbolTable
from Microsoft.Scripting.Runtime import CompilerContext
from Microsoft.Scripting.Hosting.Providers import HostingHelpers


class ExpressionWalker (PythonWalker):
    def __init__(self):
        self.names = []
    def Walk(self, node):
        if isinstance(node, NameExpression):
            self.names.append(SymbolTable.IdToString(node.Name))
        return True

py = Python.CreateEngine()
src = HostingHelpers.GetSourceUnit(py.CreateScriptSourceFromString('x + y * 2 > z'))
pylc = HostingHelpers.GetLanguageContext(py)
p = Parser.CreateParser(CompilerContext(src, pylc.GetCompilerOptions(), ErrorSink.Default), pylc.Options)
ast = p.ParseFile(True)

walker = ExpressionWalker()
ast.Walk(walker)
print walker.names

Это напечатает следующее:

['x', 'y', 'z']
0 голосов
/ 03 июня 2011
print filter(lambda x: x.isalpha(), list("x + y * 2 > z"))

ИЛИ

def parse_expression(expression, operations=['+','-','*','/','%','^']):
    output = []
    tmp = None
    for x in expression:
        if x.strip() == '':
            continue
        if tmp is None:
            tmp = [x]
        elif not x in operations:
            tmp.append(x)
        else:
            output.append(''.join(tmp))
            tmp = None
    (tmp is not None and output.append(''.join(tmp)))
    return output

ИЛИ

import re
print re.findall(r'(?i)(?:[a-z0-9_]+)', ('test_1+ y__2 * c/_3')
0 голосов
/ 06 мая 2011

Вы можете использовать класс Regex .NET Framework:

import clr

clr.AddReference('System')
from System.Text.RegularExpressions import Regex

operation = "x + y * 2 > z"

regex = Regex("[a-zA-Z]+")
matches = regex.Matches("x + y * 2 > z")
result = ""
for m in matches:
    result += m.Value + ","

print result
...