为什么Oracle 10g to_char(日期时间)截断字符串?

时间:2016-09-29 17:25:14

标签: oracle buffer truncate to-char

我得到了bug report,其中Oracle 10g正在截断to_char(datetime)的返回值:

SQL> select to_char(systimestamp, '"day:"DD"hello"') from dual;

TO_CHAR(SYSTIMESTAMP,'"DAY:"DD"HE
---------------------------------
day:27hel

值得注意的是,Oracle 11g似乎没有发生这种情况。我的问题是,它为什么会发生?是否有一些配置变量设置为告诉to_char(datetime)为其返回值分配更大的缓冲区?

2 个答案:

答案 0 :(得分:3)

我不确定,但它可能只是在SQL * Plus中显示。你试过在Toad中运行吗?或者,如果将结果分配给PL / SQL块中的varchar2并输出结果?

这是我在SQL * Plus参考10g中找到的内容:

  

SQL * Plus中未格式化的DATE列的默认宽度和格式   由数据库NLS_DATE_FORMAT参数确定。除此以外,   默认格式宽度为A9。请参阅COLUMN的FORMAT子句   命令以获取有关格式化DATE列的更多信息。

您的值被修剪为9个字符,对应于默认的A9格式。我没有相同的版本,这种行为不会在11g中再现,所以请你检查一下我的理论吗?

答案 1 :(得分:0)

我遇到了同样的问题,我知道解决方案。 我使用的是版本11.2.0.4.0,但我认为可以在其他版本中重复这种情况。它以某种方式取决于客户。 (例如,我不能使用SQL * Plus重复它,只能使用PL / SQL Devepoper) 试试这个:

select to_char(systimestamp, '"day:"DD"йцукенг OR any other UTF-encoded-something"') from dual
union all
select to_char(systimestamp, '"day:"DD"hello"') from dual;

您将获得以下结果:

day:08йцукенг OR any other UTF-encoded-so
day:08hello

你可以看到“催化”丢失了。由于7个双字节符号“йцукенг”,这正好超过了7个字节。 Oracle为字符数分配缓冲区,而不是所需的字节数。 命令

alter session set nls_length_semantics=byte/char

不幸的是不会影响这种行为。

所以我的解决方案是将结果转换为varchar2(足够的容量)

select cast(to_char(systimestamp, '"day:"DD"йцукенг OR any other UTF-encoded-something"') as varchar(1000)) from dual
union all
select to_char(systimestamp, '"day:"DD"hello"') from dual

显式类型转换使表达式独立于客户端或配置。 顺便说一下,所有隐含的to_char转换都会发生同样的事情。例如。

case [numeric_expression]
when 1 then '[unicode_containing_string]'
end

结果可能被削减。