gpt4 book ai didi

python - 如何有效检查使用transformString后定义的语法是否被替换?

转载 作者:行者123 更新时间:2023-12-01 07:21:02 24 4
gpt4 key购买 nike

我编写了一个 python 脚本,用于从数千个 SQL 文件中删除 RCS 关键字。基本上它使用 pyparsetransformString 来转换和剥离已知的 RCS 标签。然而这个函数是有效的,因为我无法知道transformString是否执行了ParseAction,我的脚本只是盲目地重写sql代码文件,即使扫描的文件中没有RCS关键字。

这是我的示例代码,我在其中删除了 RCS 关键字,我需要知道该操作是否找到了要替换的 token ,并且在决定写入当前文件之前实际上进行了替换。如果transformString没有进行替换,我想跳过写入文件。

from pyparsing import *
# simulate some SQL code
original_code = """
CREATE OR REPLACE FUNCTION oracle_function_name
(
p_company_code IN varchar2

)
--
RETURN number
IS

-- $Workfile: oracle_function_name.sql $
-- $Author: az $
-- $Date: 2018/11/20 $
-- $Revision: #1 $

l_rate := 0;
end if;
Close cur_rate;
--
return l_rate;
end;
/

"""
# Grammar definitions
Workfile_Grammar = ZeroOrMore('/*') + ZeroOrMore('*') + ZeroOrMore('--')+ CaselessKeyword('$Workfile:') + Word( alphas+"_"+alphas+".", alphanums+"_"+alphas+".") + CaselessKeyword('$') + LineStart()
Workfile_Grammar.setParseAction( replaceWith("") )

author_Grammar = ZeroOrMore('/*') + ZeroOrMore('*') + ZeroOrMore('--')+ CaselessKeyword('$Author:') + Word( alphas+"_"+alphas+".", alphanums+"_"+alphas+".") + CaselessKeyword('$') + LineStart()
author_Grammar.setParseAction(replaceWith(""))

date_Grammar = ZeroOrMore('/*') + ZeroOrMore('*') + ZeroOrMore('--')+ CaselessKeyword('$Date:') + Word( alphanums+"/"+alphanums+"/") + CaselessKeyword('$') + LineStart()
date_Grammar.setParseAction(replaceWith(""))

revision_Grammar = ZeroOrMore('/*') + ZeroOrMore('*') + ZeroOrMore('--')+ CaselessKeyword('$Revision:') + Word( '#'+alphanums) + CaselessKeyword('$') + LineStart()
revision_Grammar.setParseAction(replaceWith(""))

change_Grammar = ZeroOrMore('/*') + ZeroOrMore('*') + ZeroOrMore('--')+ CaselessKeyword('$Change:') + Word(alphanums) + CaselessKeyword('$') + LineStart()
change_Grammar.setParseAction(replaceWith(""))

dateTime_Grammar = ZeroOrMore('/*') + ZeroOrMore('*') + ZeroOrMore('--')+ CaselessKeyword('$Date:') + Word( alphanums+"/"+alphanums+"/") + Word(alphanums+":"+alphanums+":"+alphanums) + CaselessKeyword('$') + LineStart()
dateTime_Grammar.setParseAction(replaceWith(""))

header_Grammar = ZeroOrMore('/*') + ZeroOrMore('*') + ZeroOrMore('--')+ CaselessKeyword('$Header:') + Word( "//"+alphanums+"/"+alphas+"_"+alphas+".", alphanums+"_"+alphas+".") + CaselessKeyword('$') + LineStart()
header_Grammar.setParseAction( replaceWith("") )

postStripFile = author_Grammar.transformString(header_Grammar.transformString(dateTime_Grammar.transformString(change_Grammar.transformString(revision_Grammar.transformString(date_Grammar.transformString(Workfile_Grammar.transformString(original_code)))))))
# Is there a way to check the transFormStrings have found and removed any Grammar (RCS keywords?)

print(postStripFile)

# this is where we write postStripFile back to the original file name
# so that the files with RCS tags are stripped in place and the ones without are left in place without changes.

最佳答案

最简单的方法是比较调用 transformString 之前和之后的字符串,如果不同,则写入文件。

# combine all transformers into a single parser, so transform can be done in
# one pass
parser = (Workfile_Grammar
| date_grammar
| revision_grammar
| change_grammar
| dateTime_grammar
| header_grammar
| author_grammar
)

new_sql = parser.transformString(original_sql)
if new_sql != original_sql:
# do whatever when detecting original has been transformed

稍微更有效的方法可能是向所有表达式添加另一个解析操作,将全局变量设置为 True:

changed = False
def changes_made():
global changed
changed = True

Workfile_Grammar.setParseAction(changes_made, replaceWith(""))
...

changed = False
new_sql = parser.transformString(original_sql)
if changed:
# ... etc. ...

setParseAction 将接受成功解析后调用的多个函数。由于 changes_made 不会对解析的标记进行任何修改,因此就 pyparsing 而言,它只是一个传递。

在同一运行中多次调用 transformString 之前,您必须确保将 changes_made 重置为 False。

我个人偏好第一种方法更简单。

关于python - 如何有效检查使用transformString后定义的语法是否被替换?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/57702798/

24 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com