Oracle
 sql >> Base de données >  >> RDS >> Oracle

Fractionner une chaîne en plusieurs lignes dans Oracle

Cela peut être une méthode améliorée (également avec regexp et connect by) :

with temp as
(
    select 108 Name, 'test' Project, 'Err1, Err2, Err3' Error  from dual
    union all
    select 109, 'test2', 'Err1' from dual
)
select distinct
  t.name, t.project,
  trim(regexp_substr(t.error, '[^,]+', 1, levels.column_value))  as error
from 
  temp t,
  table(cast(multiset(select level from dual connect by  level <= length (regexp_replace(t.error, '[^,]+'))  + 1) as sys.OdciNumberList)) levels
order by name

MODIFIER :Voici une explication simple (comme dans "pas en profondeur") de la requête.

  1. length (regexp_replace(t.error, '[^,]+')) + 1 utilise regexp_replace pour effacer tout ce qui n'est pas le délimiteur (virgule dans ce cas) et length +1 pour obtenir le nombre d'éléments (erreurs) présents.
  2. Le select level from dual connect by level <= (...) utilise une requête hiérarchique pour créer une colonne avec un nombre croissant de correspondances trouvées, de 1 au nombre total d'erreurs.

    Aperçu :

    select level, length (regexp_replace('Err1, Err2, Err3', '[^,]+'))  + 1 as max 
    from dual connect by level <= length (regexp_replace('Err1, Err2, Err3', '[^,]+'))  + 1
    
  3. table(cast(multiset(.....) as sys.OdciNumberList)) fait un casting de types oracle.
    • Le cast(multiset(.....)) as sys.OdciNumberList transforme plusieurs collections (une collection pour chaque ligne de l'ensemble de données d'origine) en une seule collection de nombres, OdciNumberList.
    • La table() transforme une collection en un jeu de résultats.
  4. FROM sans jointure crée une jointure croisée entre votre jeu de données et le multiset.En conséquence, une ligne dans le jeu de données avec 4 correspondances se répétera 4 fois (avec un nombre croissant dans la colonne nommée "column_value").

    Aperçu :

    select * from 
    temp t,
    table(cast(multiset(select level from dual connect by  level <= length (regexp_replace(t.error, '[^,]+'))  + 1) as sys.OdciNumberList)) levels
    
  5. trim(regexp_substr(t.error, '[^,]+', 1, levels.column_value)) utilise la column_value en tant que nième_apparition/occurrence paramètre pour regexp_substr .
  6. Vous pouvez ajouter d'autres colonnes à partir de votre ensemble de données (t.name, t.project par exemple) pour une visualisation facile.

Quelques références aux documents Oracle :

  • REGEXP_REPLACE
  • REGEXP_SUBSTR
  • Constantes, types et mappages d'extensibilité (OdciNumberList)
  • CAST (multiset)
  • Requêtes hiérarchiques