SQL COMMAND · 类型与运算符
CREATE TYPE
定义一种新数据类型
CREATE类型与运算符引入 10(基线)现存至 20 devel1 次语法变更
- 动词
CREATE- 对象
TYPE- 分组
- 类型与运算符
- 引入版本
- 10(基线)
- 状态
- 现存
- 语法变更次数
- 1
- 手册小节数
- 6
版本轨迹
相对 PostgreSQL 17 语法未变,正文有更新。
语法铁道图 PostgreSQL 18
沿轨道从左向右阅读,分岔表示选择,绕行表示可选,回环表示重复。方框为参数,点击带下划线的参数可展开子规则。
CREATE TYPE · 语法 2
CREATE TYPE · 语法 3
CREATE TYPE · 语法 4
CREATE TYPE · 语法 5
语法概要
CREATE TYPEnameAS ( [attribute_namedata_type[ COLLATEcollation] [, ... ] ] ) CREATE TYPEnameAS ENUM ( [ 'label' [, ... ] ] ) CREATE TYPEnameAS RANGE ( SUBTYPE =subtype[ , SUBTYPE_OPCLASS =subtype_operator_class] [ , COLLATION =collation] [ , CANONICAL =canonical_function] [ , SUBTYPE_DIFF =subtype_diff_function] [ , MULTIRANGE_TYPE_NAME =multirange_type_name] ) CREATE TYPEname( INPUT =input_function, OUTPUT =output_function[ , RECEIVE =receive_function] [ , SEND =send_function] [ , TYPMOD_IN =type_modifier_input_function] [ , TYPMOD_OUT =type_modifier_output_function] [ , ANALYZE =analyze_function] [ , SUBSCRIPT =subscript_function] [ , INTERNALLENGTH = {internallength| VARIABLE } ] [ , PASSEDBYVALUE ] [ , ALIGNMENT =alignment] [ , STORAGE =storage] [ , LIKE =like_type] [ , CATEGORY =category] [ , PREFERRED =preferred] [ , DEFAULT =default] [ , ELEMENT =element] [ , DELIMITER =delimiter] [ , COLLATABLE =collatable] ) CREATE TYPEname
描述
CREATE TYPE在当前数据库中注册一种新的数据类型。定义该类型的用户将成为其拥有者。
如果给出了模式名,则该类型会在指定模式中创建;否则会在当前模式中创建。类型名必须不同于同一模式中任何现有类型或域的名称。(由于表也具有关联的数据类型,类型名还必须不同于同一模式中任何现有表的名称。)
如上面的语法概要所示,CREATE TYPE有五种形式。它们分别用于创建复合类型、枚举类型、范围类型、基础类型或shell 类型。下文将依次讨论前四种。shell 类型只是稍后定义某种类型时使用的占位符;它通过执行除类型名外不带任何参数的CREATE TYPE来创建。正如相应小节所述,创建范围类型和基础类型时,需要用 shell 类型作为前向引用。
复合类型
第一种形式的CREATE TYPE创建复合类型。复合类型由属性名和数据类型列表指定。如果某个属性的数据类型支持排序规则,还可以指定该属性的排序规则。复合类型本质上与表的行类型相同,但如果目的只是定义一种类型,使用CREATE TYPE 就不必实际创建表。例如,独立的复合类型可用作函数的参数类型或返回类型。
要创建复合类型,必须对所有属性类型都拥有USAGE 权限。
枚举类型
如第 8.7 节中所述,第二种形式的 CREATE TYPE创建枚举(enum)类型。枚举类型接受一个带引号标签的列表,其中每个标签的长度都必须小于 NAMEDATALEN字节(在标准 PostgreSQL构建中为 64 字节)。(也可以创建零标签的枚举类型,但在使用ALTER TYPE 至少添加一个标签之前,这种类型不能用来保存值。)
范围类型
如第 8.17 节中所述,第三种形式的 CREATE TYPE创建范围类型。
范围类型的subtype可以是任何带有关联 B-树操作符类的类型(该操作符类用于确定范围类型值的顺序)。通常使用子类型默认的 B-树操作符类来确定顺序;若要使用非默认操作符类,可用subtype_opclass指定其名称。如果子类型支持排序规则,而你希望在范围排序中使用非默认排序规则,可用 collation选项指定所需排序规则。
可选的canonical函数必须接受一个正在定义的范围类型值作为参数,并返回同一类型的值。在适用时,它用于将范围值转换为规范形式。更多信息见第 8.17.8 节。创建 canonical函数有些棘手,因为它必须在声明范围类型之前定义。为此,必须先创建一种 shell 类型,它除了名称和拥有者外没有任何属性,只是一个占位符类型。这可通过执行不带任何附加参数的命令CREATE TYPE 完成。然后就可以把该 shell 类型用作参数类型和结果类型来声明该函数,最后再用同一名称声明范围类型。这样会自动用有效的范围类型替换 shell 类型条目。name
可选的subtype_diff 函数必须接受两个subtype类型的值作为参数,并返回一个表示这两个给定值之差的double precision值。虽然这是可选的,但提供该函数可显著提高该范围类型列上 GiST 索引的效率。详见第 8.17.8 节。
可选的multirange_type_name参数指定对应多范围类型的名称。若未指定,将按如下规则自动选择:如果范围类型名称包含子串range,则把类型名中的 range替换为multirange,作为多范围类型名;否则就在范围类型名后附加 _multirange后缀。
要创建范围类型,你必须拥有子类型的 USAGE 权限。
基础类型
第四种形式的CREATE TYPE创建一种新的基础类型(标量类型)。要创建新的基础类型,你必须是超级用户。(这样限制是因为错误的类型定义可能使服务器陷入混乱,甚至导致其崩溃。)
这些参数可以按任意顺序出现,不必局限于上面展示的顺序,而且大多数都是可选的。在定义该类型之前,必须先注册两个或更多函数(使用 CREATE FUNCTION)。支持函数 input_function和 output_function是必需的;receive_function、send_function、type_modifier_input_function、type_modifier_output_function、analyze_function以及 subscript_function则是可选的。通常这些函数必须用 C 或其他低级语言编写。
input_function将类型的外部文本表示转换为该类型的操作符和函数所使用的内部表示。output_function 执行相反的转换。输入函数可以声明为接受一个cstring 参数,或者接受三个参数,类型分别为cstring、oid、integer。第一个参数是以 C 字符串表示的输入文本,第二个参数是该类型自身的 OID(数组类型例外,此时传入的是其元素类型的 OID),第三个参数是在已知情况下目标列的 typmod(未知则传入 -1)。输入函数必须返回该数据类型本身的值。通常输入函数应声明为 STRICT;否则,在读取 NULL 输入值时会以 NULL 作为第一个参数调用它。除非函数抛出错误,否则在这种情况下仍必须返回 NULL。(这种情况主要是为了支持可能需要拒绝 NULL 输入的域输入函数。)输出函数必须声明为接受一个新数据类型参数,并且必须返回cstring类型。对于 NULL 值不会调用输出函数。
可选的receive_function 把类型的外部二进制表示转换为内部表示。如果未提供此函数,该类型就不能参与二进制输入。外部二进制表示应选择为既能低成本转换为内部形式,又具有合理可移植性。(例如,标准整数数据类型把网络字节序用作外部二进制表示,而内部表示则使用机器的本地字节序。)receive_function 应进行充分检查以确保值有效。它可以声明为接受一个 internal参数,或者接受三个参数,类型分别为 internal、oid、integer。第一个参数是指向保存已接收字节串的StringInfo缓冲区的指针;其余可选参数与文本输入函数相同。接收函数必须返回该数据类型本身的值。通常,接收函数应声明为 STRICT;否则,在读取 NULL 输入值时会以 NULL 作为第一个参数调用它。除非函数抛出错误,否则在这种情况下仍必须返回 NULL。(这种情况主要是为了支持可能需要拒绝 NULL 输入的域接收函数。)类似地,可选的 send_function把内部表示转换为外部二进制表示。如果未提供此函数,该类型就不能参与二进制输出。发送函数必须声明为接受一个新数据类型参数,并且必须返回 bytea类型。对于 NULL 值不会调用发送函数。
读到这里,你可能会问:既然新类型本身还没创建,输入和输出函数怎么能声明为返回或接受这个新类型呢?答案是,应先把该类型定义为一种 shell 类型,它除了名称和拥有者外没有任何属性,只是一个占位符类型。这可通过执行不带任何附加参数的命令 CREATE TYPE 完成。然后就可以定义引用该 shell 类型的 C I/O 函数。最后,再用带完整定义的nameCREATE TYPE替换该 shell 条目,生成一个完整且有效的类型定义,此后新类型就能正常使用。
如果该类型支持修饰符,也就是附加在类型声明上的可选约束,例如 char(5)或numeric(30,2),就需要可选的type_modifier_input_function和 type_modifier_output_function。PostgreSQL允许用户定义类型接受一个或多个简单常量或标识符作为修饰符。不过,这些信息必须能够打包成单个非负整数值,以便存储在系统目录中。声明的修饰符会以 cstring数组的形式传递给type_modifier_input_function。它必须检查这些值是否有效(若无效则抛出错误),若有效则返回一个非负integer值,该值将作为列的“typmod”存储。如果该类型没有type_modifier_input_function,就会拒绝类型修饰符。type_modifier_output_function 则把内部整数 typmod 值转换回适合用户显示的正确形式。它必须返回一个cstring值,即精确追加到类型名后的字符串;例如,numeric的该函数可能返回 (30,2)。允许省略type_modifier_output_function;在这种情况下,默认显示格式只是把存储的 typmod 整数值放在圆括号中。
可选的analyze_function 为该数据类型的列执行类型专用的统计信息收集。默认情况下,如果该类型有默认的 B-树操作符类,ANALYZE将尝试使用该类型的“等于”和“小于”操作符收集统计信息。对于非标量类型,这种行为很可能不合适,因此可以通过指定自定义分析函数来覆盖。分析函数必须声明为接受一个 internal参数并返回boolean结果。分析函数的详细 API 见src/include/commands/vacuum.h。
可选的subscript_function允许在 SQL 命令中对该数据类型进行下标访问。指定此函数并不会使该类型被视为“真正的”数组类型;例如,它不会成为 ARRAY[]构造结果类型的候选者。但如果对这种类型的值使用下标是提取其中数据的一种自然记法,就可以编写 subscript_function 来定义其含义。下标函数必须声明为接受一个internal 参数,并返回一个internal结果,也就是指向实现下标操作的方法(函数)结构体的指针。下标函数的详细 API 见 src/include/nodes/subscripting.h。阅读 src/backend/utils/adt/arraysubs.c中的数组实现,或更简单的contrib/hstore/hstore_subs.c 代码,也可能有所帮助。更多信息见下文数组类型。
虽然新类型内部表示的细节只有 I/O 函数以及你为该类型编写的其他函数才知道,但仍有若干内部表示属性必须向 PostgreSQL声明。其中最重要的是 internallength。基础类型可以是定长的,此时internallength为正整数;也可以是变长的,此时将internallength设为 VARIABLE。(在内部,这通过把 typlen设为 -1 表示。)所有变长类型的内部表示都必须以一个 4 字节整数开头,用来给出该类型该值的总长度。(注意,如第 66.2 节中所述,长度字段通常是经过编码的;直接访问它并不明智。)
可选标志PASSEDBYVALUE表示该数据类型的值按值传递,而不是按引用传递。按值传递的类型必须是定长的,且其内部表示不能大于Datum类型的大小(某些机器上为 4 字节,另一些为 8 字节)。
alignment参数指定该数据类型所需的存储对齐方式。允许的值分别对应按 1、2、4 或 8 字节边界对齐。注意,变长类型的对齐至少必须为 4,因为它们的第一个组成部分必然是一个int4。
storage参数允许为变长数据类型选择存储策略。(定长类型只允许 plain。)plain表示该类型数据始终行内存储且不压缩。extended表示系统会先尝试压缩较长的数据值,如果仍然过长,就把该值移出主表行。external允许把值移出主表,但系统不会尝试压缩它。main允许压缩,但不鼓励把值移出主表。(采用这种存储策略的数据项在没有其他办法让一行适配时仍可能被移出主表,但与extended和external 数据项相比,它们会被优先保留在主表中。)
如第 66.2 节和第 36.13.1 节所述,除plain之外所有storage值都意味着该数据类型的函数能够处理经过TOAST 处理的值。具体指定哪一种其他值,只是决定可 TOAST 数据类型列的默认 TOAST 存储策略;用户仍可使用ALTER TABLE SET STORAGE 为单个列选择其他策略。
like_type参数提供了指定数据类型基本表示属性的另一种方法:从某个现有类型复制这些属性。internallength、passedbyvalue、alignment和 storage的值都从指定类型复制而来。(虽然可以通过同时给出LIKE子句和这些选项来覆盖其中某些值,但通常不建议这样做。)当新类型的底层实现以某种方式“借用”现有类型时,以这种方式指定表示属性尤其有用。
category和 preferred参数可用于在存在歧义时帮助控制应用哪一种隐式类型转换。每种数据类型都属于一个由单个 ASCII 字符命名的类别,并且在其类别内要么是“首选”的,要么不是。当这一规则有助于解析重载函数或操作符时,解析器会优先转换为首选类型(但只会从同一类别中的其他类型转换)。更多细节见第 10 章。对于与任何其他类型之间都没有隐式类型转换的类型,保持这些设置的默认值就足够了。不过,对于一组彼此存在隐式类型转换的相关类型,把它们都标记为属于同一类别,并选择一两个“最通用”的类型作为该类别的首选类型,通常会有帮助。category参数在将用户定义类型加入现有内置类别(例如数值类型或字符串类型)时尤其有用。不过,也可以创建全新的纯用户定义类型类别。为这种类别命名时,可选择任一非大写字母的 ASCII 字符。
如果用户希望该数据类型列的默认值不是空值,可以指定默认值。用 DEFAULT关键字指定默认值。(该默认值可以被附加到具体列上的显式DEFAULT子句覆盖。)
若要表明一种类型是定长数组类型,可用ELEMENT 关键字指定数组元素的类型。例如,要定义由 4 字节整数(int4)构成的数组,可指定 ELEMENT = int4。更多细节见下文数组类型。
若要指定该类型数组在外部表示中用于分隔各值的分隔符,可把 delimiter设为特定字符。默认分隔符是逗号(,)。注意,这个分隔符关联的是数组元素类型,而不是数组类型本身。
如果可选的布尔参数 collatable为真,则该类型的列定义和表达式可以通过COLLATE子句携带排序规则信息。是否实际使用这些排序规则信息取决于操作该类型的函数实现;仅仅把类型标记为支持排序规则并不会自动实现这一点。
数组类型
每当创建用户定义类型时,PostgreSQL 都会自动创建一个关联的数组类型,其名称由元素类型名前加一个下划线组成;必要时还会截断,以保持其长度小于 NAMEDATALEN字节。(如果这样生成的名称与现有类型名冲突,就会重复这一过程,直到找到不冲突的名称。)这种隐式创建的数组类型是变长的,并使用内置输入/输出函数 array_in和array_out。此外,系统在处理基于该用户定义类型的ARRAY[] 等构造时,使用的也是这种类型。该数组类型会跟踪其元素类型的拥有者或模式的任何变化,并在元素类型被删除时一并删除。
如果系统会自动创建正确的数组类型,你可能会合理地问,为什么还需要ELEMENT选项。ELEMENT最主要的用途是:你正在创建一种定长类型,而它在内部恰好是若干相同元素组成的数组,并且除了为整个类型提供的操作之外,你还希望允许通过下标直接访问这些元素。例如,类型point在内部就表示为两个浮点数,可以用point[0]和 point[1]访问。注意,这种机制只适用于内部形式恰好是一串相同定长字段的定长类型。由于历史原因(也就是说这显然不对,但现在改已经太晚了),定长数组类型的下标从零开始,而变长数组则从一开始。
指定SUBSCRIPT选项允许对某种数据类型使用下标,即使系统在其他方面并不把它视为数组类型。上面刚描述的定长数组行为,实际上是由SUBSCRIPT处理函数 raw_array_subscript_handler实现的;如果你为定长类型指定了ELEMENT而没有同时写 SUBSCRIPT,系统就会自动使用该函数。
指定自定义SUBSCRIPT函数时,通常不必再指定 ELEMENT,除非SUBSCRIPT处理函数需要查阅typelem来确定应返回什么。请注意,指定ELEMENT会让系统认为新类型包含元素类型,或者在物理上以某种方式依赖元素类型;因此,例如,如果存在该依赖类型的列,就不允许更改元素类型的属性。
参数
name要创建的类型名称(可选地带有模式限定)。
attribute_name复合类型的一个属性(列)的名称。
data_type将成为复合类型一列的现有数据类型名称。
collation要与复合类型的某一列或范围类型关联的现有排序规则名称。
label表示枚举类型某个值所关联文本标签的字符串字面量。
subtype范围类型所表示范围的元素类型名称。
subtype_operator_class子类型的 B-树操作符类名称。
canonical_function范围类型规范化函数的名称。
subtype_diff_function子类型差分函数的名称。
multirange_type_name对应多范围类型的名称。
input_function将数据从类型的外部文本形式转换为内部形式的函数名。
output_function将数据从类型的内部形式转换为外部文本形式的函数名。
receive_function将数据从类型的外部二进制形式转换成内部形式的函数名。
send_function将数据从类型的内部形式转换为外部二进制形式的函数名。
type_modifier_input_function将类型的修饰符数组转换为内部形式的函数名。
type_modifier_output_function将类型修饰符的内部形式转换为外部文本形式的函数名。
analyze_function为该数据类型执行统计分析的函数名。
subscript_function定义对该数据类型值进行下标访问时行为的函数名。
internallength一个数字常量,用于指定新类型内部表示的字节长度。默认假定它是变长的。
alignment该数据类型的存储对齐需求。如果被指定,它必须是
char、int2、int4或者double。默认是int4。storage该数据类型的存储策略。如果被指定,必须是
plain、external、extended或者main。默认是plain。like_type与新类型具有相同表示形式的现有数据类型名称。除非在本
CREATE TYPE命令的其他位置显式覆盖,否则internallength、passedbyvalue、alignment和storage的值都会从该类型复制。category该类型的类别码(单个 ASCII 字符)。默认值是表示“用户定义类型”的
'U'。其他标准类别码见表 52.65。你也可以选择其他 ASCII 字符来创建自定义类别。preferred若该类型是其类型类别中的首选类型,则为真,否则为假。默认值为假。在现有类型类别中创建新的首选类型时要格外小心,因为这可能导致出人意料的行为变化。
default该数据类型的默认值。若省略,默认值为 null。
element正在创建的类型是数组;该参数指定数组元素类型。
delimiter在由该类型构成的数组中各值之间使用的分隔符字符。
collatable如果该类型的操作可以使用排序规则信息,则为真。默认为假。
注解
由于数据类型一旦创建,其使用方式就不再受限制,因此创建基础类型或范围类型,相当于对类型定义中提到的那些函数授予公共执行权限。这对适合用于类型定义的那类函数来说通常不是问题。但如果设计一种类型时,需要在把它转换为外部形式或从外部形式转换回来时使用“秘密”信息,就应当三思。
在PostgreSQL 8.3 之前,自动生成的数组类型名称总是恰好等于元素类型名称前加一个下划线字符(_)。(因此,类型名称的长度限制比其他名称少一个字符。)虽然现在通常仍是这样,但在名称达到最大长度或与以下划线开头的用户类型名冲突时,数组类型名称可能与此不同。因此,依赖这一约定编写代码的做法已经弃用。请改用 pg_type.typarray 来定位与给定类型关联的数组类型。
建议避免使用以下划线开头的类型名和表名。虽然服务器会改变生成的数组类型名称以避免与用户给定的名称冲突,但仍然存在混淆风险,特别是对旧客户端软件而言,它们可能会假定以下划线开头的类型名总是表示数组。
在PostgreSQL 8.2 之前,不存在 shell 类型创建语法CREATE TYPE 。创建新基础类型的做法是先创建它的输入函数。在这种做法下,PostgreSQL会首先把新数据类型名视为输入函数的返回类型。此时 shell 类型会被隐式创建,然后就可以在其余 I/O 函数的定义中引用它。这种做法仍然有效,但已弃用,并且可能在未来某个版本中被禁止。另外,为避免由于函数定义中的简单拼写错误而意外使系统目录充满 shell 类型,只有在输入函数用 C 编写时,才会以这种方式创建 shell 类型。name
在PostgreSQL 16 及更高版本中,基础类型的输入函数最好使用新的 errsave()/ereturn()机制返回“软”错误,而不是像早期版本那样抛出 ereport()异常。更多信息见 src/backend/utils/fmgr/README。
示例
这个示例创建一种复合类型,并在函数定义中使用它:
CREATE TYPE compfoo AS (f1 int, f2 text);
CREATE FUNCTION getfoo() RETURNS SETOF compfoo AS $$
SELECT fooid, fooname FROM foo
$$ LANGUAGE SQL;
这个示例创建一种枚举类型,并在表定义中使用它:
CREATE TYPE bug_status AS ENUM ('new', 'open', 'closed');
CREATE TABLE bug (
id serial,
description text,
status bug_status
);
这个示例创建一种范围类型:
CREATE TYPE float8_range AS RANGE (subtype = float8, subtype_diff = float8mi);
这个示例创建基础类型box,然后在表定义中使用它:
CREATE TYPE box;
CREATE FUNCTION my_box_in_function(cstring) RETURNS box AS ... ;
CREATE FUNCTION my_box_out_function(box) RETURNS cstring AS ... ;
CREATE TYPE box (
INTERNALLENGTH = 16,
INPUT = my_box_in_function,
OUTPUT = my_box_out_function
);
CREATE TABLE myboxes (
id integer,
description box
);
如果box的内部结构是由四个 float4元素构成的数组,则也可以改为这样写:
CREATE TYPE box (
INTERNALLENGTH = 16,
INPUT = my_box_in_function,
OUTPUT = my_box_out_function,
ELEMENT = float4
);
这样就能通过下标访问 box 值的各个分量。除此之外,该类型的行为与前例相同。
这个示例创建一种大对象类型,并在表定义中使用它:
CREATE TYPE bigobj (
INPUT = lo_filein, OUTPUT = lo_fileout,
INTERNALLENGTH = VARIABLE
);
CREATE TABLE big_objs (
id integer,
obj bigobj
);
更多示例(包括配套的输入和输出函数)请见第 36.13 节。
兼容性
第一种CREATE TYPE形式,即创建复合类型的形式,符合SQL标准。其他形式都是 PostgreSQL扩展。SQL标准中的CREATE TYPE 语句还定义了PostgreSQL尚未实现的其他形式。
支持创建零属性的复合类型,是 PostgreSQL对标准的一种特有背离(类似于CREATE TABLE中的同类情况)。
另见
语法演化
相邻大版本之间的差异,新的在前。版本号链接到对应快照。
PostgreSQL 18← 17正文更新
正文更新PostgreSQL 17← 16正文更新
正文更新PostgreSQL 16← 15正文更新
正文更新PostgreSQL 15← 14正文更新
正文更新PostgreSQL 14← 13语法变化
+ [ , MULTIRANGE_TYPE_NAME = multirange_type_name ]+ [ , ANALYZE = analyze_function ]+ [ , SUBSCRIPT = subscript_function ]正文更新PostgreSQL 13← 12正文更新
正文更新PostgreSQL 12← 11正文更新
正文更新PostgreSQL 11← 10正文更新
正文更新
同组命令
| 命令 | 动词 | 对象 | 版本变动 | 最近变更 |
|---|---|---|---|---|
CREATE CAST | CREATE | CAST | — | |
| 定义一种新的类型转换 | 现存 | |||
DROP CAST | DROP | CAST | — | |
| 移除一个类型转换 | 现存 | |||
CREATE COLLATION | CREATE | COLLATION | 162 次 | |
| 定义一种新排序规则 | 现存 | |||
ALTER COLLATION | ALTER | COLLATION | 141 次 | |
| 更改排序规则的定义 | 现存 | |||
DROP COLLATION | DROP | COLLATION | — | |
| 删除一个排序规则 | 现存 | |||
CREATE CONVERSION | CREATE | CONVERSION | — | |
| 定义一个新的编码转换 | 现存 | |||
ALTER CONVERSION | ALTER | CONVERSION | 141 次 | |
| 更改一个转换的定义 | 现存 | |||
DROP CONVERSION | DROP | CONVERSION | — | |
| 移除一个转换 | 现存 | |||
CREATE DOMAIN | CREATE | DOMAIN | 171 次 | |
| 定义一个新域 | 现存 | |||
ALTER DOMAIN | ALTER | DOMAIN | 142 次 | |
| 更改一个域的定义 | 现存 | |||
DROP DOMAIN | DROP | DOMAIN | — | |
| 移除一个域 | 现存 | |||
CREATE OPERATOR | CREATE | OPERATOR | 192 次 | |
| 定义一个新的操作符 | 现存 | |||
ALTER OPERATOR | ALTER | OPERATOR | 172 次 | |
| 更改一个操作符的定义 | 现存 | |||
DROP OPERATOR | DROP | OPERATOR | 141 次 | |
| 移除一个操作符 | 现存 | |||
CREATE OPERATOR CLASS | CREATE | OPERATOR CLASS | — | |
| 定义一个新的操作符类 | 现存 | |||
ALTER OPERATOR CLASS | ALTER | OPERATOR CLASS | 141 次 | |
| 更改一个操作符类的定义 | 现存 | |||
DROP OPERATOR CLASS | DROP | OPERATOR CLASS | — | |
| 移除一个操作符类 | 现存 | |||
CREATE OPERATOR FAMILY | CREATE | OPERATOR FAMILY | — | |
| 定义一个新的操作符族 | 现存 | |||
ALTER OPERATOR FAMILY | ALTER | OPERATOR FAMILY | 141 次 | |
| 更改一个操作符族的定义 | 现存 | |||
DROP OPERATOR FAMILY | DROP | OPERATOR FAMILY | — | |
| 移除一个操作符族 | 现存 | |||
CREATE TYPE | CREATE | TYPE | 141 次 | |
| 定义一种新数据类型 | 现存 | |||
ALTER TYPE | ALTER | TYPE | 142 次 | |
| 更改类型的定义 | 现存 | |||
DROP TYPE | DROP | TYPE | — | |
| 移除一个数据类型 | 现存 | |||