User-Defined PL/SQL Subtypes
PL/SQL lets you define your own subtypes.
The base type can be any scalar or user-defined PL/SQL data type specifier such as CHAR
, DATE
, or RECORD
(including a previously defined user-defined subtype).
Note:
The information in this topic applies to both user-defined subtypes and the predefined subtypes listed in PL/SQL Predefined Data Types.
Subtypes can:
-
Provide compatibility with ANSI/ISO data types
-
Show the intended use of data items of that type
-
Detect out-of-range values
Topics
Unconstrained Subtypes
An unconstrained subtype has the same set of values as its base type, so it is only another name for the base type.
Therefore, unconstrained subtypes of the same base type are interchangeable with each other and with the base type. No data type conversion occurs.
To define an unconstrained subtype, use this syntax:
SUBTYPE subtype_name IS base_type
For information about subtype_name
and base_type
, see subtype.
An example of an unconstrained subtype, which PL/SQL predefines for compatibility with ANSI, is:
SUBTYPE "DOUBLE PRECISION" IS FLOAT
Example 4-24 User-Defined Unconstrained Subtypes Show Intended Use
In this example, the unconstrained subtypes Balance
and Counter
show the intended uses of data items of their types.
DECLARE SUBTYPE Balance IS NUMBER; checking_account Balance(6,2); savings_account Balance(8,2); certificate_of_deposit Balance(8,2); max_insured CONSTANT Balance(8,2) := 250000.00; SUBTYPE Counter IS NATURAL; accounts Counter := 1; deposits Counter := 0; withdrawals Counter := 0; overdrafts Counter := 0; PROCEDURE deposit ( account IN OUT Balance, amount IN Balance ) IS BEGIN account := account + amount; deposits := deposits + 1; END; BEGIN NULL; END; /
Constrained Subtypes
A constrained subtype has only a subset of the values of its base type.
If the base type lets you specify size, precision and scale, or a range of values, then you can specify them for its subtypes. The subtype definition syntax is:
SUBTYPE subtype_name IS base_type { precision [, scale ] | RANGE low_value .. high_value } [ NOT NULL ]
Otherwise, the only constraint that you can put on its subtypes is NOT
NULL
:
SUBTYPE subtype_name IS base_type [ NOT NULL ]
Note:
The only base types for which you can specify a range of values are PLS_INTEGER
and its subtypes (both predefined and user-defined).
A constrained subtype can be implicitly converted to its base type, but the base type can be implicitly converted to the constrained subtype only if the value does not violate a constraint of the subtype.
A constrained subtype can be implicitly converted to another constrained subtype with the same base type only if the source value does not violate a constraint of the target subtype.
See Also:
-
"subtype_definition ::=" syntax diagram
-
"subtype" semantic description
-
"Example 4-23", "Violating Constraint of SIMPLE_INTEGER Subtype"
Example 4-25 User-Defined Constrained Subtype Detects Out-of-Range Values
In this example, the constrained subtype Balance
detects out-of-range values.
DECLARE SUBTYPE Balance IS NUMBER(8,2); checking_account Balance; savings_account Balance; BEGIN checking_account := 2000.00; savings_account := 1000000.00; END; /
Result:
DECLARE
*
ERROR at line 1:
ORA-06502: PL/SQL: value or conversion error: number precision too large
ORA-06512: at line 9
Example 4-26 Implicit Conversion Between Constrained Subtypes with Same Base Type
In this example, the three constrained subtypes have the same base type. The first two subtypes can be implicitly converted to the third subtype, but not to each other.
DECLARE SUBTYPE Digit IS PLS_INTEGER RANGE 0..9; SUBTYPE Double_digit IS PLS_INTEGER RANGE 10..99; SUBTYPE Under_100 IS PLS_INTEGER RANGE 0..99; d Digit := 4; dd Double_digit := 35; u Under_100; BEGIN u := d; -- Succeeds; Under_100 range includes Digit range u := dd; -- Succeeds; Under_100 range includes Double_digit range dd := d; -- Raises error; Double_digit range does not include Digit range END; /
Result:
DECLARE * ERROR at line 1: ORA-06502: PL/SQL: value or conversion error ORA-06512: at line 12
Subtypes with Base Types in Same Data Type Family
If two subtypes have different base types in the same data type family, then one subtype can be implicitly converted to the other only if the source value does not violate a constraint of the target subtype.
For the predefined PL/SQL data types and subtypes, grouped by data type family, see PL/SQL Predefined Data Types.
Example 4-27 Implicit Conversion Between Subtypes with Base Types in Same Family
In this example, the subtypes Word
and Text
have different base types in the same data type family. The first assignment statement implicitly converts a Word
value to Text
. The second assignment statement implicitly converts a Text
value to Word
. The third assignment statement cannot implicitly convert the Text
value to Word
, because the value is too long.
DECLARE SUBTYPE Word IS CHAR(6); SUBTYPE Text IS VARCHAR2(15); verb Word := 'run'; sentence1 Text; sentence2 Text := 'Hurry!'; sentence3 Text := 'See Tom run.'; BEGIN sentence1 := verb; -- 3-character value, 15-character limit verb := sentence2; -- 6-character value, 6-character limit verb := sentence3; -- 12-character value, 6-character limit END; /
Result:
DECLARE * ERROR at line 1: ORA-06502: PL/SQL: value or conversion error: character string buffer too small ORA-06512: at line 13