【问题标题】:How to parse quotes correctly?如何正确解析引号?
【发布时间】:2020-05-14 09:24:05
【问题描述】:

我正在使用带有 Presto 语法的 ANTLR 来解析 SQL 查询。这是我正在使用的字符串的定义:

STRING
    : '\'' ( ('\\' '\'') | ~'\'' | '\'\'' )* '\''
    ;

但是,当我有这样的查询时:

select replace(name,'\'','')
FROM table1;        

它在将 '\'',' 解析为一个字符串时搞砸了。

当我改用以下规则时:

STRING
    : '\'' ( ('\\' '\'') | ~'\'')* '\''
    ;

我没有正确解析如下查询:

SELECT * FROM table1 where col1 = 'nir''s'

这当然是一个合法的查询。

知道我怎样才能同时抓住两者吗?

谢谢, 尼尔。

【问题讨论】:

    标签: python sql antlr


    【解决方案1】:

    如果要支持\',不仅要否定单引号,还要否定反斜杠。

    类似这样的:

    STRING
        : '\'' ( '\\' '\''   // match \'
               | ~[\\']      // match anything other than \ and '
               | '\'\''      // match ''
               )* 
          '\''
        ;
    

    要考虑不同的转义字符,请执行以下操作:

    STRING
        : '\'' ( '\\' ~[\r\n] // match \ followed by any char other than a line break
               | ~[\\']       // match anything other than \ and '
               | '\'\''       // match ''
               )* 
          '\''
        ;
    

    【讨论】:

    • 我的建议是将'\'' 标记为一个标记,'nir''s' 是一个标记。这不是你想要的吗?如果是这样,请更新您的问题并明确说明您所期望的令牌。
    • @Nir99 你的问题是你的` is eaten up by '\''`,因此不被视为转义引用的一部分。这就是为什么'\'','' 被作为单个字符串来使用。 Bart 的建议解决了这个问题,并将导致 '\'','' 被解析为两个字符串(以及一个逗号和一个空格),这正是你想要的。
    • @brat,很抱歉,我在第一次阅读时没有理解您的回答。但这正是我想要的。非常感谢!
    • 嗯,事实上我仍然对使用正则表达式的不同查询有疑问。例如,我无法正确解析以下查询,因为我没有正确解析字符串: select * from table1 where REGEXP_MATCH(col1, r'^\d{8}$')
    • 也尝试更新规则但没有成功: : '\'' ( '\\' '\'' // 匹配 \' | '\\' 'd' | ~[\\ '] // 匹配除 \ 和 ' | '\'\'' // 匹配 '' )* '\'' ;
    猜你喜欢
    • 1970-01-01
    • 2019-01-06
    • 2019-04-14
    • 2019-01-26
    • 1970-01-01
    • 1970-01-01
    • 2018-10-09
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多