Oracle
 sql >> Cơ Sở Dữ Liệu >  >> RDS >> Oracle

Tại sao một bộ định lượng không tham lam đôi khi không hoạt động trong Oracle regex?

Đó là một BUG!

Bạn đúng rằng trong Perl, 'A=1,B=2,C=3,' =~ /.*B=.*?,/; print $& bản in A=1,B=2,

Những gì bạn đã vấp phải là một lỗi vẫn tồn tại trong Cơ sở dữ liệu Oracle 11g R2. Nếu cùng một nguyên tử biểu thức chính quy giống hệt nhau (bao gồm bộ định lượng nhưng không bao gồm công cụ sửa đổi độ tham) xuất hiện hai lần trong một biểu thức chính quy, thì cả hai lần xuất hiện sẽ có độ tham được chỉ ra bởi lần xuất hiện đầu tiên bất kể độ tham được chỉ định bởi lần thứ hai. Đây là một lỗi đã được chứng minh rõ ràng bởi các kết quả này (ở đây, "nguyên tử biểu thức chính quy giống hệt nhau" là [^B]* ):

SQL> SELECT regexp_substr('A=1,B=2,C=3,', '[^B]*B=[^Bx]*?,') as good FROM dual;

GOOD
--------
A=1,B=2,

SQL> SELECT regexp_substr('A=1,B=2,C=3,', '[^B]*B=[^B]*?,') as bad FROM dual;

BAD
-----------
A=1,B=2,C=3,

Sự khác biệt duy nhất giữa hai biểu thức chính quy là biểu thức "tốt" loại trừ 'x' là một đối sánh có thể có trong danh sách đối sánh thứ hai. Vì 'x' không xuất hiện trong chuỗi mục tiêu, việc loại trừ nó sẽ không tạo ra sự khác biệt nào, nhưng như bạn có thể thấy, việc loại bỏ 'x' sẽ tạo ra sự khác biệt lớn. Đó phải là một lỗi.

Dưới đây là một số ví dụ khác từ Oracle 11.2:( SQL Fiddle với nhiều ví dụ hơn nữa )

SELECT regexp_substr('A=1,B=2,C=3,', '.*B=.*?,')  FROM dual; =>  A=1,B=2,C=3,
SELECT regexp_substr('A=1,B=2,C=3,', '.*B=.*,')   FROM dual; =>  A=1,B=2,C=3,
SELECT regexp_substr('A=1,B=2,C=3,', '.*?B=.*?,') FROM dual; =>  A=1,B=2,
SELECT regexp_substr('A=1,B=2,C=3,', '.*?B=.*,')  FROM dual; =>  A=1,B=2,
-- Changing second operator from * to +
SELECT regexp_substr('A=1,B=2,C=3,', '.*B=.+?,')  FROM dual; =>  A=1,B=2,
SELECT regexp_substr('A=1,B=2,C=3,', '.*B=.+,')   FROM dual; =>  A=1,B=2,C=3,
SELECT regexp_substr('A=1,B=2,C=3,', '.+B=.+,')   FROM dual; =>  A=1,B=2,C=3,
SELECT regexp_substr('A=1,B=2,C=3,', '.+?B=.+,')  FROM dual; =>  A=1,B=2,

Mô hình nhất quán:lòng tham của lần xuất hiện đầu tiên được sử dụng cho lần xuất hiện thứ hai cho dù nó có nên hay không.



  1. Database
  2.   
  3. Mysql
  4.   
  5. Oracle
  6.   
  7. Sqlserver
  8.   
  9. PostgreSQL
  10.   
  11. Access
  12.   
  13. SQLite
  14.   
  15. MariaDB
  1. Oracle SQL cho Ngày làm việc Cuối cùng của Tháng Hiện tại bao gồm các ngày lễ liên bang ở oracle

  2. Trợ giúp Truy vấn - Chuỗi trong đó mệnh đề có &ký tự

  3. Xác thực bằng khóa công khai và cx_Oracle bằng Python

  4. oracle sql select cú pháp với mệnh đề GROUP BY và HAVING

  5. ODP.NET Oracle.ManagedDataAcess lỗi ORA-12570 ngẫu nhiên