AskOverflow.Dev

AskOverflow.Dev Logo AskOverflow.Dev Logo

AskOverflow.Dev Navigation

  • 主页
  • 系统&网络
  • Ubuntu
  • Unix
  • DBA
  • Computer
  • Coding
  • LangChain

Mobile menu

Close
  • 主页
  • 系统&网络
    • 最新
    • 热门
    • 标签
  • Ubuntu
    • 最新
    • 热门
    • 标签
  • Unix
    • 最新
    • 标签
  • DBA
    • 最新
    • 标签
  • Computer
    • 最新
    • 标签
  • Coding
    • 最新
    • 标签
主页 / dba / 问题 / 651
Accepted
tmow
tmow
Asked: 2011-01-18 04:28:04 +0800 CST2011-01-18 04:28:04 +0800 CST 2011-01-18 04:28:04 +0800 CST

在 DB2 SQL 中模拟类似 REGEXP 的行为

  • 772

我在stackoverflow上发布了相同的内容(请告诉我是否必须删除一个)。

我正在开发一个 DB2 数据库,据我所知,不支持 regexp(没有其他库)。

所以我无法实现类似于本文“将正则表达式匹配的力量带入 SQL ”中所解释的内容

你知道我是否可以用 SQL 语句“模拟”这样的正则表达式吗?

^a[aofdmep]{1}[az]{1}[a-z0-9]{4}[sidbfkfpo]{1}

编辑

在上述假设中,我发现我的情况可以接受WHERE Like 谓词:

WHERE USER_NAME NOT LIKE 'a_______'

但这是不安全的,并且不包括我没有可以匹配的固定字符的其他情况。

db2 regular-expression
  • 6 6 个回答
  • 23876 Views

6 个回答

  • Voted
  1. mustaccio
    2014-10-18T08:22:02+08:002014-10-18T08:22:02+08:00

    既然这个老问题已经被挖掘出来了,我会提到你可以使用 DB2 中内置的 XQuery 支持来进行正则表达式匹配,类似于

    select whatever
    from users
    where
       xmlcast(
         xmlquery('fn:matches($USER_NAME,"^a[aofdmep][a-z][a-z0-9]{4}[sidbfkfpo]")') 
         as integer) = 1
    

    XMLQUERYmatches上面针对该列调用 XQuery函数USER_NAME。结果是 XML boolean,因此XMLCAST用于将其转换为 SQL 数据类型。

    • 12
  2. Best Answer
    Joe
    2011-01-18T06:18:52+08:002011-01-18T06:18:52+08:00

    首先,{1}s 是多余的,所以它实际上只是:

    ^[aofdmep][a-z][a-z0-9]{4}a[sidbfkfpo]
    

    这实际上是一个非常简单的模式......它只是查看字符串的前 8 个字符是什么,并且它始终是一个固定长度的字符串,因此您可以构建一个包含所有排列的表,然后执行以下操作:

    WHERE SUBSTR(string_to_match, 1, 8) IN (
      SELECT valid_prefixes FROM table_of_things_to_match
    )
    

    不幸的是,它是 7*26*36^4*9 ... 27.5 亿个可能的组合,但仍然是固定字符串,所以你可以这样做:

    WHERE SUBSTR(string_to_match, 1, 1) IN ('a','o','f','d','m','e','p')
      AND SUBSTR(string_to_match, 2, 1) IN ('a','b','c','d' ... 'z')
      AND SUBSTR(string_to_match, 3, 1) IN ('a','b','c','d' ... 'z','0','1' ... '9')
      AND SUBSTR(string_to_match, 4, 1) IN ('a','b','c','d' ... 'z','0','1' ... '9')
      AND SUBSTR(string_to_match, 5, 1) IN ('a','b','c','d' ... 'z','0','1' ... '9')
      AND SUBSTR(string_to_match, 6, 1) IN ('a','b','c','d' ... 'z','0','1' ... '9')
      AND SUBSTR(string_to_match, 7, 1) = 'a'
      AND SUBSTR(string_to_match, 8, 1) IN ('s','i','d','b','f','k','p','o')
    

    (当然是填写...位)

    哎呀,f最后一个字符类中有两个 s,所以只有 24.5 亿个排列。

    我不会假装它会很快......它可能不会很快,但它会给你你正在寻找的模式。如果你经常这样做,我可能会建立一个字符表,这样你就有一种简单的方法来选择字母/数字或字母数字。

    • 11
  3. Leigh Riffel
    2011-01-18T10:31:06+08:002011-01-18T10:31:06+08:00
    SELECT * FROM
       (SELECT 'afr923zs' MyString FROM SYSIBM.SYSDUMMY1)
    WHERE substr(MyString,1,1) = 'a' 
    AND   substr(MyString,2,1) IN ('a','o','f','d','m','e','p')
    AND   substr(MyString,3,1) BETWEEN 'a' AND 'z'
    AND  (substr(MyString,4,1) BETWEEN 'a' AND 'z' 
       OR substr(MyString,4,1) BETWEEN '0' AND '9')
    AND  (substr(MyString,5,1) BETWEEN 'a' AND 'z' 
       OR substr(MyString,5,1) BETWEEN '0' AND '9')
    AND  (substr(MyString,6,1) BETWEEN 'a' AND 'z' 
       OR substr(MyString,6,1) BETWEEN '0' AND '9')
    AND  (substr(MyString,7,1) BETWEEN 'a' AND 'z' 
       OR substr(MyString,7,1) BETWEEN '0' AND '9')
    AND   substr(MyString,8,1) IN ('s','i','d','b','f','k','p','o');
    
    • 6
  4. dbenham
    2014-10-18T06:28:19+08:002014-10-18T06:28:19+08:00

    基于 Leigh Riffel 和 Joe 的回答,当您有很长的单个字符列表或有多个字符范围时,您可能会考虑使用 LIKE。

    SELECT *
      FROM (SELECT 'afr923zs' MyString FROM SYSIBM.SYSDUMMY1) T
     WHERE substr(MyString,1,1) = 'a'
       AND 'aofdmep' like '%'||substr(MyString,2,1)||'%'
       AND substr(MyString,3,1) BETWEEN 'a' AND 'z'
       AND 'abcdefghijklmnopqrstuvwxyz0123456789' like '%'||substr(MyString,4,1)||'%'
       AND 'abcdefghijklmnopqrstuvwxyz0123456789' like '%'||substr(MyString,5,1)||'%'
       AND 'abcdefghijklmnopqrstuvwxyz0123456789' like '%'||substr(MyString,6,1)||'%'
       AND 'abcdefghijklmnopqrstuvwxyz0123456789' like '%'||substr(MyString,7,1)||'%'
       AND 'sidbfkpo' like '%'||substr(MyString,8,1)||'%'
    ;
    

    由于您多次使用相同的字符列表,您还可以考虑使用 CROSS JOINed 常量列。

    SELECT *
      FROM (SELECT 'afr923zs' MyString FROM SYSIBM.SYSDUMMY1) T
      CROSS JOIN (SELECT 'abcdefghijklmnopqrstuvwxyz0123456789' alphanum FROM SYSIBM.SYSDUMMY1) T2
     WHERE substr(MyString,1,1) = 'a'
       AND 'aofdmep' like '%'||substr(MyString,2,1)||'%'
       AND substr(MyString,3,1) BETWEEN 'a' AND 'z'
       AND alphanum like '%'||substr(MyString,4,1)||'%'
       AND alphanum like '%'||substr(MyString,5,1)||'%'
       AND alphanum like '%'||substr(MyString,6,1)||'%'
       AND alphanum like '%'||substr(MyString,7,1)||'%'
       AND 'sidbfkpo' like '%'||substr(MyString,8,1)||'%'
    ;
    

    您的示例不需要,但 CROSS JOINed “表”可以定义多个命名字符类列。

    • 2
  5. mikrom
    2015-06-22T23:35:23+08:002015-06-22T23:35:23+08:00

    REGEXP_LIKE 现在在 DB2 for iSeries 中可用 - 请参阅: http ://www.itjungle.com/fhg/fhg051915-story01.html

    • 2
  6. Aidanh
    2015-12-18T04:03:38+08:002015-12-18T04:03:38+08:00

    在 DB2 for z/OS 中,SQL 将包括 PASSING,如下所示

    select whatever
    from users
    where
       xmlcast(
         xmlquery('fn:matches($USER_NAME,"^a[aofdmep][a-z][a-z0-9]{4}[sidbfkfpo]")'
          PASSING USER as "USER_NAME") 
         as integer) = 1
    
    • 0

相关问题

  • z/OS 上 DB2 v9 上的 BLOB

  • 解释计划中的 HSJOIN 是什么意思?

  • 如何使用正则表达式查询名称?

Sidebar

Stats

  • 问题 205573
  • 回答 270741
  • 最佳答案 135370
  • 用户 68524
  • 热门
  • 回答
  • Marko Smith

    你如何mysqldump特定的表?

    • 4 个回答
  • Marko Smith

    您如何显示在 Oracle 数据库上执行的 SQL?

    • 2 个回答
  • Marko Smith

    如何选择每组的第一行?

    • 6 个回答
  • Marko Smith

    使用 psql 列出数据库权限

    • 10 个回答
  • Marko Smith

    我可以查看在 SQL Server 数据库上运行的历史查询吗?

    • 6 个回答
  • Marko Smith

    如何在 PostgreSQL 中使用 currval() 来获取最后插入的 id?

    • 10 个回答
  • Marko Smith

    如何在 Mac OS X 上运行 psql?

    • 11 个回答
  • Marko Smith

    如何从 PostgreSQL 中的选择查询中将值插入表中?

    • 4 个回答
  • Marko Smith

    如何使用 psql 列出所有数据库和表?

    • 7 个回答
  • Marko Smith

    将数组参数传递给存储过程

    • 12 个回答
  • Martin Hope
    Manuel Leduc PostgreSQL 多列唯一约束和 NULL 值 2011-12-28 01:10:21 +0800 CST
  • Martin Hope
    markdorison 你如何mysqldump特定的表? 2011-12-17 12:39:37 +0800 CST
  • Martin Hope
    Stuart Blackler 什么时候应该将主键声明为非聚集的? 2011-11-11 13:31:59 +0800 CST
  • Martin Hope
    pedrosanta 使用 psql 列出数据库权限 2011-08-04 11:01:21 +0800 CST
  • Martin Hope
    Jonas 如何使用 psql 对 SQL 查询进行计时? 2011-06-04 02:22:54 +0800 CST
  • Martin Hope
    Jonas 如何从 PostgreSQL 中的选择查询中将值插入表中? 2011-05-28 00:33:05 +0800 CST
  • Martin Hope
    Jonas 如何使用 psql 列出所有数据库和表? 2011-02-18 00:45:49 +0800 CST
  • Martin Hope
    BrunoLM Guid vs INT - 哪个更好作为主键? 2011-01-05 23:46:34 +0800 CST
  • Martin Hope
    bernd_k 什么时候应该使用唯一约束而不是唯一索引? 2011-01-05 02:32:27 +0800 CST
  • Martin Hope
    Patrick 如何优化大型数据库的 mysqldump? 2011-01-04 13:13:48 +0800 CST

热门标签

sql-server mysql postgresql sql-server-2014 sql-server-2016 oracle sql-server-2008 database-design query-performance sql-server-2017

Explore

  • 主页
  • 问题
    • 最新
    • 热门
  • 标签
  • 帮助

Footer

AskOverflow.Dev

关于我们

  • 关于我们
  • 联系我们

Legal Stuff

  • Privacy Policy

Language

  • Pt
  • Server
  • Unix

© 2023 AskOverflow.DEV All Rights Reserve