sql >> Base de Datos >  >> RDS >> Oracle

¿Cómo deshacerse de los caracteres NUL en la base de datos de Oracle?

Personalmente, usaría CHR() para identificar los valores nulos. Un nul es un ASCII 0 y CHR() devolverá la representación de caracteres del número que ingresa.

SQL> with the_data as (
  2  select 'a' || chr(0) || 'b' as str from dual
  3   union all
  4  select 'a' || 'c' from dual
  5         )
  6  select dump(str)
  7    from the_data
  8   where str like '%' || chr(0) || '%'
  9         ;

DUMP(STR)
----------------------------------------------------    
Typ=1 Len=3: 97,0,98

Como puede ver al concatenar signos de porcentaje alrededor de CHR(0) (que es equivalente a nul) puede devolver filas con nul.

DUMP() devuelve el tipo de datos (1 significa VARCHAR2 ) la longitud de la cadena en bytes y la representación interna de los datos; el valor predeterminado es binario.

Sin embargo, debe tener cuidado con los datos multibyte como CHR() devuelve el carácter equivalente al módulo de 256 del número:

SQL> with the_data as (
  2  select 'a' || chr(0) || 'b' as str from dual
  3   union all
  4  select 'a' || chr(256) || 'c' from dual
  5         )
  6  select dump(str)
  7    from the_data
  8   where str like '%' || chr(0) || '%'
  9         ;

DUMP(STR)
-------------------------------------------------
Typ=1 Len=3: 97,0,98
Typ=1 Len=4: 97,1,0,99

Como puede ver, identificaría erróneamente un nul aquí, usando CHR() o DUMP()

En otras palabras, si no tiene datos multibyte, lo más fácil es simplemente reemplazar es:

update <table>
   set <column> = replace(<column>, chr(0));

Utilizando RAWTOHEX() tiene problemas similares; aunque puedes encontrar el 00 no hay garantía de que en realidad sea un nul:

SQL> with the_data as (
  2  select 'a' || chr(0) || 'b' as str from dual
  3   union all
  4  select 'a' || chr(256) || 'c' from dual
  5         )
  6  select rawtohex(str)
  7    from the_data
  8   where str like '%' || chr(0) || '%'
  9         ;

RAWTOHEX
--------
610062
61010063

En realidad, también tiene otro problema; imagina que tienes dos caracteres 10 y 06 el valor devuelto es entonces 1006 y encontrarás 00 . Si tuviera que usar este método, debe asegurarse de mirar solo dos grupos de caracteres, desde el comienzo de la cadena.

Como la representación interna de un carácter nulo se usa para representar partes de otros caracteres multibyte, no puede simplemente reemplazarlos ya que no sabe si es un carácter o medio carácter. Por lo tanto, si está utilizando un conjunto de caracteres de varios bytes, hasta donde yo sé, no podrá hacer esto.