LENGTH命令的奇怪行为 - ORACLE

Jor*_*pos 11 sql oracle

我在这里遇到了一个我无法理解的错误情况.我写的关于函数的文档也没有东西可以点亮这个东西.

我有一张有田地的桌子titulo varchar2(55).我在巴西,一些在这一领域中的字符有口音,我的目标是创建没有口音相似的场(由原始字符代替,因为这á成为a等等).

我可以使用一堆函数来做到这一点replace,translate而其他人,但我发现在互联网上,接缝更优雅,然后我使用它.这就是问题所在.

我的更新代码如下:

update myTable 
   set TITULO_URL = replace(
                 utl_raw.cast_to_varchar2(
                           nlssort(titulo, 'nls_sort=binary_ai')
                                         )
                            ,' ','_');
Run Code Online (Sandbox Code Playgroud)

正如我所说,目标是转换其等效的每个重音字符,而没有重音加上空格字符 _

然后我收到了这个错误:

ORA-12899: value too large for column 
     "mySchem"."myTable"."TITULO_URL" (actual: 56, maximum: 55)
Run Code Online (Sandbox Code Playgroud)

起初我可能会添加一些角色,让我检查一下.我做了一个select命令让我得到一个titulo有55个字符的行.

select titulo from myTable where length(titulo) = 55
Run Code Online (Sandbox Code Playgroud)

然后我选择一行来做一些测试,我选择的行有这个值:( 'FGHJTÓRYO DE YHJKS DA DGHQÇÃA DE ASGA XCVBGL EASDEÔNASD'我确实将它改为保存数据,但结果是一样的)

当我做以下选择声明,事情变得奇怪:

select a, length(a), b, length(b)
  from ( select 'FGHJTÓRYO DE YHJKS DA DGHQÇÃA DE ASGA XCVBGL EASDEÔNASD' a,
                replace(
                   utl_raw.cast_to_varchar2( 
                               nlssort('FGHJTÓRYO DE YHJKS DA DGHQÇÃA DE ASGA XCVBGL EASDEÔNASD', 'nls_sort=binary_ai')
                                           )
                       ,' ','_') b
           from dual
       )
Run Code Online (Sandbox Code Playgroud)

这个sql的结果是(为了更好的可视化,我会将值降低一个):

                     a                                       LENGTH(a)
FGHJTÓRYO DE YHJKS DA DGHQÇÃA DE ASGA XCVBGL EASDEÔNASD        55     
                     b                                       LENGTH(b)
fghjtoryo_de_yhjks_da_dghqcaa_de_asga_xcvbgl_easdeonasd        56
Run Code Online (Sandbox Code Playgroud)

比较两个字符串一个在另一个上面没有大小差异:

FGHJTÓRYO DE YHJKS DA DGHQÇÃA DE ASGA XCVBGL EASDEÔNASD
fghjtoryo_de_yhjks_da_dghqcaa_de_asga_xcvbgl_easdeonasd
Run Code Online (Sandbox Code Playgroud)

我已经在Toad,PLSQL Developer和SQLPLUSW上测试了这个查询,结果相同.所以我的问题是这个长度(b)= 56来自哪里?我知道它可以是字符集,但我无法弄清楚为什么.我甚至用trim命令测试,结果是一样的.

我做的另一项测试

  • substr(b, 1,55) 结果与上面的文字相同
  • lenght(trim(b)) 结果是56
  • substr(b,56) 结果是空的(没有空,没有空格,只是空)

@Sebas建议:

  • LENGTHB(b) 结果是56
  • ASCII(substr(b,56))

那么,再说一次:这个长度(b)= 56来自哪里?

对不起,很长的帖子,感谢那些下来的人(阅读所有内容).感谢那些不读的人:)

最好的祝福

小智 3

“nlssort”函数的文档没有说明输出字符串将是输入字符串的规范化,或者它们将具有相同的长度。该函数的目的是返回可用于对输入字符串进行排序的数据。

请参阅http://docs.oracle.com/cd/E11882_01/server.112/e26088/functions113.htm#SQLRF51561

使用它来标准化你的字符串是很诱人的,因为显然它是有效的,但你在这里赌博......

哎呀,它甚至可以产生LENGTH(b)=200并且仍然在做它应该做的事情:)