📜  使用转换函数

📅  最后修改于: 2020-12-29 04:19:51             🧑  作者: Mango


除了SQL实用程序函数外,Oracle内置函数库还包含类型转换函数。在某些情况下,查询期望输入特定数据类型,但查询会接收其他数据类型。在这种情况下,Oracle会隐式地尝试将意外值转换为兼容的数据类型,该数据类型可以就地替换,并且不会损害应用程序的连续性。类型转换可以由Oracle隐式完成,也可以由程序员显式完成。

隐式数据类型转换基于一个矩阵来工作,该矩阵展示了Oracle对内部类型转换的支持。除了这些规则外,Oracle还提供类型转换功能,可在查询中使用它们进行显式转换和格式化。实际上,建议执行显式转换,而不要依赖软件智能。尽管隐式转换效果很好,但可以消除在内部很难键入错误输入的时机。

隐式数据类型转换

Oracle可以将VARCHAR2或CHAR值隐式转换为NUMBER或DATE类型的值。类似地,Oracle服务器可以将NUMBER或DATA类型的值自动转换为字符数据。请注意,仅当字符代表有效数字或日期类型值时,才会发生隐式互转换。

例如,检查下面的SELECT查询。这两个查询将给出相同的结果,因为Oracle在内部将15000和’15000’视为相同。

查询1

SELECT employee_id,first_name,salary
FROM employees
WHERE salary > 15000;

查询2

SELECT employee_id,first_name,salary
FROM employees
WHERE salary > '15000';

显式数据类型转换

SQL Conversion函数是单行函数,能够类型转换列值,字面量或表达式。 TO_CHAR,TO_NUMBER和TO_DATE是执行交叉修改数据类型的三个函数。

TO_CHAR函数

TO_CHAR函数用于使用格式模型(可选)将数字或日期输入转换为字符类型。

句法

TO_CHAR(number1, [format], [nls_parameter])

对于数字到字符的转换,nls参数可用于指定小数字符,组分隔符,本地货币模型或国际货币模型。这是一个可选规范-如果不可用,将使用会话级nls设置。对于日期到字符的转换,nls参数可用于指定日期和月份名称(如适用)。

使用TO_CHAR函数转换为字符类型后,可以将日期格式化为多种格式。 TO_CHAR函数用于使Oracle 11g以特定格式显示日期。格式模型区分大小写,并且必须用单引号引起来。

考虑下面的SELECT查询。查询使用TO_CHAR函数格式化EMPLOYEES表的HIRE_DATE和SALARY列。

SELECT first_name,
       TO_CHAR (hire_date, 'MONTH DD, YYYY') HIRE_DATE,
       TO_CHAR (salary, '$99999.99') Salary
FROM employees
WHERE rownum < 5;

FIRST_NAME           HIRE_DATE          SALARY
-------------------- ------------------ ----------
Steven               JUNE      17, 2003  $24000.00
Neena                SEPTEMBER 21, 2005  $17000.00
Lex                  JANUARY   13, 2001  $17000.00
Alexander            JANUARY   03, 2006   $9000.00

第一个TO_CHAR用于将雇用日期转换为日期格式MONTH DD,YYYY,即拼出的月份并用空格填充,然后是月份的两位数日期,然后是年份的四位数。如果您希望以混合大小写(即“ December”)显示月份名称,则只需在格式参数中使用此大小写:(“ Month DD,YYYY”)。

图10-39中的第二个TO_CHAR函数用于格式化SALARY以显示货币符号和两个小数位。

Oracle提供了全面的格式模型集。下表显示了格式模型的列表,可用于使用TO_CHAR将日期和数字值转换为字符。

Format Model Description
,(comma) It returns a comma in the specified position. You can specify multiple commas in a number format model. Restrictions:A comma element cannot begin a number format model. A comma cannot appear to the right of a decimal character or period in a number format model.
.(period) Returns a decimal point, which is a period (.) in the specified position. Restriction: You can specify only one period in a number format model
$ Returns value with a leading dollar sign
0 Returns leading zeros. Returns trailing zeros.
9 Returns value with the specified number of digits with a leading space if positive or with a leading minus if negative. Leading zeros are blank, except for a zero value, which returns a zero for the integer part of the fixed-point number.
B Returns blanks for the integer part of a fixed-point number when the integer part is zero (regardless of “0”s in the format model).
C Returns in the specified position the ISO currency symbol (the current value of the NLS_ISO_CURRENCY parameter).
D Returns in the specified position the decimal character, which is the current value of the NLS_NUMERIC_CHARACTER parameter. The default is a period (.).
Restriction: You can specify only one decimal character in a number format model.
EEE Returns a value using in scientific notation.
FM Returns a value with no leading or trailing blanks.
G Returns in the specified position the group separator (the current value of the NLS_NUMERIC_CHARACTER parameter). You can specify multiple group separators in a number format model. Restriction: A group separator cannot appear to the right of a decimal character or period in a number format model
L Returns in the specified position the local currency symbol (the current value of the NLS_CURRENCY parameter).
MI Returns negative value with a trailing minus sign (-). Returns positive value with a trailing blank. Restriction: The MI format element can appear only in the last position of a number format model.
PR Returns negative value in . It can appear only in the end of a number format model.
RN,rm Returns a value as Roman numerals in uppercase. Returns a value as Roman numerals in lowercase.
Value can be an integer between 1 and 3999.
S Returns negative value with a leading or trailing minus sign (-). Returns positive value with a leading or trailing plus sign (+). Restriction: The S format element can appear only in the first or last position of a number format model.
TM “Text minimum”. Returns (in decimal output) the smallest number of characters possible. This element is case-insensitive.
U Returns in the specified position the “Euro” (or other) dual currency symbol (the current value of the NLS_DUAL_CURRENCY parameter).
V Returns a value multiplied by 10n (and if necessary, round it up), where n is the number of 9’s after the “V”.
X Returns the hexadecimal value of the specified number of digits.

TO_NUMBER函数

TO_NUMBER函数将字符值转换为数字数据类型。如果要转换的字符串包含非数字字符,则该函数返回错误。

句法

TO_NUMBER (string1, [format], [nls_parameter])

下表列出了格式模型列表,可用于使用TO_NUMBER将字符值以数字形式转换。

Format Model Description
CC Century
SCC Century BC prefixed with –
YYYY Year with 4 numbers
SYYY Year BC prefixed with –
IYYY ISO Year with 4 numbers
YY Year with 2 numbers
RR Year with 2 numbers with Y2k compatibility
YEAR Year in characters
SYEAR Year in characters, BC prefixed with –
BC BC/AD Indicator
Q Quarter in numbers (1,2,3,4)
MM Month of year 01, 02…12
MONTH Month in characters (i.e. January)
MON JAN, FEB
WW Week number (i.e. 1)
W Week number of the month (i.e. 5)
IW Week number of the year in ISO standard.
DDD Day of year in numbers (i.e. 365)
DD Day of the month in numbers (i.e. 28)
D Day of week in numbers(i.e. 7)
DAY Day of the week in characters (i.e. Monday)
FMDAY Day of the week in characters (i.e. Monday)
DY Day of the week in short character description (i.e. SUN)
J Julian Day (number of days since January 1 4713 BC, where January 1 4713 BC is 1 in Oracle)
HH,H12 Hour number of the day (1-12)
HH24 Hour number of the day with 24Hours notation (0-23)
AM, PM AM or PM
MI, SS Number of minutes and seconds (i.e. 59) ,
SSSSS Number of seconds this day.
DS Short date format. Depends on NLS-settings. Use only with timestamp.
DL Long date format. Depends on NLS-settings. Use only with timestamp.
E Abbreviated era name. Valid only for calendars: Japanese Imperial, ROC Official, Thai Buddha.
EE The full era name
FF The fractional seconds. Use with timestamp.
FF1..FF9 The fractional seconds. Use with timestamp. The digit controls the number of decimal digits used for fractional seconds.
FM Fill Mode: suppresses blanks in output from conversion
FX Format Exact: requires exact pattern matching between data and format model.
IYY OR IY OR I The last 3,2,1 digits of the ISO standard year. Output only
RM The Roman numeral representation of the month (I .. XII)
RR The last 2 digits of the year.
RRRR The last 2 digits of the year when used for output. Accepts fout-digit years when used for input.
SP Spelled format. Can appear of the end of a number element. The result is always in english. For example month 10 in format MMSP returns “ten”
SPTH Spelled and ordinal format; 1 results in first.
TH Converts a number to it’s ordinal format. For example 1 becoms 1st.
TS Short time format. Depends on NLS-settings. Use only with timestamp.
TZD Abbreviated time zone name. ie PST.
TZH,TZM Time zone hour/minute displacement.
TZR Time zone region
X Local radix character. In America this is a period (.)

下面的SELECT查询接受数字作为字符输入,并按照格式说明符将其打印出来。

SELECT  TO_NUMBER('121.23', '9G999D99') 
FROM DUAL

TO_NUMBER('121.23','9G999D99')
------------------------------
                        121.23

SELECT  TO_NUMBER('1210.73', '9999.99') 
FROM DUAL;

TO_NUMBER('1210.73','9999.99')
------------------------------
                       1210.73

TO_DATE函数

该函数以字符值作为输入,并返回与之等效的格式化日期。 TO_DATE函数允许用户以任何格式输入日期,然后将其转换为Oracle 11g使用的默认格式。

句法:

TO_DATE( string1, [ format_mask ], [ nls_language ] )

format_mask参数由一系列元素组成,这些元素精确表示数据的外观,并且必须用单引号引起来。

Format Model Description
YEAR Year, spelled out
YYYY 4-digit year
YYY,YY,Y Last 3, 2, or 1 digit(s) of year.
IYY,IY,I Last 3, 2, or 1 digit(s) of ISO year.
IYYY 4-digit year based on the ISO standard
RRRR Accepts a 2-digit year and returns a 4-digit year.
Q Quarter of year (1, 2, 3, 4; JAN-MAR = 1).
MM Month (01-12; JAN = 01).
MON Abbreviated name of month.
MONTH Name of month, padded with blanks to length of 9 characters.
RM Roman numeral month (I-XII; JAN = I).
WW Week of year (1-53) where week 1 starts on the first day of the year and continues to the seventh day of the year.
W Week of month (1-5) where week 1 starts on the first day of the month and ends on the seventh.
IW Week of year (1-52 or 1-53) based on the ISO standard.
D Day of week (1-7).
DAY Name of day.
DD Day of month (1-31).
DDD Day of year (1-366).
DY Abbreviated name of day.
J Julian day; the number of days since January 1, 4712 BC.
HH12 Hour of day (1-12).
HH24 Hour of day (0-23).
MI,SS Minute (0-59).
SSSSS Seconds past midnight (0-86399).
FF Fractional seconds. Use a value from 1 to 9 after FF to indicate the number of digits in the fractional seconds. For example, ‘FF4’.
AM,PM Meridian indicator
AD,BC AD, BC indicator
TZD Daylight savings information. For example, ‘PST’
TZH,TZM,TZR Time zone hour/minute/region.

下面的示例将转换成日期:

SELECT TO_DATE('January 15, 1989, 11:00 A.M.',  'Month dd, YYYY, HH:MI A.M.',  'NLS_DATE_LANGUAGE = American')
FROM DUAL;

TO_DATE('
---------
15-JAN-89

一般功能

常规函数用于处理数据库中的NULL值。常规NULL处理函数的目的是将NULL值替换为备用值。我们将在下面简要介绍这些功能。

NVL

NVL函数将替代值替换为NULL值。

句法:

NVL( Arg1, replace_with )

在语法中,两个参数都是必需的。请注意,NVL函数适用于所有类型的数据类型。并且原始字符串和替换的数据类型必须处于兼容状态,即Oracle可以相同或隐式转换。

如果arg1是字符值,则oracle在比较替换字符串之前将其转换为与arg1兼容的数据类型,并在expr1字符集中返回VARCHAR2。如果arg1是数字,则Oracle确定数字优先级最高的参数,将另一个参数隐式转换为该数据类型,然后返回该数据类型。

如果尚未将员工分配给任何工作,即JOB_ID为NULL,则下面的SELECT语句将显示“ n / a”。否则,它将显示实际的JOB_ID值。

SELECT  first_name, NVL(JOB_ID, 'n/a')
FROM employees;

NVL2

作为对NVL的增强,Oracle引入了一种功能,该函数不仅可以将值替换为NULL列值,而且还可以替换为NOT NULL列。 NVL2函数可用于将替代值替换为NULL以及非NULL值。

句法:

NVL2( string1, value_if_NOT_null, value_if_null )

如果雇员的JOB_CODE为NULL,则下面的SELECT语句将显示“ Bench”。对于作业代码的确定的非空值,它将显示恒定值“作业分配”。

SQL> SELECT NVL2(JOB_CODE, 'Job Assigned', 'Bench')
FROM employees;

空IF

NULLIF函数比较两个参数expr1和expr2。如果expr1和expr2相等,则返回NULL;否则,返回NULL。否则,返回expr1。与其他null处理函数,第一个参数不能为NULL。

句法:

NULLIF (expr1, expr2)

请注意,第一个参数可以是计算结果为NULL的表达式,但不能为字面量NULL。这两个参数都是函数执行所必需的。

由于两个输入值12相等,因此以下查询返回NULL。

SELECT    NULLIF (12, 12)
FROM DUAL;

同样,在下面的查询中返回“ SUN”,因为两个字符串都不相等。

SELECT NULLIF ('SUN', 'MOON')
FROM DUAL;

合并

COALESCE函数(一种更通用的NVL形式)返回参数列表中的第一个非空表达式。它至少需要两个强制参数,但最大参数没有限制。

句法:

COALESCE (expr1, expr2, ... expr_n )

考虑下面的SELECT查询。它选择输入到雇员地址字段中的第一个非空值。

SELECT COALESCE (address1, address2, address3) Address
FROM  employees;

有趣的是,COALESCE函数的工作方式类似于IF..ELSIF..ENDIF构造。上面的查询可以重写为-

IF address1 is not null THEN
   result := address1;
ELSIF address2 is not null THEN
   result := address2;
ELSIF address3 is not null THEN
   result := address3;
ELSE
   result := null;
END IF;

条件函数

Oracle提供了条件函数DECODE和CASE甚至在SQL语句中也施加条件。

DECODE函数

该函数是IF..THEN..ELSE条件过程语句的SQL等效项。 DECODE适用于所有数据类型的值/列/表达式。

句法:

DECODE (expression, search, result [, search, result]... [, default])

DECODE函数按顺序将表达式与每个搜索值进行比较。如果expression和search参数之间存在相等,则它将返回相应的结果。如果不匹配,则返回默认值(如果已定义),否则返回NULL。如果任何类型兼容性都不匹配,则oracle在内部进行可能的隐式转换以返回结果。

实际上,在使用DECODE函数时,Oracle认为两个null是等效的。

SELECT DECODE(NULL,NULL,'EQUAL','NOT EQUAL') 
FROM DUAL;

DECOD
-----
EQUAL

如果expression为null,则Oracle返回也为null的第一个搜索结果。 DECODE函数的最大组件数为255。

SELECT    first_name, salary, DECODE (hire_date, sysdate,'NEW JOINEE','EMPLOYEE')
    FROM employees;

案例表达

CASE表达式的工作原理与DECODE相同,但是语法和用法不同。

句法:

CASE  [ expression ]
   WHEN condition_1 THEN result_1
   WHEN condition_2 THEN result_2
   ...
   WHEN condition_n THEN result_n
   ELSE result
END

Oracle搜索从左开始,然后向右移动,直到找到一个真正的条件,然后返回与其关联的结果表达式。如果没有条件为真,并且存在ELSE子句,则Oracle返回用else定义的结果。否则,Oracle返回null。

CASE表达式中的最大参数数为255。所有表达式都计入此限制,包括简单CASE表达式的初始表达式和可选的ELSE表达式。每个WHEN … THEN对均视为两个参数。为了避免超出此限制,可以嵌套CASE表达式,以便return_expr本身是CASE表达式。

SELECT first_name, CASE    WHEN salary < 200 THEN 'GRADE 1'
            WHEN salary > 200 AND salary < 5000 THEN 'GRADE 2'
            ELSE 'GRADE 3'
           END CASE
FROM employees;    

ENAM      CASE
----    -------
JOHN    GRADE 2
EDWIN   GRADE 3
KING    GRADE 1