Как получить все вхождения подстроки между некоторыми персонажами? - PullRequest
0 голосов
/ 24 декабря 2018

То, что я пытаюсь получить, это часть текста столбца, которая находится между некоторыми символами ($$, если быть точным), но хитрость в том, что эти символы могут встречаться более двух раз (но всегда, даже если есть большечем 2, чем должно быть, как $$xxx$$ ... $$yyy$$), и мне нужно получить их отдельно.

Когда я пытаюсь это сделать, если шаблон встречается только один раз, это не проблема:

regexp_substr(txt,'\$\$(.*)\$\$',1,1,null,1)

Но допустим, что текст столбца: $$xxx$$ ... $$yyy$$

, тогда он дает мне: xxx$$ ... $$yyy

, но мне нужно два, чтобы получить их в отдельных строках, таких как:

xxx
yyy

что я не мог сделать, так как?

Ответы [ 2 ]

0 голосов
/ 24 декабря 2018

Можно также использовать CONNECT BY, чтобы «проходить» по элементам, окруженным двойными знаками доллара, возвращая данные внутри (2-я группа).Этот метод обрабатывает элементы NULL (ID 7, элемент 2), и поскольку знаки доллара используются при перемещении регулярного выражения слева направо, символы между группами не совпадают ложно.

SQL> with tbl(id, txt) as (
     select 1, '$$xxx$$' from dual union all
     select 2, '$$xxx$$ ... $$yyy$$' from dual union all
     select 3, '' from dual union all
     select 4, '$$xxx$$abc$$yyy$$' from dual union all
     select 5, '$$xxx$$ ... $$yyy$$ ... $$www$$ ... $$zzz$$' from dual union all
     select 6, '$$aaa$$$$bbb$$$$ccc$$$$ddd$$' from dual union all
     select 7, '$$aaa$$$$$$$$ccc$$$$ddd$$' from dual
   )
   select id, level, regexp_substr(txt,'(\$\$(.*?)\$\$)',1,level,null,2) element
   from tbl
   connect by regexp_substr(txt,'(\$\$(.*?)\$\$)',1,level) is not null
     and prior txt = txt
     and prior sys_guid() is not null
   order by id, level;

        ID      LEVEL ELEMENT
---------- ---------- -------------------------------------------
         1          1 xxx
         2          1 xxx
         2          2 yyy
         3          1
         4          1 xxx
         4          2 yyy
         5          1 xxx
         5          2 yyy
         5          3 www
         5          4 zzz
         6          1 aaa
         6          2 bbb
         6          3 ccc
         6          4 ddd
         7          1 aaa
         7          2
         7          3 ccc
         7          4 ddd

18 rows selected.

SQL>
0 голосов
/ 24 декабря 2018

Вы можете использовать рекурсивный запрос, который соответствует первому вхождению, а затем удаляет его из строки для следующей итерации рекурсивного запроса.

Предполагается, что ваша таблица и столбец называются tbl и txt:

with cte(match, txt) as (
    select regexp_substr(txt,'\$\$(.*?)\$\$', 1, 1, null, 1),
           regexp_replace(txt,'\$\$(.*?)\$\$', '', 1, 1)
    from   tbl
    where  regexp_like(txt,'\$\$(.*?)\$\$') 
    union all
    select regexp_substr(txt,'\$\$(.*?)\$\$', 1, 1, null, 1),
           regexp_replace(txt,'\$\$(.*?)\$\$', '', 1, 1)
    from   cte
    where  regexp_like(txt,'\$\$(.*?)\$\$') 
)
select match from cte
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...