确定最终结果的长度属性

当为函数或CAST规范指定 CODEUNITS32、 CODEUNITS16 或OCTETS时,最终结果字符串的长度属性将根据指定的函数应用特定的公式进行计算。

为了确定函数或CAST规范的最终结果,如果指定了 CODEUNITS32 或 CODEUNITS16 ,则 Db2 可能需要使用中间结果字符串,具体取决于数据的编码方案:

  • 当指定了 CODEUNITS32 或 CODEUNITS16 时,ASCII和EBCDIC数据需要使用 UTF-16 中间结果字符串。
  • UTF-8 数据要求使用 中间结果字符串,仅当指定了 时。 UTF-16 CODEUNITS16

无论是否使用中间字符串,当为函数或CAST规范指定 CODEUNITS32、 CODEUNITS16 或OCTETS时,最终结果字符串的长度属性均通过应用下表中描述的公式进行计算。 除非另有说明,否则在公式中每一步计算的长度属性均以字节为单位。

确定字符串的长度属性

最终结果字符串的长度属性公式取决于函数。

每个长度属性(IML、rl和函数的最终结果)的计算最终值受函数最大长度或结果对应数据类型最大长度的限制,以适用者为准。 每个长度属性都以字节为单位。

CAST 规范、CHAR、CLOB、DBCLOB、GRAPHIC、VARCHAR、VARGRAPHIC
请按照以下三个步骤确定最终结果的长度属性:
1. 中间琴弦的长度(IML)

当指定了 CODEUNITS32 或 CODEUNITS16 时:

  • 如果源字符串不是Unicode CCSID 1200、1208或367,则使用比较转换规则中的公式将源字符串转换为CCSID 1200,以确定中间字符串(IML)的结果长度。
  • 如果源字符串是Unicode CCSID 1208或367,并且指定了 CODEUNITS16 ,则使用比较转换规则中的公式将源字符串转换为CCSID 1200,以确定中间字符串(IML)的结果长度。
  • 否则,中间字符串与源字符串相同。

指定了“八位字节”时:

  • 如果源字符串的CCSID与函数结果的CCSID不同,则使用比较转换规则中的公式将源字符串转换为函数结果的CCSID,以确定中间字符串(IML)的结果长度。
  • 否则,中间字符串与源字符串相同。

例外 :对于 GRAPHIC 和 VARGRAPHIC 函数,如果源字符串是 EBCDIC,则在源字符串转换为 CCSID 1200 并确定中间字符串的长度之前,源字符串会扩展为带有前缀 X'42'

2. 中间字符串的结果长度属性(rl)
中间字符串的结果长度(rl)取决于是否明确指定了长度参数
如果未指定长度 ,则结果长度(rl)属性为:
   rl = IML
如果指定了长度 ,结果长度(rl)属性为:
   IF (ol * n) < r_IML THEN
      rl = ol * n
   ELSE
        IF intermediate string is in CCSID 1200
        (UTF-16) THEN
           rl = MIN( ol * n , IML + ( r  * 2 )) 
        ELSE
           rl = MIN( ol * n , IML + r ) 
其中:
  • ol = 原始长度参数,以指定的字符串单位表示
    n =
    4个字节用于 CODEUNITS32
    2字节用于 CODEUNITS16
  • IML = 中间字符串的长度
  • r_IML = IML四舍五入到n的下一个倍数
  • r = ol - (r_IML/n),以指定的字符串单位表示

    r 的计算是对长度参数和输入参数的估计字符数之间的差值的估计,以指定的字符串单位表示。

3. 最终结果字符串的长度(函数的结果)
如果需要转换CCSID,则使用比较转换规则中的公式,将中间字符串的结果长度(rl)转换为函数结果的CCSID,从而确定最终字符串的结果长度属性。 否则,最终字符串的结果长度属性为rl。
字符串长度、定位、定位字符串、位置
请按照以下三个步骤确定最终结果的长度属性:
1. 中间琴弦的长度(IML)
中间字符串(IML)的长度确定方式与CAST规范相同。 (参见中间字符串长度(IML)。

对于LOCATE、LOCATE_IN_STRING和POSITION函数,这适用于源字符串搜索字符串。 如果转换后的源字符串搜索字符串的中间字符串的CCSID不同,则搜索字符串的中间字符串将转换为源字符串的中间字符串的CCSID

2. 中间字符串的结果长度属性(rl)
结果长度(rl)属性始终为4(整数长度):
   rl = 4
3. 最终结果字符串的长度(函数的结果)
函数的最终结果的长度始终为整数。
插入,覆盖
请按照以下三个步骤确定最终结果的长度属性:
1. 中间琴弦的长度(IML)
源字符串插入字符串的中间字符串 (IML) 的长度以与 CAST 规范相同的方式确定。 (参见中间字符串长度(IML)。

如果转换后的源字符串插入字符串的中间字符串的CCSID不同,则插入字符串的中间字符串将转换为源字符串的中间字符串的CCSID。

2. 中间字符串的结果长度属性(rl)
中间字符串的结果长度(rl)属性取决于起始和长度参数是否为常量。
如果 startlength 参数均为常量,则结果 length 属性为:
   rl = L1 - MIN ( MAX ( 0, L1 - (V2 - 1)
   * n ), V3 * m) + L4 
如果至少有一个参数 (开始长度参数)不是常量,则结果长度属性为:
   rl = L1 + L4 
其中:
  • L1 和 分别是 L4 源字符串插入字符串中间字符串的长度属性。
  • V2 和 分别是 V3 起始值长度值 ,以指定的字符串单位表示。
    m=
    1 如果源字符串的中间字符串不是 CCSID 1200 ( UTF-16 )
    2 如果源字符串的中间字符串是CCSID 1200 ( UTF-16 )
    n=
    4个字节用于 CODEUNITS32
    2字节用于 CODEUNITS16
3. 最终结果字符串的长度(函数的结果)
最终结果的长度与CAST规范最终结果的长度相同。 (参见最终结果字符串(函数结果)的长度属性。)
向左键、向右键
请按照以下三个步骤确定最终结果的长度属性:
1. 中间琴弦的长度(IML)
中间字符串(IML)的长度确定方式与CAST规范相同。 (参见中间字符串长度(IML)。
2. 中间字符串的结果长度属性(rl)
结果长度(rl)属性与中间字符串的长度相同:
   rl = IML
3. 最终结果字符串的长度(函数的结果)
如果需要转换CCSID,则使用比较转换规则中的公式,将中间字符串的结果长度(rl)转换为函数结果的CCSID,从而确定最终字符串的结果长度属性。 否则,最终字符串的结果长度属性为rl。
最终字符串的结果长度属性为:
   MIN(length of source string, length of CCSID
   converted string )
SUBSTRING
请按照以下三个步骤确定最终结果的长度属性:
1. 中间琴弦的长度(IML)
中间字符串(IML)的长度确定方式与CAST规范相同。 (参见中间字符串长度(IML)。
2. 中间字符串的结果长度属性(rl)
中间字符串的结果长度(rl)取决于是否明确指定了长度参数
如果未指定长度 ,则结果长度(rl)属性为:
   rl = IML
如果指定了长度 ,结果长度(rl)属性为:
   rl = MIN(ol * n, IML)
其中:
  • ol = 原始长度参数,以指定的字符串单位表示
    n =
    4个字节用于 CODEUNITS32
    2字节用于 CODEUNITS16
  • IML = 中间字符串的长度
3. 最终结果字符串的长度(函数的结果)
最终结果字符串的长度与LEFT内置函数相同。

示例

示例 1
假设 T1 是一个用EBCDIC编码的表,而 C1 是一个CHAR(26)列(EBCDIC CCSID 37的SBCS数据)。 CHAR函数在以下语句中调用:
SELECT CHAR(C1,10,CODEUNITS32) as COL1 FROM T1; 
Db2 使用中间字符串来计算函数,并使用以下步骤确定中间和最终结果字符串的长度:
  1. C1 ,即SBCS EBCDIC 37数据,转换为Unicode 1200( UTF-16 )。 转换结果的长度(使用比较转换规则中的公式,X * 2)为 26 * 2。 因此,中间字符串的长度为52字节(IML = 52)。
  2. CHAR函数根据该字符串的前10个 UTF-32 字符进行评估。 结果长度属性为40字节 (rl = ol * n or 10 * 4),因为 ol * n < r_IML or 40 < 52
  3. 40字节的字符串被转换回SBCS EBCDIC 37。 转换结果的长度(使用比较转换规则中的公式,X *.5)为40 *.5。 因此,函数的最终结果长度为20字节。
示例 2
这个例子与第一个例子类似,只是指定函数的长度为20,而不是10。 假设 T1 是一个用EBCDIC编码的表,而 C1 是一个CHAR(26)列(EBCDIC CCSID 37的SBCS数据)。 CHAR函数在以下语句中调用:
SELECT CHAR(C1,20,CODEUNITS32) as COL1 FROM T1; 
Db2 使用中间字符串来计算函数,并使用以下步骤确定中间和最终结果字符串的长度:
  1. C1 ,即SBCS EBCDIC 37数据,转换为Unicode 1200( UTF-16 )。 转换结果的长度(使用比较转换规则中的公式,X * 2)为 26 * 2。 因此,中间结果字符串的长度为52字节(IML = 52)。
  2. CHAR函数根据中间字符串的前20个 UTF-32 字符进行评估。 然而,由于中间字符串中字符的估计数量(以指定的字符串单位表示)只有13个字符(r_IML/n or 52/4 ),因此必须用7个填充字符填充中间字符串,以满足所需的20个字符(r = ol - (r_IML/n) or 20 - 13 )。在Unicode 1200( UTF-16 )中,每个填充字符占2个字节。

    结果长度属性被计算为66字节 (rl = MIN(ol * n, IML + (r * 2)) or MIN(20 * 4, 52 + 14)) ,因为 ol * n < r_IML or 80 < 52 不是真的。

  3. 将66字节字符串转换回SBCS EBCDIC 37。 转换结果的长度(使用比较转换规则中的公式,X *.5)为66 *.5。 因此,函数的最终结果长度为33字节。