Chinaunix首页 | 论坛 | 博客
  • 博客访问: 256578
  • 博文数量: 79
  • 博客积分: 3450
  • 博客等级: 中校
  • 技术积分: 875
  • 用 户 组: 普通用户
  • 注册时间: 2006-06-18 13:12
文章分类

全部博文(79)

文章存档

2011年(1)

2010年(3)

2009年(19)

2008年(23)

2007年(15)

2006年(18)

我的朋友

分类: Oracle

2008-05-07 10:55:27

CREATE VIEW
Name
CREATE VIEW  --  定义一个视图
Synopsis
CREATE VIEW view AS SELECT query
输入
view
所要创建的视图名称.
query
一个将为视图提供行和列的 SQL 查询.
请参阅 SELECT 语句获取有效参数的更多信息.
输出
CREATE
如果视图创建成功,返回此信息.
ERROR: Relation 'view' already exists
如果在数据库中已经存在所声明的视图.
NOTICE: Attribute 'column' has an unknown type
如果不声明,所创建的视图将有一个未知类型的字段. 例如,下面命令返回一个警告:
CREATE VIEW vista AS SELECT 'Hello World'
然而下面命令将不出现警告:
CREATE VIEW vista AS SELECT text 'Hello World'
描述
CREATE VIEW将定义一个表的视图. 这个视图不是物理上实际存在(于磁盘)的.具体的说,自动生成 一个改写索引规则的查询用以支持在视图上的检索.
注意
目前,视图是只读的∶系统将不允许在视图上插入,更新,或者删除数据.你可以通过在视图上创建把插入等动作重写为向其它表做合适操作的规则来 实现可更新视图的效果.更多信息详见 CREATE RULE .
使用 DROP VIEW 语句删除视图.
用法
创建一个由所有 Comedy (喜剧)电影组成的视图:
CREATE VIEW kinds AS
    SELECT *
    FROM films
    WHERE kind = 'Comedy';
SELECT * FROM kinds;
 code |           title          | did | date_prod | kind | len
-------+---------------------------+-----+------------+--------+-------
 UA502 | Bananas                   | 105 | 1971-07-13 | Comedy | 01:22
 C_701 | There's a Girl in my Soup | 107 | 1970-06-11 | Comedy | 01:36
(2 rows)  
兼容性 SQL92  
 为 CREATE VIEW 声明了一些附加的功能:
CREATE VIEW view [ column [, ...] ]
    AS SELECT expression [ AS colname ] [, ...]
    FROM table [ WHERE condition ]
    [ WITH [ CASCADE | LOCAL ] CHECK OPTION ]  
完整的命令可选的子句是:
CHECK OPTION
这个选项用于可更新视图. 所有对视图的 INSERT 和 UPDATE 都要经过视图定义条件的校验. 如果 没有通过校验,更新将被拒绝.
LOCAL
对这个视图进行完整性检查.
CASCADE
对此视图和任何相关视图进行完整性检查. 在既没有声明 CASCADE 也没有声明 LOCAL 时,假设为 CASCADE.
--------------------------------------------------------------------------------
DECLARE
DECLARE
Name
DECLARE  --  定义一个游标
Synopsis
DECLARE cursorname [ BINARY ] [ INSENSITIVE ] [ SCROLL ]
    CURSOR FOR query
    [ FOR { READ ONLY | UPDATE [ OF column [, ...] ] ]
输入
cursorname
将在随后 FETCH 操作中使用的游标名.
BINARY
令游标以二进制而不是文本格式获取数据.
INSENSITIVE
 关键字, 表明从游标检索出来的数据不应该被其他进程或游标的更新动作影响. 因为在 PostgreSQL 里,游标的操作总是发生在事务 里,所以总是符合上面描述.这个关键字没有作用.
SCROLL
 关键字,表明每个 FETCH 操作可以检索出多行数据. 因为在PostgreSQL 在任何情况下都允许这样, 所以这个关键字没有作用.
query
一个 SQL 查询,它提供由游标控制的行. 请参考 SELECT 语句获取有关有效参数的详细信息.
READ ONLY
 关键字,表明游标将用于只读模式. 因为这是 PostgreSQL 唯一的游标访问模式,所以该关键字没有作用.
UPDATE
 关键字,表明游标将被用于更新表. 因为游标更新目前还不被 PostgreSQL 支持,所以这个关键字将产生一个错误信息.
column
将被更新的列.因为游标更新目前不被 PostgreSQL 支持, 所以 UPDATE 子句将产生一个错误信息.
输出
SELECT
如果 SELECT 成功运行,返回此信息.
NOTICE: Closing pre-existing portal "cursorname"
如果在当前的事务块中此游标名称已经定义,返回此信息. 前面定义的游标被丢弃.
ERROR: DECLARE CURSOR may only be used in begin/end transaction blocks
如果一个游标没有在事务块内部定义,返回此信息.
描述
DECLARE允许用户创建游标, 用于在一个大的查询里面检索少数几行数据. 使用 FETCH,游标可以既可以返回文本也可以返回二进制格式。 .
通常游标返回文本格式,要么是 ASCII 要么是某种由 PostgreSQL 特定的后端决定的编码方式. 因为数据在系统内部是用二进制格式存储的, 系统必须对数据做一定转换以生成文本格式.另外,文本格式一般都比对应的二进制格式占的存储空间大. 一旦格式转换回文本,客户应用需要将文本转换为二进制格式来操作. BINARY 游标给你返回内部二进制形态的数据。
作为例子,如果查询从一个整数列返回一个一, 在通常的游标里你将获得一个字符串'1'而如果是一个二进制查询,你将得到一个 4-字节的等于ctrl-A('^A')的数值.
游标应该小心使用 BINARY. 一些用户应用如 psql 是不识别二进制游标的, 而且期望返回的数据是文本格式.
而且,字符串表示方式是与硬件体系无关的, 而二进制格式会因不同的硬件体系不同而不同,而且 PostgreSQL 对二进制游标不做字节序解析或者其他格式转换 。 因此,如果你的客户机和服务器使用不同的格式 (如: "高位高字节" 和 "底位底字节").你可能就不会希望你的数据 以二进制格式返回.所以二进制游标将比文本略微快一点,因为二进制在服务器和客户端的数据传输中有较少的转换.
小技巧: 如果你希望用 ASCII 显示数据, 将数据以 ASCII 模式访问将节省客户端的工作.
注意
游标只能在事务中使用.使用 BEGIN, COMMIT和 ROLLBACK定义一个事务块。
在 中游标只能在嵌入 SQL (ESQL) 的应用中使用. PostgreSQL 后端没有一个明确的 OPEN cursor 语句;一个游标被认为在定义时就已经打开了. 不过,PostgreSQL嵌入的 SQL 预编译器, ecpg, 支持 习惯,包括那些和 DECLARE 和 OPEN 相关的语句.
用法
定义一个游标:
DECLARE liahona CURSOR
    FOR SELECT * FROM films;  
兼容性 SQL92  
 只允许在嵌入的 SQL 中和模块中使用游标. PostgreSQL 允许交互地使用游标. 允许嵌入或模块的游标更新数据库信息. 所有 PostgreSQL 的游标都是只读的. BINARY 关键字是 PostgreSQL 扩展.
--------------------------------------------------------------------------------
DELETE
DELETE
Name
DELETE  --  删除一个表中的行
Synopsis
DELETE FROM [ ONLY ] table [ WHERE condition ]
输入
table
一个现存表的名字
condition
这是一个 SQL 选择查询,它返回要被删除的行.
请参考 SELECT 语句获取关于 WHERE 子句的更多信息.
输出
DELETE count
如果行被成功的删除返回此信息. count 是要被删除的行数.
如果 count 为 0, 没有行被删除.
描述
DELETE从指明的表里删除满足 WHERE condition (条件)的行.
如果 condition (WHERE 子句)不存在, 效果是删除表中所有行.结果是一个有效的空表.
小技巧: TRUNCATE 是一个 PostgreSQL 扩展, 它提供一个更快的从表中删除所有行的机制。
缺省时DELETE将删除所声明的表和所有它的子表的记录. 如果你希望只更新提到的表,你应该使用OLNY子句.
要对表进行修改,你必须有写权限,同样也必须有读表的权限,这样才能对符合 condition(条件) 的值进行读取操作.
用法
删除所有电影(films)但不删除音乐(musicals):
DELETE FROM films WHERE kind <> 'Musical';
SELECT * FROM films;
 code |           title           | did | date_prod | kind   | len
-------+---------------------------+-----+------------+---------+-------
 UA501 | West Side Story           | 105 | 1961-01-03 | Musical | 02:32
 TC901 | The King and I            | 109 | 1956-08-11 | Musical | 02:13
 WD101 | Bed Knobs and Broomsticks | 111 |            | Musical | 01:57
(3 rows)
清空表 films:
DELETE FROM films;
SELECT * FROM films;
 code | title | did | date_prod | kind | len
------+-------+-----+-----------+------+-----
(0 rows)
兼容性 SQL92  
 允许定位的 DELETE (删除)语句:
DELETE FROM table WHERE
    CURRENT OF cursor   
这里 cursor 表示一个打开的游标. PostgreSQL 里交互式游标是只读的.
--------------------------------------------------------------------------------
DROP AGGREGATE
DROP AGGREGATE
Name
DROP AGGREGATE  --  删除一个用户定义的聚集函数
Synopsis
DROP AGGREGATE name type
输入
name
现存的聚集函数名。
type
现存的聚集函数的输入数据类型,或者 * -- 如果这个聚集函数接受任意输入类型.(请参考 PostgreSQL 用户手册 获取关于数据类型的更多信息)。
输出
DROP
命令成功的返回信息.
ERROR: RemoveAggregate: aggregate 'name' for type type does not exist
如果声明的函数在数据库中不存在,返回此信息.
描述
DROP AGGREGATE将删除对一个现存聚集函数的所有索引. 执行这条命令的用户必须是该聚集函数的所有者.
注意
使用 CREATE AGGREGATE语句创建一个聚集函数。
用法
将类型 int4的聚集函数 myavg 删除:
DROP AGGREGATE myavg(int4);
兼容性 SQL92 
在 中没有 DROP AGGREGATE语句. 该语句是一个 PostgreSQL 语言的扩展.
--------------------------------------------------------------------------------
DROP DATABASE
Name
DROP DATABASE  --  删除一个数据库.
Synopsis
DROP DATABASE name
输入
name
要被删除的现有数据库名.
输出
DROP DATABASE
如果命令成功执行,返回此命令.
DROP DATABASE: cannot be executed on the currently open database
你不能和准备删除的数据库建立联接.你需要和 template1 或者任何其它的数据库相连来运行这些命令.
DROP DATABASE: cannot be executed on the currently open database
执行这条命令之前你必须先结束正在处理的事务。
描述
DROP DATABASE删除一个现存数据库的目录入口并且删除包含数据的目录.只有数据库所有者能够执行这条命令(通常也是数据库创建者).
DROP DATABASE不能撤销,小心使用.
注意
这条命令在和目标数据库联接时不能执行. 通常更好的做法是用 dropdb脚本代替,该脚本是此命令的一个封装。 ,
请参考 CREATE DATABASE语句获取如何创建数据库的信息.
兼容性 SQL92 
DROP DATABASE是一个 PostgreSQL 语言的扩展. 在 中没有这条命令.
--------------------------------------------------------------------------------
DROP FUNCTION
Name
DROP FUNCTION  --  删除一个用户定义的函数
Synopsis
DROP FUNCTION name ( [ type [, ...] ] )
输入
name
现存的函数名称.
type
函数参数的类型.
输出
DROP
命令成功执行的返回信息.
NOTICE RemoveFunction: Function "name" ("types") does not exist
如果当前数据库里不存在所声明的函数,返回此信息.
描述
DROP FUNCTION 将删除一个现存的函数的引用.要执行这条命令,用户必须是函数的所有者. 必须声明函数的输入参数类型,因为几个不同的函数可能会有同样的名字 和不同的参数列表.
注意
请参考 CREATE FUNCTION 获取创建聚集函数的信息.
对依赖于该函数的类型, 操作符访问方式或者触发器是否事先被删除不做任何校验.
用法
这条命令删除平方根函数:
DROP FUNCTION sqrt(int4);  
兼容性 SQL92  
DROP FUNCTION是 PostgreSQL 语言的扩展.
SQL/PSM
SQL/PSM 是一个为实现函数扩展能力而提出的标准. SQL/PSM DROP FUNCTION 语句有下面的语法:
DROP [ SPECIFIC ] FUNCTION name { RESTRICT | CASCADE }
--------------------------------------------------------------------------------
DROP GROUP
DROP GROUP
Name
DROP GROUP  --  删除一个用户组
Synopsis
DROP GROUP name
输入
name
现存组名。
输出
DROP GROUP
成功删除组后返回的信息。
描述
DROP GROUP从数据库中删除指定的组。组中的用户不被删除。 组中的用户不被删除。
使用 CREATE GROUP增加新组,用 ALTER GROUP修改组的成员。
用法
删除一个组:
DROP GROUP staff;
兼容性 SQL92 
里没有 DROP GROUP.
--------------------------------------------------------------------------------
DROP INDEX
Name
DROP INDEX  --  删除一个索引
Synopsis
DROP INDEX index_name [, ...]
输入
index_name
要删除的索引名.
输出
DROP
如果索引成功删除返回的信息.
ERROR: index "index_name" does not exist
如果 index_name 不是这个数据库的索引,返回此信息.
描述
DROP INDEX从数据库中删除一个现存的索引. 要执行这个命令,你必须是索引的所有者. the index.
注意
DROP INDEX是PostgreSQL 语言扩展.
请参考 CREATE INDEX语句获取如何创建索引的信息.
用法
此命令将删除title_idx 索引:
    DROP INDEX title_idx;  
兼容性 SQL92  
 定义用于访问纯关系型数据库的命令. 索引是一个与具体实现相关的特性,因而没有与具体实现相关的特性或定义在 语言里面.
--------------------------------------------------------------------------------
DROP LANGUAGE
DROP LANGUAGE
Name
DROP LANGUAGE  --  删除一个用户定义的过程语言
Synopsis
DROP [ PROCEDURAL ] LANGUAGE 'name'
输入
name
现存语言的名称.
输出
DROP
如果语言成功删除,返回此信息.
ERROR: Language "name" doesn't exist
如果语言 name 没有找到,返回此信息.
描述
DROP PROCEDURAL LANGUAGE将删除曾注册过的过程语言 name.
注意
DROP PROCEDURAL LANGUAGE语句是 PostgreSQL 语言的扩展.
请参考 CREATE LANGUAGE获取如何创建过程语言的信息.
将不会校验用这种语言注册的函数或触发器是否仍然存在. 要想重新使用这些东西而不用删除和重新创建所有这些函数, 函数 pg_proc 的 prolang字段/属性必须调整为为 PL 重新创建的 pg_language 入口的新对象标识( OID).
用法
下面命令删除 PL/Sample 语言:
DROP PROCEDURAL LANGUAGE 'plsample';  
兼容性 SQL92  
在里没有 DROP PROCEDURAL LANGUAGE.
--------------------------------------------------------------------------------
DROP OPERATOR
DROP OPERATOR
Name
DROP OPERATOR  --  删除一个用户定义操作符
Synopsis
DROP OPERATOR id ( lefttype | NONE , righttype | NONE )
输入
id
一个现存的操作符的标识符.
lefttype
该操作符左参数的类型.如果该操作符没有左参数, 写 NONE.
righttype
该操作符右参数的类型.如果该操作符没有右参数, 写 NONE.
输出
DROP
命令成功执行的返回函数.
ERROR: RemoveOperator: binary operator 'oper' taking 'lefttype' and 'righttype' does not exist
如果声明的双目操作符不存在,返回此信息.
ERROR: RemoveOperator: left unary operator 'oper' taking 'lefttype' does not exist
如果声明的左目操作符不存在,返回此信息.
ERROR: RemoveOperator: right unary operator 'oper' taking 'righttype' does not exist
如果声明的右目操作符不存在,返回此信息.
描述
DROP OPERATOR语句从数据库中删除一个现存的操作符. 要执行这个命令,你必须是操作符所有者.
左目操作符的右类型或右目操作符的左类型可以声明为 NONE.
注意
DROP OPERATOR语句是 PostgreSQL 语言扩展.
请参考 CREATE OPERATOR获取如何创建操作符的信息.
删除任何依赖于被删除的操作符的访问模式和操作符表是用户的责任.
用法
将用于int4的幂操作符 a^n 删除:
DROP OPERATOR ^ (int4, int4);  
删除用于boolean变量的左目取反操作符(! b):
DROP OPERATOR ! (none, bool);  
删除用于 int4的阶乘 (! i) : int4:
DROP OPERATOR ! (int4, none);  
兼容性 SQL92  
在里没有 DROP OPERATOR 语句.
--------------------------------------------------------------------------------
DROP RULE
DROP RULE
Name
DROP RULE  --  删除一个重写规则
Synopsis
DROP RULE name [, ...]
输入
name
要删除的现存的规则.
输出
DROP
删除成功返回的信息.
ERROR: Rule or view "name" not found
如果声明的规则不存在,返回此信息.
描述
DROP RULE从声明的 PostgreSQL规则系统里删除一个规则. PostgreSQL 将立即停止使用之并且将会把它从系统表中清理出去.
注意
DROP RULE语句是 PostgreSQL 语言的扩展.
请参考 CREATE RULE 获取如何创建规则的信息.
一旦一个规则被删除掉,该规则所写的历史记录信息将可能不存在.
用法
删除重写规则 newrule:
DROP RULE newrule;  
兼容性 SQL92  
在 中没有DROP RULE.
--------------------------------------------------------------------------------
DROP SEQUENCE
DROP SEQUENCE
Name
DROP SEQUENCE  --  删除一个序列
Synopsis
DROP SEQUENCE name [, ...]
输入
name
序列名.
输出
DROP
序列成功删除后返回的信息.
ERROR: sequence "name" does not exist
如果声明的序列不存在,返回此信息.
描述
DROP SEQUENCE从数据库中删除序列号生成器. 因为目前的序列实现是作为一个特殊的表,所以此语句就象 DROP TABLE 语句一样.
注意
DROP SEQUENCE语句是 Postgres 语言扩展.
请参考 CREATE SEQUENCE 语句获取如何创建一个序列的信息.
用法
从数据库中删除序列 serial:
DROP SEQUENCE serial;  
兼容性 SQL92  
在里没有 DROP SEQUENCE.
--------------------------------------------------------------------------------
DROP TABLE
DROP TABLE
Name
DROP TABLE  --  删除一个表
Synopsis
DROP TABLE name [, ...]
输入
name
要删除的现存表或视图.
输出
DROP
如果命令成功完成,返回此信息.
ERROR: table "name" does not exist
果声明的表或视图在数据库中不存在.
描述
DROP TABLE从数据库中删除表或视图. 只有其所有者才能删除一个表或视图. 使用 DELETE 一个表可能没有任何行,但不会被删除.
如果被删除的表有从索引,它们将首先被删除. 从索引的删除将对所属表的内容没有任何影响.
注意
请参考 CREATE TABLE 和 ALTER TABLE 获取如何创建或更改表的信息.
用法
删除 films 和 distributors表:
DROP TABLE films, distributors;  
兼容性 SQL92 
 为 DROP TABLE 声明了一些附加的功能:
DROP TABLE table { RESTRICT | CASCADE }
  
RESTRICT
确保只有不存在相关视图或完整性约束的表才可以被删除.
CASCADE
任何引用的视图或完整性约束都将被删除.
小技巧: 目前,要删除一个视图,你必须明确删除之.
--------------------------------------------------------------------------------
DROP TRIGGER
DROP TRIGGER
Name
DROP TRIGGER  --  删除一个触发器定义.
Synopsis
DROP TRIGGER name ON table
输入
name
现存的触发器名.
table
表的名称.
输出
DROP
如果触发器成功的删除,返回此信息.
ERROR: DropTrigger: there is no trigger name on relation "table"
如果声明的触发器不存在,返回此信息.
描述
DROP TRIGGER将删除所有对一个现存触发器的引用. 要执行这个命令,当前用户必须是触发器的所有者.
注意
DROP TRIGGER是 PostgreSQL 语言的扩展.
请参考 CREATE TRIGGER 获取如何创建触发器的信息.
用法
删除表films的if_dist_exists触发器:
DROP TRIGGER if_dist_exists ON films;  
兼容性 SQL92  
在里没有DROP TRIGGER.
--------------------------------------------------------------------------------
DROP TYPE
DROP TYPE
Name
DROP TYPE  --  删除一个用户定义数据类型
Synopsis
DROP TYPE typename [, ...]
输入
typename
现存的类型名.
输出
DROP
命令执行成功的返回信息.
ERROR: RemoveType: type 'typename' does not exist
如果声明的类型没有找到,返回此信息.
描述
DROP TYPE将从系统表里删除用户的类型.
只有类型所有者可以删除类型.
注意
DROP TYPE 语句是 PostgreSQL 语言的扩展.
请参考 CREATE TYPE 获取如何创建类型的信息.
用户有责任删除任何使用了被删除类型的操作符,函数,聚集,访问模式, 子类型和表.不过,相关等数组数据类型(由 CREATE TYPE 自动创建)将自动删除.
如果删除了一个内建的类型,后端的行为将不可预测.
用法
删除 box 类型:
DROP TYPE box;
   兼容性 SQL92 
SQL3
DROP TYPE是 SQL3 语句.
--------------------------------------------------------------------------------
DROP USER
DROP USER
Name
DROP USER  --  删除一个数据库用户帐号
Synopsis
DROP USER name
输入
name
一个现存用户的名称.
输出
DROP USER
用户被成功删除的返回信息.
ERROR: DROP USER: user "name" does not exist
如果用户名没有找到,返回此信息.
DROP USER: user "name" owns database "name", cannot be removed
你必须先删除数据库或者改变其所有者。
描述
DROP USER从数据库中删除指定的用户。 它不删除数据库里此用户所有的表,视图或其他对象。 如果该用户拥有任何数据库,你会收到一个错误信息。
使用 CREATE USER增加新用户,用 ALTER USER修改用户属性。 PostgreSQL 还有一个脚本 dropuser,这个脚本和这条命令功能相同(实际上,脚本里调用此命令),但是可以在命令行上运行。
用法
删除一个用户帐户:
DROP USER jonathan;
兼容性 SQL92  
在里没有DROP USER.
--------------------------------------------------------------------------------
DROP VIEW
DROP VIEW
Name
DROP VIEW  --  删除一个视图
Synopsis
DROP VIEW name [, ...]
 
输入
name
现存视图名称.
输出
DROP
命令成功执行的返回.
ERROR: view name does not exist
如果声明的视图在数据库中不存在,返回此信息.
描述
DROP VIEW从数据库中删除一个现存的视图. 执行这条命令必须是视图的所有者.
注意
请参考CREATE VIEW 获取关于如何创建视图的信息.
用法
下面命令将删除视图 kinds:
DROP VIEW kinds;
兼容性 SQL92  
 为 DROP VIEW 声明了一些附加的功能:
DROP VIEW view { RESTRICT | CASCADE }   
输入
RESTRICT
确保只有不存在关联视图或完整性约束的视图可以被删除.
CASCADE
任何引用的视图和完整性约束都将被删除.
注意
目前,要从 PostgreSQL 数据库中删除一个视图, 你必须明确地将其删除.
--------------------------------------------------------------------------------
END
Name
END  --  提交当前的事务
Synopsis
END [ WORK | TRANSACTION ]
输入
WORK
TRANSACTION
可选关键字。没有作用。
输出
COMMIT
事务成功提交后的返回信息。
NOTICE: COMMIT: no transaction in progress
如果没有正在处理的事务,返回此信息。
描述
END是 PostgreSQL 而 -兼容的同义语句是 COMMIT.
注意
关键字 WORK 和 TRANSACTION 是多余的,可以省略。
使用 ROLLBACK退出一个事务。
用法
令所有改变生效:
END WORK;  
兼容性 SQL92  
END是 PostgreSQL 的扩展,提供与 COMMIT相同的功能。
--------------------------------------------------------------------------------
EXPLAIN
EXPLAIN
Name
EXPLAIN  --  显示语句执行规划
Synopsis
EXPLAIN [ VERBOSE ] query    
输入
VERBOSE
显示详细查询规划的标志.
query
任何 query (查询).
输出
NOTICE: QUERY PLAN: plan
PostgreSQL 后端明确的查询规划.
EXPLAIN
查询规划显示后发送的标志.
描述
这条命令显示PostgreSQL规划器为所提供的查询生成的执行规划。执行规划显示查询引用的表是如何被扫描的--- 是简单的顺序扫描,还是 索引扫描等 --- 并且如果引用了多个表, 采用了什么样的连接算法从每个输入的表中取出所需要的记录。
显示出来的最关键的部分是预计的查询执行开销, 这就是规划器对运行该查询所需时间的估计(以磁盘页面存取为单位计量)。实际上显示了两个数字:返回第一条记录前的启动时间, 和返回所有记录的总时间。对于大多数查询而言,关心的是总时间,但是, 在某些环境下,比如一个 EXISTS 子查询里, 规划器将选择最小启动时间而不是最小总时间 (因为执行器在获取一条记录后总是要停下来)。同样, 如果你用一条 LIMIT 子句限制返回的记录数, 规划器会在最终的开销上做一个合理的插值以计算哪个规划开销最省。
VERBOSE 选项输出规划树在系统内部的完整内容, 而不仅仅是一个概要(并且还把它发送给 postmaster 日志文件)。 通常这个选项只是对调试PostgreSQL有用。
注意
在 PostgreSQL 中只有很少的关于使用优化器的开销的文档.通常的关于查询优化的开销的估算可以在数据库的手册中找到. 请参考 程序员手册 中关于索引和基因查询优化器的章节获取更多信息.
用法
显示一个对只有一个 int4 列和 128 行的表的简单查询的查询规划:
EXPLAIN SELECT * FROM foo;
    NOTICE: QUERY PLAN:
Seq Scan on foo (cost=0.00..2.28 rows=128 width=4)
EXPLAIN  
对同一个拥有支持查询 equijoin 条件的索引的表, EXPLAIN 将显示一个不同的规划:
EXPLAIN SELECT * FROM foo WHERE i = 4;
    NOTICE: QUERY PLAN:
Index Scan using fi on foo (cost=0.00..0.42 rows=1 width=4)
EXPLAIN  
最后,同一个拥有支持查询 equijoin 条件的索引的表, EXPLAIN对使用一个聚集函数的查询将显示下面内容:
EXPLAIN SELECT sum(i) FROM foo WHERE i = 4;
    NOTICE: QUERY PLAN:
Aggregate (cost=0.42..0.42 rows=1 width=4)
 -> Index Scan using fi on foo (cost=0.00..0.42 rows=1 width=4)
  
注意这里显示的数字, 甚至还有选择的查询策略都有可能在各个 PostgreSQL版本之间不同--因为规划器在不断改进。
兼容性 SQL92 
在 中没有EXPLAIN 语句.
--------------------------------------------------------------------------------
FETCH
Name
FETCH  --  用游标从表中抓取行
Synopsis
FETCH [ direction ] [ count ] { IN | FROM } cursor
FETCH [ FORWARD | BACKWARD | RELATIVE ] [ # | ALL | NEXT | PRIOR ] { IN | FROM } cursor
输入
direction
selector定义抓取的方向.它可以是下述之一:
FORWARD
抓取后面的行. selector 省略时这是缺省值.
BACKWARD
抓取前面行.
RELATIVE
为 兼容设置的多余键字.
count
count决定抓取几行.可以是下列之一:
#
一个表明抓取几行的整数. 注意负整数等效于改变 FORWARD 和 BACKWARD 属性.
ALL
检索所有剩余的行.
NEXT
等效于声明 count 为 1.
PRIOR
等效于声明 count 为 -1.
cursor
一个打开的游标的名称.
输出
FETCH返回由声明游标定义的查询结果. 如果查询失败,将返回下面的信息:
NOTICE: PerformPortalFetch: portal "cursor" not found
如果 cursor 在前面没有定义,返回此信息.游标必须在一个事务块中定义.
NOTICE: FETCH/ABSOLUTE not supported, using RELATIVE
PostgreSQL 不支持游标的绝对定位.
ERROR: FETCH/RELATIVE at current position is not supported
 允许我们用下面语句在"当前位置"不停地检索游标
FETCH RELATIVE 0 FROM cursor.
PostgreSQL 目前不支持这种用法;实际上,零被保留用于检索所有行, 等效于声明 ALL 关键字.如果使用 RELATIVE 关键字, PostgreSQL 假设用户试图使用 的特性,因而返回此错误.
描述
FETCH允许用户使用游标检索行.所要检索的行数用 # 声明.如果游标中剩下的行小于 #, 那么只有那些可用的抓过来.用关键字 ALL 代替数字将导致游标中所有剩余行被抓过来. 记录可以 FORWARD (向前)抓,也可以 BACKWARD (向后)抓.缺省的方向是 FORWARD (向前).
注意: 可以用负数作为行记数, 符号等效于颠倒抓取方向关键字(FORWARD 和 BACKWARD).例如, FORWARD -1 等效于 BACKWARD 1.
注意
注意 FORWARD 和 BACKWARD 关键字是 PostgreSQL 扩展. 语法也支持,在此命令的第二种形式中声明. 详细的兼容性 SQL92 信息见下面.
在游标中更新数据还不被 PostgreSQL, 支持,因为将游标更新影射回基本表是不太可能的,这一点对 VIEW 更新也一样.因而用户必须显式的使用 UPDATE 命令来更新数据.
游标只能用于事务内部,因为它们存储的数据跨越了多个用户的查询.
使用 MOVE语句改变游标位置.使用 DECLARE语句定义一个游标.使用 BEGIN, COMMIT, 和 ROLLBACK语句获取更多关于事务的信息.
用法
下面的例子用一个游标跨过一个表。
-- 建立一个游标:
BEGIN WORK;
DECLARE liahona CURSOR FOR SELECT * FROM films;
-- 抓取头 5 行到游标 liahona 里:
FETCH FORWARD 5 IN liahona;
 code |          title          | did | date_prod | kind    | len
-------+-------------------------+-----+------------+----------+-------
 BL101 | The Third Man           | 101 | 1949-12-23 | Drama    | 01:44
 BL102 | The African Queen       | 101 | 1951-08-11 | Romantic | 01:43
 JL201 | Une Femme est une Femme | 102 | 1961-03-12 | Romantic | 01:25
 P_301 | Vertigo                 | 103 | 1958-11-14 | Action   | 02:08
 P_302 | Becket                  | 103 | 1964-02-03 | Drama    | 02:28
-- 抓取前面行:
FETCH BACKWARD 1 IN liahona;
 code | title   | did | date_prod | kind   | len
-------+---------+-----+------------+--------+-------
 P_301 | Vertigo | 103 | 1958-11-14 | Action | 02:08
-- 关闭游标并提交事务:
CLOSE liahona;
COMMIT WORK;
兼容性 SQL92 
注意: 非嵌入式游标的使用是 PostgreSQL 扩展.游标的语法和用途与定义与 里定义的嵌入式用法相似。
 允许游标在 FETCH 中的绝对定位, 并且允许将结果放在明确的变量里:
FETCH ABSOLUTE #
    FROM cursor
    INTO :variable [, ...]
   
ABSOLUTE
游标将放置在写明的绝对的行数的位置上.在 PostgreSQL 中所有的行数都是相对数量,所以这一功能不支持.
:variable
目标宿主变量.
--------------------------------------------------------------------------------
GRANT
Name
GRANT  --  定义访问权限
Synopsis
GRANT { { SELECT | INSERT | UPDATE | DELETE | RULE | REFERENCES | TRIGGER } [,...] | ALL [ PRIVILEGES ] }
    ON [ TABLE ] objectname [, ...]    TO { username | GROUP groupname | PUBLIC } [, ...]
描述
GRANT命令将某对象(表,视图,序列) 上的特定权限给予一个用户或者多个用户或者一组用户.这些权限将增加到那些已经赋予的权限上,如果存在这些权限的话.
键字 PUBLIC 表示该权限要赋予所有用户, 包括那些以后可能创建的用户.PUBLIC 可以看做是一个隐含定义好的组,它总是包括所有用户.请注意,任何特定的用户都将拥有直接赋予他/她的权限,加上 他/她所处的任何组,以及再加上赋予 PUBLIC 的权限的总和.
在创建完对象之后,除了对象的创建者之外, 其它用户没有任何访问该对象的权限,除非创建者赋予某些权限. 对对象的创建者而言,没有什么权限需要赋予,因为创建者自动持有所有权限.(不过,创建者出于安全考虑可以选择 废弃一些他自己的权限.请注意赋予和废止权限的能力是创建者与生具来的,并且不会丢失.删除对象的权利也是创建者固有的,并且不能赋予或 撤销.)
可能的权限有∶
SELECT
允许对声明的表,试图,或者序列 SELECT 仁义字段.还允许做 COPY 的源.
INSERT
允许向声明的表 INSERT 一个新行. 同时还允许做 COPY 的目标.
UPDATE
允许对声明的表中任意字段做 UPDATE . SELECT ... FOR UPDATE 也要求这个权限 (除了 SELECT 权限之外).比如, 这个权限允许使用nextval, currval 和 setval.
DELETE
允许从声明的表中 DELETE 行.
RULE
允许在该表/视图上创建规则.(参阅 CREATE RULE 语句.)
REFERENCES
要在一个表上创建一个外键约束,你必须在带参考健字的表上 拥有这个权限.
TRIGGER
允许在声明表上创建触发器.(参阅 CREATE TRIGGER 语句.)
ALL PRIVILEGES
把上面所有权限都一次赋予.PRIVILEGES 关键字在 PostgreSQL 里是可选的, 但是严格的 SQL 要求有这个关键字.
其它命令要求的权限都在相应的命令的参考页上列出.
注意
我们要注意数据库 superusers 可以访问所有对象, 而不会受对象的权限设置影响.这个特点类似 Unix 系统的 root 的权限.和 root 一样,除了必要的情况,总是以超级用户 身分进行操作是不明智的做法.
目前,要在 PostgreSQL 里只对某几列 赋予权限,你必须创建一个拥有那几行的视图然后给那个视图赋予权限.
使用 psql的 \z 命令 获取在现有对象上的与权限有关的信息.
          Database    = lusitania
   +------------------+---------------------------------------------+
   | Relation        |        Grant/Revoke Permissions             |
   +------------------+---------------------------------------------+
   | mytable          | {"=rw","miriam=arwdRxt","group todos=rw"}   |
   +------------------+---------------------------------------------+
   Legend:
         uname=arwR -- privileges granted to a user
   group gname=arwR -- privileges granted to a group
              =arwR -- privileges granted to PUBLIC
                  r -- SELECT ("read")
                  w -- UPDATE ("write")
                  a -- INSERT ("append")
                  d -- DELETE
                  R -- RULE
                  x -- REFERENCES
                  t -- TRIGGER
            arwdRxt -- ALL PRIVILEGES
用 REVOKE 命令删除访问权限.
例子
把表 films 的插入权限赋予所有用户∶
GRANT INSERT ON films TO PUBLIC;
赋予用户manuel对视图kinds的所有权限∶
GRANT ALL PRIVILEGES ON kinds TO manuel;
兼容性 SQL92
在 ALL PRIVILEGES 里的 PRIVILEGES 关键字是必须的.SQL 不支持在一条命令里 对多个表设置权限.
 的 GRANT 语法允许在一个表里 为独立的字段设置权限,并且允许设置一个权限用来给其它人赋予同样的权限∶
GRANT privilege [, ...]
    ON object [ ( column [, ...] ) ] [, ...]
    TO { PUBLIC | username [, ...]
} [ WITH GRANT OPTION ]
SQL 允许对其它类型的对象赋予 USAGE 权限∶CHARACTER SET,COLLATION,TRANSLATION,DOMAIN.
TRIGGER 权限是 SQL99 引入的.RULE 权限是 PostgreSQL 扩展.
又见
REVOKE
--------------------------------------------------------------------------------
INSERT
Name
INSERT  --  在表中创建新行
Synopsis
INSERT INTO table [ ( column [, ...] ) ]
    { DEFAULT VALUES | VALUES ( expression [, ...] ) | SELECT query }
 输入
table
现存表的名称.
column
表 table 中的列/字段名.
DEFAULT VALUES
所有字段都会用NULL或者创建表时用DEFAULT子句声明的值填充.
expression
赋予 column 的一个有效表达式或值.
query
一个有效的查询.请参考 SELECT 语句获取有效参数的进一步描述.
输出
INSERT oid 1
如果只插入了一行,返回此信息. oid OID 是被插入行的数字标识.
INSERT 0 #
如果插入了超过一行,返回此信息. # 是插入的行数.
描述
INSERT允许我们向表中插入新行. 我们可以一次插入一行或多行作为查询结果. 目标列表中的列/字段可以按任何顺序排列.
在目标列中没有出现的列/字段将插入缺省值, 要么是定义了的 DEFAULT 值或者 NULL。 如果向定义为 NOT NULL 的列中插入 NULL 值, PostgreSQL 将拒绝新列。
如果每行的表达式不是正确的数据类型,将试图进行自动的类型转换.
要想向表中插入数据,你必须有插入权限, 同样也要有选择权限用于处理 WHERE 子句里声明的任何表。
用法
向表 films 里插入一行:
INSERT INTO films VALUES
    ('UA502','Bananas',105,'1971-07-13','Comedy',INTERVAL '82 minute');  
在第二个例子里面省略了字段 len 因此在它里面将只存储缺省的 NULL 值:
INSERT INTO films (code, title, did, date_prod, kind)
    VALUES ('T_601', 'Yojimbo', 106, DATE '1961-06-16', 'Drama');
  
向表 distributors 里插入一行;注意只声明了字段 name ,而没有声明的字段 did 将被赋于它的缺省值:
INSERT INTO distributors (name) VALUES ('British Lion');
  
从表 tmp 中插入几行到表 films 中:
INSERT INTO films SELECT * FROM tmp;
  
插入数组(请参考 PostgreSQL 用户手册 获取关于数组的更多信息):
-- 创建一个空的 3x3 游戏板来玩圈-和-叉游戏
-- (所有这些查询创建相同的板属性)
INSERT INTO tictactoe (game, board[1:3][1:3])
    VALUES (1,'{{"","",""},{},{"",""}}');
INSERT INTO tictactoe (game, board[3][3])
    VALUES (2,'{}');
INSERT INTO tictactoe (game, board)
    VALUES (3,'{{,,},{,,},{,,}}');
  
兼容性 SQL92  
INSERT语句与 完全兼容. 可能碰到的关于 query 子句特性的限制在 SELECT语句中有相关文档. .
--------------------------------------------------------------------------------
LISTEN
Name
LISTEN  --  监听一个通知
Synopsis
LISTEN name
输入
name
通知条件名.
输出
LISTEN
成功完成注册后的返回信息.
NOTICE Async_Listen: We are already listening on name
如果这个后端已经注册了该通知条件.
描述
LISTEN将当前 PostgreSQL 后端注册为通知条件 name. 的监听器.
当执行了命令 NOTIFY name 后, 不管是此后端(进程)或者是其他一个联接到同一数据库的后端(进程)执行的, 所有正在监听此通知条件的后端(进程)都将收到通知,并且接下来每个后端将通知与其相连的前端应用.请参考 NOTIFY 获取更多信息.
使用 UNLISTEN 命令,可以将一个后端内已注册的通知条件删除. 同样,后端进程退出时自动删除该后端正在监听的已注册通知条件.
前端应用检测通知事件的方法取决于 PostgreSQL 应用使用的编程接口.如果使用基本的 libpq 库, 应用将 LISTEN 当作普通 SQL 命令使用,而且必须周期地调用 PQnotifies 过程来检测是否有通知到达. 其他像 libpgtcl 接口提供了更高级的控制通知事件的方法;实际上,使用 libpgtcl ,应用程序员不应该直接使用 LISTEN 或 UNLISTEN. 请参考你使用的库的文档获取更多细节.
NOTIFY 的手册页包含更广泛的关于 LISTEN 和 NOTIFY 的使用的讨论.
注意
name可以是任何可以作为名称有效的字符串;它不需要与任何实际表相对应. 如果 notifyname 被双引号包围,它甚至可以不是一个有效的语句串, 而可以是任何小于31字符的字符串.
一些以前的 PostgreSQL, 如果 name 不与任何现存的表名对应就必须用双引号括起来.不管语意上是否正确.现在不再有这个限制了.
用法
在 psql 里配制和执行一个监听/通知序列:
LISTEN virtual;
NOTIFY virtual;
Asynchronous NOTIFY 'virtual' from backend with pid '8448' received.
兼容性 SQL92 
在里没有 LISTEN.
--------------------------------------------------------------------------------
LOAD
Name
LOAD -- 装载或重载一个共享库文件
Synopsis
LOAD 'filename'
描述
装载一个共享库文件到 PostgreSQL 后端的地址空间. 一旦一个文件被装载,如果该文件前面曾经装载过,那么首先卸载它.这条命令 主要用于在一个共享库件修改后卸载和重载它. 要利用这个共享库件,我们必须用 CREATE FUNCTION 命令声明函数.
文件名是和 CREATE FUNCTION 里描写等共享库的 名字相同方法声明的;特别要注意等是我们可以依赖搜索路径和自动附加系统标准共享库扩展名的特点. 参阅程序员手册获取更多细节.
兼容性 SQL92
LOAD是 PostgreSQL 扩展.
又见
CREATE FUNCTION , PostgreSQL 程序员手册
--------------------------------------------------------------------------------
LOCK
Name
LOCK  --  明确地锁定一个表
Synopsis
LOCK [ TABLE ] name
LOCK [ TABLE ] name [, ...] IN lockmode MODE
这里 lockmode 可以是下列之一∶
        ACCESS SHARE | ROW SHARE | ROW EXCLUSIVE | SHARE UPDATE EXCLUSIVE |
        SHARE | SHARE ROW EXCLUSIVE | EXCLUSIVE | ACCESS EXCLUSIVE
输入
name
要锁定的现存的表.
ACCESS SHARE MODE
注意: 这个锁模式对被查询的表自动生效。
这是最小限制的锁模式,只与 ACCESS EXCLUSIVE 模式冲突。它用于保护被查询的表免于被并行的 ALTER TABLE, DROP TABLE 和 VACUUM FULL 对同一表操作的语句修改。
ROW SHARE MODE
注意: 任何 SELECT...FOR UPDATE 语句执行时自动生效。
与 EXCLUSIVE 和 ACCESS EXCLUSIVE 锁模式冲突。
ROW EXCLUSIVE MODE
注意: 任何 UPDATE, DELETE和 INSERT 语句执行时自动生效。
与 SHARE, SHARE ROW EXCLUSIVE, EXCLUSIVE 和 ACCESS EXCLUSIVE 模式冲突。
SHARE UPDATE EXCLUSIVE MODE
Note: 由 VACUUM (没有 FULL) 自动要求.
和SHARE UPDATE EXCLUSIVE,SHARE,SHARE ROW EXCLUSIVE, EXCLUSIVE 和 ACCESS EXCLUSIVE 模式冲突.这个模式保护一个表不被并行的(事务进行)大纲修改和 VACUUM.
SHARE MODE
注意: 任何 CREATE INDEX 语句执行时自动附加。 共享锁住整个表.
与 ROW EXCLUSIVE,SHARE UPDATE EXCLUSIVE, SHARE ROW EXCLUSIVE,EXCLUSIVE 和 ACCESS EXCLUSIVE 模式冲突。这个模式防止一个表的并行数据更新。
SHARE ROW EXCLUSIVE MODE
注意: 这个模式类似 EXCLUSIVE MODE,但是允许其他事务的 ROW SHARE 锁.
与 ROW EXCLUSIVE,SHARE UPDATE EXCLUSIVE, SHARE,SHARE ROW EXCLUSIVE,EXCLUSIVE 和 ACCESS EXCLUSIVE 模式冲突。
EXCLUSIVE MODE
注意: 这个模式同样比 SHARE ROW EXCLUSIVE 更有约束力.它阻塞所有并行的 ROW SHARE/SELECT... FOR UPDATE 查询。
与 ROW SHARE,ROW EXCLUSIVE,SHARE UPDATE EXCLUSIVE, SHARE,SHARE ROW EXCLUSIVE,EXCLUSIVE 和 ACCESS EXCLUSIVE 模式冲突。 这个模式只允许并发的 ACCESS SHARE,也就是说只有从表中读取数据 可以和一个持有这个锁模式的事务并发执行.
ACCESS EXCLUSIVE MODE
注意: 由语句 ALTER TABLE, DROP TABLE,VACUUM FULL 执行时自动生效。这是最严格的约束锁,它 保护一个被锁定的表不被任何其他并行的操作更改。
注意: 一个不合格的 LOCK TABLE 同样要求这个锁模式 (例如,一条没有显式锁模式选项的命令)。
与所有锁模式冲突.
输出
LOCK TABLE
成功获取锁之后的返回.
ERROR name: Table does not exist.
如果name 不存在,返回此信息.
描述
LOCK TABLE控制一次事务的生命期内对某表的并行访问. PostgreSQL 在可能的情况下尽可能使用最小约束的锁模式。 LOCK TABLE 在你需要时提供更有约束力的锁。
RDBMS 锁定使用下面术语:
EXCLUSIVE
一个排它锁禁止其它同类型的锁获得批准.(注意∶ROW EXCLUSIVE 模式 并不完全遵循这个命名规则,因为它是在表一级共享的;它只是相对于 要更新的行而言是排它的.)
SHARE
共享锁允许其它(事务)也持有同类型锁,但是禁止对应的 EXCLUSIVE 锁获得批准.
ACCESS
锁定表结构.
ROW
锁定独立的行.
例如,假设一个应用在 READ COMMITED 隔离级别上运行事务,并且它需要保证在表中的数据在事务的运行过程中都存在。要实现这个目的,你 可以在查询之前对表使用 SHARE 锁模式进行锁定。这样将保护数据不被并行修改并且为任何更进一步的对表的读操作提供实际的当前状态的数据, 因为 SHARE 锁模式与任何写操作需要的 ROW EXCLUSIVE 模式冲突,并且你的 LOCK TABLE name IN SHARE MODE 语句将等到所有并行的写操作提交或回卷后才执行。 因此,一旦你获得该锁,那么就不会存在未提交的写操作.
注意: 当运行在 SERIALIZABLE 隔离级别并且你需要读取真实状态的数据时,你必须在执行任何 DML 语句 之前运行一个 LOCK TABLE 语句。一个串行事务的数据视图将在其第一个 DML 语句开始的时候冻结住.
除了上面的要求外,如果一个事务准备修改一个表中的数据, 那么应该使用 SHARE ROW EXCLUSIVE 锁模式以避免死锁情况(当两个 并行的事务试图以 SHARE 模式锁住表然后试图更改表中的数据时,两个事务(隐含的)都需要 ROW EXCLUSIVE 锁模式,而此模式与并行的 SHARE 锁冲突)。
继续上面的死锁(两个事务彼此等待)问题, 你应该遵循两个通用的规则以避免死锁条件:
事务应该以相同的顺序对相同的对象请求锁。
例如,如果一个应用更新行 R1 然后更新行 R2(在同一的事务里), 那么第二个应用如果稍后要更新行 R1 时不应该更新行 R2(在 同一事务里)。相反,它应该与第一个应用以相同的顺序更新行 R1 和 R2。
事务请求两个互相冲突的锁模式的前提:其中一个锁模式是自冲突的 (也就是说,一次只能被一个事务持有)。 如果涉及多种锁模式,那么事务应该总是最先请求最严格的锁模式。
这个规则的例子在前面的关于用 SHARE ROW EXCLUSIVE 模式取代 SHARE 模式的讨论中已经给出了。
注意: PostgreSQL 的确检测死锁,并将回卷至少一个等待的事务以解决死锁。
注意
LOCK ... IN ACCESS SHARE MODE 需要在目标表上有 SELECT 权限.所有其它形式的 LOCK 需要 UPDATE 和/或 DELETE 权限.
LOCK只是在一个事务块的内部有用 (BEGIN...COMMIT),因为锁在事务结束的时候马上被释放.出现在任意事务块外面的 LOCK 都自动生成一个自包含的事务,因此该锁在获取之后马上被丢弃.
LOCK只在事务内部使用.
用法
演示在往一个外键表上插入时在有主键的表上使用 SHARE 的锁:
BEGIN WORK;
LOCK TABLE films IN SHARE MODE;
SELECT id FROM films
    WHERE name = 'Star Wars: Episode I - The Phantom Menace';
-- 如果记录没有返回则回卷
INSERT INTO films_user_comments VALUES
    (_id_, 'GREAT! I was waiting for it for so long!');
COMMIT WORK;
  
在执行删除操作时对一个有主键的表进行 SHARE ROW EXCLUSIVE 锁:
BEGIN WORK;
LOCK TABLE films IN SHARE ROW EXCLUSIVE MODE;
DELETE FROM films_user_comments WHERE id IN
    (SELECT id FROM films WHERE rating < 5);
DELETE FROM films WHERE rating < 5;
COMMIT WORK;
  
兼容性 SQL92 
在里面没有LOCK TABLE ,可以使用 SET TRANSACTION 来声明当前事务的级别. 我们也支持这个,参阅 SET TRANSACTION获取详细信息。
除了ACCESS SHARE,ACCESS EXCLUSIVE,和SHARE UPDATE EXCLUSIVE 锁模式外, PostgreSQL 锁模式和 LOCK TABLE 语句都与那些在 Oracle(TM) 里面的兼容。

--------------------------------------------------------------------------------
MOVE
Name
MOVE  --  把游标放到表中的特定的行
Synopsis
MOVE [ direction ] [ count ]
    { IN | FROM } cursor
描述
MOVE允许用户对游标进行一定行的移动. MOVE 的工作类似于 FETCH 命令, 但只是定位光标而不返回行.
请参考 FETCH命令获取语法和参数的详细信息.
注意
MOVE是 PostgreSQL 语言扩展.
请参考 FETCH获取有效参数的描述.使用 DECLARE定义游标.请参考 BEGIN, COMMIT和 ROLLBACK语句获取关于事务的详细信息. ,
用法
设置和使用一个游标:
BEGIN WORK;
DECLARE liahona CURSOR FOR SELECT * FROM films;
-- 忽略开头 5 行:
MOVE FORWARD 5 IN liahona;
MOVE
-- 抓取游标 liahona 里的第六行:
FETCH 1 IN liahona;
FETCH
 code | title | did | date_prod | kind   | len
-------+--------+-----+-----------+--------+-------
 P_303 | 48 Hrs | 103 | 1982-10-22| Action | 01:37
(1 row)
-- 关闭游标 liahona 并提交工作:
CLOSE liahona;
COMMIT WORK;
兼容性 SQL92 
里没有 MOVE 语句.但是, 允许我们从一个绝对游标位置 FETCH (抓取)行,隐含地将游标移动到正确位置.
--------------------------------------------------------------------------------
NOTIFY
Name
NOTIFY  --  生成一个通知
Synopsis
NOTIFY name       
输入
notifyname
生成信号(通知)的通知条件.
输出
NOTIFY
确认通知命令已经执行了.
Notify events
事件发送给在监听的前端;前端是否响应或怎样响应取决于它自身的程序.
描述
NOTIFY命令向当前数据库中所有执行过 LISTEN notifyname ,正在监听特定通知条件的前端应用发送一个通知事件.
传递给前端的通知事件包括通知条件名和发出通知的后端进程 PID. 数据库设计者有责任定义用于某个数据库的条件名和每个通知条件的含义.
通常,通知条件名与数据库里的表的名字相同, 通知时间实际上意味着"我修改了此数据库,请看一眼有什么新东西". NOTIFY 和 LISTEN 命令并不强制这种联系.例如,数据库设计者可以使用几个不同的条件名来标志一个表的几种不同改变.
NOTIFY为访问 PostgreSQL 数据库的一组进程提供了一种简单的信号形式或IPC(内部进程通讯)机制. 更高级的机制可以通过使用数据库中的表从通知者传递数据到被通知者.
当NOTIFY用于通知某一特定表修改的动作的发生, 一个实用的编程技巧是将 NOTIFY 放在一个由表更新触发的规则里.用这种方法,通知将在表更新的时候自动触发,而且应用程序员不会碰巧忘记处理它.
NOTIFY和 SQL 事务用某种重要的方法进行交换.首先,如果 NOTIFY 在事务内部执行,通知事件直到事务提交才会送出. 这么做是有道理的,因为如果事务退出了,我们将希望在它里面的所有命令都没有效果 - 包括 NOTIFY.但如果有人希望通知事件及时发送,这就不太好了.其次,当一个正在监听的后端在一次事务内收到一个通知信号, 直到本次事务完成(提交或退出)之前,该通知事件将不被 送到与之相连的前端。同样,如果一个通知在事务内部发送出去了,而该事务稍后又退出了,我们就希望通知可以在某种程度上被撤消- -但通知一旦发送出去,后端便不能从前端"收回" 通知. 所以通知时间只是在事务之间传递.这一点就要求使用 NOTIFY 作为实时信号的 应用应该确保他们的事务尽可能短.
NOTIFY在一方面的行为象 Unix 的信号: 如果同一条件名在短时间内发出了多条信号,接收者几次执行 NOTIFY 可能只回收到一条通知信息. 所以依赖于收到的通知条数的方法是很不可靠的.因而,使用 NOTIFY唤醒需要关注某事的应用, 同时还要使用数据库对象(如序列号)来跟踪事件发生了几次.
前端经常会自己发送与正在监听的通知名一样的 NOTIFY . 这时它(前端)也和其他正在监听的前端一样收到一个通知事件.这样可能导 致一些无用的工作(与应用逻辑有关)-- 例如,对前端刚写过的表又进行一次读操作以发现是否有更新.在 PostgreSQL 6.4 更新的版本 中,我们可以通过检查后端进程的 PID (在通知事件中提供) 是否与自己的后端的 PID 一致(从libpq中取得).当他们一样时,说明这 是其自身回弹的信息,可以忽略.(不管前面章节是如何讲的, 这是一个安全的技巧. PostgreSQL 保持自身的通知和其他到来的通知区分 开.所以你屏蔽了自己的通知后不会略过外部的通知.)
注意
name可以是作为名称的任何字串;它不需要与任何实际的表的名称对应. 如果用双引号将 name 括起,它甚至可以不是语法上有效的名称,可以是任何小于31字符长的字串.
在以前的 PostgreSQL 版本, name 如果和不和任何现存的表名对应时必须用双引号引起来, 即使它在语法上是正确的也这样。现在不需要这样做了。
在 PostgreSQL 早于 6.4 的版本, 在通知信息送出的后端 PID 总是前端自己的后端的 PID. 所以在那些早期版本里, 不可能将自身的通知信息和别的客户端的通知信息区分开.
用法
在 psql 里配置和执行一个监听/通知对:
LISTEN virtual;
NOTIFY virtual;
Asynchronous NOTIFY 'virtual' from backend with pid '8448' received.
兼容性 SQL92 
在 里没有 NOTIFY语句.
--------------------------------------------------------------------------------
REINDEX
Name
REINDEX  --  恢复一个损坏了的索引
Synopsis
REINDEX { TABLE | DATABASE | INDEX } name [ FORCE ]
输入
TABLE
重新建立声明的表的所有索引.
DATABASE
恢复一个声明了的数据库的所有系统索引. (不包括用户表的索引.)
INDEX
重新建立声明了的索引.
name
要重建的所声明的表/数据库/索引的名称.
FORCE
强制性重建系统索引.如果没有这个关键字,REINDEX 忽略那些没有标记为非法的系统索引.FORCE 和 REINDEX INDEX 或者重新建立用户索引是不相关的.
输出
REINDEX
如果表的索引成功重建,返回此信息.
描述
REINDEX用于重建损坏了的系统索引. 尽管理论上这种情况决不应该发声,但实际上索引可能因为软件臭虫 或者硬件失效而损坏.REINDEX 提供了一种恢复手段.
如果你怀疑一个索引在某用户表上崩溃了,那么你可以简单地重建 该索引,或者重建该表的所有索引,用 REINDEX INDEX 或者 REINDEX TABLE 命令.
注意: 另外一个处理崩溃了的用户表索引是删除然后重建它. 如果你同时还要维持一些在该表上表面的操作,那么这个方法可能更好. REINDEX 在表上施加排它的锁,而 CREATE INDEX 只锁住写,而不会限止对表的读取操作.
如果你想从一个系统表造成的崩溃中恢复,那么问题就更复杂一些. 在这种情况下,避免在做恢复的后端使用怀疑受损的索引本身是非常重要的. (实际上,在这种情况下,你可能会发现后端启动后马上就崩溃了, 因为它们倚赖于这些已经崩溃的索引.)为了安全地恢复,你必需关闭 postmaster,然后运行一个独立运行的 PostgreSQL 后端,给予它命令行参数 -O 和 -P (这些选项分别是允许对系统表进行修改 并且避免了系统索引的使用).然后发出 REINDEX INDEX, REINDEX TABLE,或者 REINDEX DATABASE 命令,具体取决于你想重新构造多少东西.如果觉得有疑问,那么用 REINDEX DATABASE FORCE 强制重建数据库中所有系统表.然后退出独立运行的后端,重启 postmaster.
因为这种情况可能是大多数用户可能用到独立运行的后端的唯一机会, 那么我们必需事先知道一些用法在顺序上的注意事项∶
用下面这样的命令启动后端
postgres -D $PGDATA -O -P my_database
用 -D 给数据库区域提供正确的路径, 或者确保设置了环境变量 PGDATA.还要声明你想操作 的数据库名字.
你可以发出任何 SQL 命令,不仅仅是 REINDEX.
要注意独立运行的后端把换行符当做命令输入终止符; 它可不懂分号是什么东西,分号是 psql 里的东西. 要令一条命令跨多个行,你必需在除最后一个换行符之外的 每个换行符之前键入一个反斜杠. 同样,你也没有任何 readline 处理的便利可用(比如,没有命令历史).
要退出后端,键入 EOF(通常是 control-D).
参阅 postgres手册页获取更多信息.
用法
重建表 mytable 上的索引:
     REINDEX TABLE mytable;
  
重建单个索引∶
    REINDEX INDEX my_index;
  
重建所有系统索引(这个只能运行在独立运行的后端中.)
REINDEX DATABASE my_database FORCE;
  
兼容性 SQL92 
在里没有 REINDEX.
--------------------------------------------------------------------------------
RESET
Name
RESET -- 把一个运行时参数值恢复为缺省值
Synopsis
RESET variable
RESET ALL
输入
variable
请参考 SET语句获取有关可用的参数的详细说明.
ALL
把所有运行时参数设置为缺省值.
描述
RESET将运行时参数恢复为缺省值. 请参考 SET命令令获取允许的变量值和缺省值的详细信息. RESET 是下面语句的一个变种
SET variable TO DEFAULT
  
诊断
参阅 SET命令.
例子
把 DateStyle 重新设为缺省值:
RESET DateStyle;
把 Geqo 重新设为缺省值:
  
RESET GEQO;
兼容性 SQL92
RESET是 PostgreSQL 扩展.
--------------------------------------------------------------------------------
REVOKE
Name
REVOKE  --  删除访问权限.
Synopsis
REVOKE { { SELECT | INSERT | UPDATE | DELETE | RULE | REFERENCES | TRIGGER } [,...] | ALL [ PRIVILEGES ] }
    ON [ TABLE ] object [, ...]
    FROM { username | GROUP groupname | PUBLIC } [, ...]
描述
REVOKE允许一个对象的创建者撤销以前 赋予(别人)的权限,可以是撤销一个或多个用户或者一组用户的权限. 关键字 PUBLIC 代表隐含定义的拥有所有用户的组.
请注意,任何特定的用户都将拥有直接赋予他/她的权限,加上 他/她所处的任何组,以及再加上赋予 PUBLIC 的权限的总和.因此,举例来说,废止 PUBLIC 的 SELECT 权限并不意味着所有用户都失去了对该对象的 SELECT 权限∶ 那些直接得到权限赋予的以及通过一个组得到权限的人仍然拥有该权限.
参阅 GRANT 命令的描述获取权限类型的 含义.
注意
使用 psql的 \z 命令 显示在一个现存对象上赋予的权限.又见 GRANT 获取关于格式的信息.
例子
撤销公众在表 films 上的插入权限∶
REVOKE INSERT ON films FROM PUBLIC;
废除用户 manuel 对视图 kinds 的所有权限∶
REVOKE ALL PRIVILEGES ON kinds FROM manuel;
兼容性 SQL92
GRANT 命令的兼容性 SQL92 信息基本上也 适用于 REVOKE.语法概要是∶
REVOKE [ GRANT OPTION FOR ] { SELECT | INSERT | UPDATE | DELETE | REFERENCES }
    ON object [ ( column [, ...] ) ]
    FROM { PUBLIC | username [, ...] }
    { RESTRICT | CASCADE }
如果 user1 给予 user2 权限WITH GRANT OPTION, 然后 user2 把它给了 user3,那么 user1 可以用 CASCADE 关键字 废除所有这些权限.如果 user1 给了 user2 WITH GRANT OPTION 权限, 然后 user2 把它给了 user3,然后如果 user1 想撤销这个权限, 但是他声明了 RESTRICT 关键字,那么会失败.
又见
GRANT
--------------------------------------------------------------------------------
ROLLBACK
Name
ROLLBACK  --  退出当前事务
Synopsis
ROLLBACK [ WORK | TRANSACTION ]
输入

输出
ABORT
成功的返回信息.
NOTICE: ROLLBACK: no transaction in progress
如果当前进程没有任何事务,返回此信息.
描述
ROLLBACK回卷当前事务并取消当前事务中的所有更新.
注意
使用 COMMIT语句将一次事务成功停止. ABORT是 ROLLBACK 同义词。
用法
取消所有更改:
ROLLBACK WORK;
  
兼容性 SQL92 
只声明了两种形式 ROLLBACK 和 ROLLBACK WORK。否则完全兼容。
--------------------------------------------------------------------------------
SELECT INTO
Name
SELECT INTO  --  从一个查询的结果中创建一个新表
Synopsis
SELECT [ ALL | DISTINCT [ ON ( expression [, ...] ) ] ]
    * | expression [ AS output_name ] [, ...]
    INTO [ TEMPORARY | TEMP ] [ TABLE ] new_table
    [ FROM from_item [, ...] ]
    [ WHERE condition ]
    [ GROUP BY expression [, ...] ]
    [ HAVING condition [, ...] ]
    [ { UNION | INTERSECT | EXCEPT } [ ALL ] select ]
    [ ORDER BY expression [ ASC | DESC | USING operator ] [, ...] ]
    [ FOR UPDATE [ OF tablename [, ...] ] ]
    [ LIMIT { count , ] { count | ALL } ]
    [ OFFSET start ]
这里
from_item可以是:
[ ONLY ] table_name [ * ]
    [ [ AS ] alias [ ( column_alias_list ) ] ]
|
( select )
    [ AS ] alias [ ( column_alias_list ) ]
|
from_item [ NATURAL ] join_type from_item
    [ ON join_condition | USING ( join_column_list ) ]
输入
TEMPORARY
TEMP
如果声明了 TEMPORARY 或者 TEMP, 那么输出表就只在本次会话中创建,并且会话结束后自动删除. 同名的现存永久表在临时表存在期间将不可见(在本次会话中). 任何在临时表上创建的索引都是自动临时的.
new_table
要创建的新表名.这个表必须是尚未存在的. 不过,我们可以在存在一个永久表的情况下创建一个(同名)临时表.
所有其它输入的域都在 SELECT 中有详细描述.
输出
请参考 CREATE TABLE和 SELECT 获取所有可能输出信息的摘要.
描述
SELECT INTO从一个查询的计算结果中创建一个新表. 书局并不返回给客户端,这一点和普通的 SELECT 不同.新表的字段具有和 SELECT 的输出字段 相关联(相同)的名字和数据类型.
注意: CREATE TABLE AS 的作用和 SELECT INTO 相同. 我们建议使用 CREATE TABLE AS 语法, 因为 SELECT INTO 不是标准语法. 实际上,这种类型的 SELECT INTO 是不能在 PL/pgSQL或者 ecpg 中使用的, 因为它们对 INTO 子句的解释是不同的.
兼容性 SQL92 
 用 SELECT ... INTO 表示选取数值到一个 宿主程序的标量变量中,而不是创建一个新表. 的用法实际上就是在PL/pgSQL和 ecpg 里的用途. PostgreSQL 用 SELECT INTO 代表创建表的意思是历史原因.在新代码里我们最好使用 CREATE TABLE AS 实现这个目地. (CREATE TABLE AS 也不是标准,但至少它 出现混淆的机会少一些.)
--------------------------------------------------------------------------------
SELECT
Name
SELECT  --  从表或视图中取出若干行.
Synopsis
SELECT [ ALL | DISTINCT [ ON ( expression [, ...] ) ] ]
    * | expression [ AS output_name ] [, ...]
    [ FROM from_item [, ...] ]
    [ WHERE condition ]
    [ GROUP BY expression [, ...] ]
    [ HAVING condition [, ...] ]
    [ { UNION | INTERSECT | EXCEPT } [ ALL ] select ]
    [ ORDER BY expression [ ASC | DESC | USING operator ] [, ...] ]
    [ FOR UPDATE [ OF tablename [, ...] ] ]
    [ LIMIT { count | ALL } ]
    [ OFFSET start ]
 
这里 from_item 可以是:
 
[ ONLY ] table_name [ * ]
    [ [ AS ] alias [ ( column_alias_list ) ] ]
|
( select )
    [ AS ] alias [ ( column_alias_list ) ]
|
from_item [ NATURAL ] join_type from_item
    [ ON join_condition | USING ( join_column_list ) ]
 
输入
expression
表的列/字段名或一个表达式.
output_name
使用 AS 子句为一个列/字段或一个表达式声明另一个名称.这个名称主要用于标记输出列用于显示。 它可以在 ORDER BY 和 GROUP BY 子句里代表列/字段的值. 但是 output_name 不能用于 WHERE 或 HAVING 子句;用表达式代替.
from_item
一个表引用,子查询,或者 JOIN 子句.详见下文.
condition
一个布尔表达式,给出真或假的结果. 参见下面描述的 WHERE 和 HAVING 子句.
select
一个选择语句,可以有除 ORDER BY,FOR UPDATE,和 LIMIT 子句以外的所有 特性(甚至在加了括弧的情况下那些语句也可以用).
FROM 项可以包括:
table_name
一个现存的表或视图的名字.如果声明了 ONLY,则只扫描该表. 如果没有声明ONLY,该表和所有其派生表(如果有的话)都被扫描. 可以在表名后面跟一个 * 来表示扫所有其后代表,但在目前的版本里,这是缺省特性. (在 PostgreSQL 7.1 以前的版本里, ONLY 是缺省特性.)
alias
用于于前面的 table_name. 的替换名字,用于缩写或消除一个表自连接时的含混. (此时同一个表要扫描好几次.) 如果写了别名,那么你也可以写一个字段别名列表,为表的一个或者几个字段提供替换名字.
select
一个在 FORM 子句里出现的子查询.它的输出作用好象是为这条 SELECT 命令在其生存期里创建一个临时表. 请注意这个子查询必须用园括弧包围. 并且必须给它加别名.
join_type
[ INNER ] JOIN, LEFT [ OUTER ] JOIN, RIGHT [ OUTER ] JOIN, FULL [ OUTER ] JOIN,或 CROSS JOIN. 之一. 就 INNER 和 OUTER 连接类型,必须出现 NATURAL ON join_condition,或 USING ( join_column_list ) 之一.对于 CROSS JOIN,上面的项都不能出现.
join_condition
一个条件限制.类似 WHERE 条件,只不过它只应用于在这条 JOIN 子句里 连接的两个 from_item.
join_column_list
一个 USING 字段列表 (a, b, ... ) 是 ON 条件 left_table.a = right_table.a AND left_table.b = right_table.b ... 的缩写.
输出
Rows
你声明的查询返回的所有结果集的行.
count
查询返回的行的计数.
描述
SELECT将从一个或更多表中返回记录行。 选择的侯选行是满足 WHERE 条件的所有行。 或者如果省略了 WHERE 语句则选择表中的所有行.(参阅 WHERE ). 子句
实际上,返回的行并不是由 FROM/WHERE/GROUP BY/HAVING 子句直接生成的行; 其实,输出行是通过给每个选出的行计算 SELECT 输出表达式形成的. 你可以在输出列表上写一个 * 表示选出的行的所有列. 同样我们可以拿 table_name.* 表示来自该表的所以行.
DISTINCT将从选择出来的结果集中删除所有的重复的行。 ALL (缺省)将返回所有侯选行,包括重复的行。
DISTINCT ON删除匹配所有你声明的表达式的行,只保留每个重复集的第一行。 DISTINCT ON 表达式是用和 ORDER BY 项一样的规则来解释的,见下文. 注意这里每个重复集的"第一行"是不可预料的,除非我们用 ORDER BY 来保证我们希望的行最先出现。例如,
        SELECT DISTINCT ON (location) location, time, report
        FROM weatherReports
        ORDER BY location, time DESC;
  
检索出每个地区的最近的天气预报。 但是如果我们没有使用 ORDER BY 来强制每个地区按时间值降续排列, 我们得到的将是每个地区的不可预料的时间的报告。
GROUP BY 子句允许用户把表分成匹配一个或多个数值的不同行的组. (参考 GROUP BY .) 子句
HAVING 允许只选择那些满足声明条件的行组(参阅 HAVING .) 子句
ORDER BY 导致返回的行按照声明的顺序排列. 如果没有给出 ORDER BY,输出的行的顺序将以系统认为开销最小的顺序产生.(参阅 ORDER BY .) 子句
多个 SELECT 查询可以用 UNION,INTERSECT,和 EXCEPT 操作符 组合起来.必要时请使用圆括弧确定这些操作符的顺序.
UNION 操作符计算是那些参与的查询所返回的行的集合。 如果没有声明 ALL,那么重复行被删除.(参阅 UNION .) 子句
INTERSECT 给出两个查询公共的行。 如果没有声明 ALL,那么重复行被删除. (参阅 INTERSECT .) 子句
EXCEPT 给出存在于第一个查询而不存在于第二个查询的行。 如果没有声明 ALL,那么重复行被删除.(参阅 EXCEPT .) 子句
FOR UPDATE 子句允许 SELECT 语句对选出的行执行排他锁。
LIMIT 子句允许给用户返回一个查询生成的结果的子集。(参阅 LIMIT .) 子句
你必须有 SELECT 权限用来从表中读取数值(参阅 GRANT/REVOKE语句.)
FROM 子句
FROM 子句为 SELECT 声明一个或多个源表. 如果声明了多个源表,则概念上结果是所有源表所有行的迪卡尔积 --- 不过通常会增加限制条件以把返回的行限制为迪卡尔积的一个小子集.
如果 FROM 项是一个简单表名字,它隐含包括来自该表子表(继承子表)的行. ONLY 将消除从该表的子表来的行. 在 PostgreSQL 7.1 以前,这是缺省结果, 而获取子表的行是通过在表名后面附加 * 实现的. 这种老式性质可以通过命令 SET SQL_Inheritance TO OFF; 获取.
FROM 项也可以是一个加了圆括弧的子查询 (请注意子查询需要一个别名子句!). 这个特性非常实用,因为这是在一条查询中获得多层分组,聚集,或者排序的唯一方法.
最后,FROM 项可以是一条 JOIN 子句,它把两个简单的 FROM 项组合 在一起.(必要时使用圆括弧来描述嵌套顺序.)
CROSS JOIN 或 INNER JOIN 是简单的迪卡尔积, 和你在顶层 FROM 里列出这两个项得到的一样. CROSS JOIN 等效于 INNER JOIN ON (TRUE),也就是说, 不会有任何行被条件删除.这些连接类型只是符号上的便利, 因为它们做得一点不比你只利用 FROM 和 WHERE 来的多.
LEFT OUTER JOIN 返回所有符合条件的迪卡尔积 (也就是说,所有符合它的 ON 条件的组合了的行),另外加上所有没有右手边行符合 ON 条件的左手边表中的行. 这样的左手边行通过向右手边行插入 NULL 扩展为全长. 请注意,当判断哪些行合格的时候,只考虑 JOIN 自己的 ON 或 USING. 然后才考虑外层的 ON 或 WHERE 条件.
相反, RIGHT OUTER JOIN 返回所有连接的行,另外加上所有未匹配右手边行(左手边插入 NULL 扩展为全长). 这个字句只是符号方便,因为你可以调换左右输入而改用 LEFT OUTER JOIN.
FULL OUTER JOIN 返回所有连接行,加上所有未匹配的左手边行 (右边插入 NULL 扩展为全长),再加上所有未匹配的右手边行(左手边插入 NULL 扩展为全长).
除了CROSS JOIN 以外的所有 JOIN 类型,你必须写 ON join_condition, USING ( join_column_list ), 和 NATURAL 中的一个. 大多数情况下会是 ON:你可以写涉及两个连接表的任何条件表达式. USING 字段列表 (a, b, ...) 是 ON 条件 left_table.a = right_table.a AND left_table.b = right_table.b ... 的缩写. 另外,USING 假设两对等式中只有一个包含在 JOIN 输出中,而不是两个. NATURAL 是提及表中所有相似名字字段的 USING 列表的缩写.
WHERE 子句
可选的 WHERE 条件有如下常见的形式:
WHERE boolean_expr
   
boolean_expr可以包含任意个得出布尔值的表达式。通常表达式会是
     expr cond_op expr
   

     log_op expr
   
这里 cond_op 可以是: =,<,<=, >,>= 或 <>, 或条件操作符象 ALL,ANY,IN,LIKE 等,或者用户定义的操作符,而 log_op 可以为 : AND,OR,NOT. SELECT 将忽略所有 WHERE 条件不为 TRUE 的行.
GROUP BY 子句
GROUP BY 声明一个分了组的表,该表源于应用使用下面的子句:
GROUP BY expression [, ...]
   
GROUP BY 将把所有在组合了的列上共享同样的值的行压缩成一行。 如果存在聚集函数,这些聚集函数将计算每个组的所有行,并且为 每个组计算一个独立的值(如果没有 GROUP BY, 聚集函数对选出的所有行计算出一个数值)。存在 GROUP BY 时,除了在聚集函数里面,SELECT 输出表达式对任何非组合列的引用都是非法的, 因为对一个非组合列会有多于一个可能的返回值。
一个在 GROUP BY 里面的条目还可以是输出列的名称或者序号(SELECT 表达式), 或者是一个从输入列的数值形成的任意表达式.当存在语义模糊时, 一个 GROUP BY 名称将被解释成一个输入列/字段名称而不是一个输出列/字段名称.
HAVING 子句
可选的 HAVING 条件有如下形式:
HAVING boolean_expr
   
这里 boolean_expr 和为 WHERE 子句里声明的相同.
HAVING 子句声明一个从前面的子句的结果集中去除了一些不符合 boolean_expr. 组后分组的表.HAVING 与 WHERE 不同:WHERE 在应用 GROUP BY 之前过滤出单独的行,而 HAVING 过滤由 GROUP BY 创建的行.
在 boolean_expr 里引用的每个列/字段应该清晰地指明一个组的列/字段, 除非引用在一个聚集函数里。
ORDER BY 子句
ORDER BY expression [ ASC | DESC | USING operator ] [, ...]
   
一个 ORDER BY 项可以是一个输出列(SELECT 表达式)的名字或者序数, 或者它也可以是任何来自输入列值形成的表达式.在出现混淆的场合下,ORDER BY 名字将被解释成一个输出名字.
序数指的是列/字段按顺序(从左到右)的位置.这个特性可以使得对没有一个合适名称的列/字段的排序成为可能. 这一点可能永远没有用, 因为总是可以通过AS 子句给一个要计算的列/字段赋予一个名称,例如:
SELECT title, date_prod + 1 AS newlen FROM films ORDER BY newlen;
   
还可以 ORDER BY 任意表达式(一个对 的扩展), 包括那些没有出现在 SELECT 结果列表里面的域。 因此下面的语句现在是合法的:
SELECT name FROM distributors ORDER BY code;
   
这个特性的一个局限就是应用于 UNION,INTERSECT,或者 EXCEPT 查询 的 ORDER BY 子句只能在一个输出字段名或者数字上声明, 而不能在一个表达式上声明.
请注意如果一个 ORDER BY 条目是一个匹配结果列和输入列的简单名称, ORDER BY 将把它解释成结果列名称. 这和 GROUP BY 在同样情况下做的选择正相反.这样的不一致是由 标准强制的.
我们可以给ORDER BY 子句里每个列/字段加一个关键字 DESC (降序)或 ASC(升序).如果不声明,ASC 是缺省. 我们还可以声明一个排序操作符来实现排序。 ASC 等效于使用 '<' 而 DESC 等效于使用 '>'。
在一个域里,空值排序时排在其它数值前面.换句话说,升序排序时, 空值排在末尾,而降序排序时空值排在开头.
UNION 子句
table_query UNION [ ALL ] table_query
    [ ORDER BY expression [ ASC | DESC | USING operator ] [, ...] ]
    [ LIMIT { count | ALL } [ { OFFSET | , } start ]]
   
这里 table_query 表明任何没有 ORDER BY,FOR UPDATE,或者 LIMIT 子句的选择表达式. (如果用圆括弧包围,ORDER BY 和 LIMIT 可以放在子表达式里. 如果没有圆括弧,这些子句将交给 UNION 的结果使用, 而不是给它们右手边的输入表达式.)
UNION 操作符的结果集是那些涉及到的所有查询所返回结果的集合。 两个做为 UNION 直接操作数的 SELECT 必须生成相同数目的字段, 并且对应的字段必须有兼容的数据类型。
缺省地,UNION 的结果不包含任何重复的行,除非声明了 ALL 子句. ALL 制止了消除重复的动作.
同一 SELECT 语句中的多个 UNION 操作符是从左向右计算的, 除非用圆括弧进行了标识).
目前,FOR UPDATE 不能在 UNION 的结果或输入中声明.
INTERSECT 子句
table_query INTERSECT [ ALL ] table_query
    [ ORDER BY expression [ ASC | DESC | USING operator ] [, ...] ]
    [ LIMIT { count | ALL } ]
    [ OFFSET start ]
   
这里 table_query 声明任何没有 ORDER BY,FOR UPDATE,或者 LIMIT 子句的选择表达式。
INTERSECT 类似 UNION,只不过它给出在两个查询中都出现的行, 而不是两个查询的所有行.
INTERSECT 的结果不包含任何重复行,除非你声明了 ALL 选项. 用了 ALL 以后,一个在 L 里有 m 个重复而在 R 里有 n 个重复 的行将出现 min(m,n) 次.
除非用圆括号指明顺序, 同一 SELECT 语句中的多个 INTERSECT 操作符是从左向右计算的。 INTERSECT 比 UNION 绑定得更紧 --- 也就是说 A UNION B INTERSECT C 将读做 A UNION (B INTERSECT C),除非你用圆括弧声明.
EXCEPT 子句
table_query EXCEPT [ ALL ] table_query
    [ ORDER BY expression [ ASC | DESC | USING operator ] [, ...] ]
    [ LIMIT { count | ALL } ]
    [ OFFSET start ]
   
这里 table_query 声明任何没有 ORDER BY,FOR UPDATE,或者 LIMIT 子句的选择表达式。
EXCEPT 类似于 UNION,只不过 EXCEPT 给出存在于左边查询输出而不存在于右边查询输出的行。
EXCEPT 的结果不包含任何重复的行,除非声明了 ALL 选项. 使用ALL时,一个在 L 中有 m 个重复而在 R 中有 n 个重复的行 将出现 max(m-n,0) 次.
除非用圆括弧指明顺序, 同一 SELECT 语句中的多个 EXCEPT 操作符是从左向右计算的。 EXCEPT 和 UNION 绑定级别相同.
LIMIT 子句
    LIMIT { count | ALL }
    OFFSET start
   
这里 count 声明返回的最大行数,而 start 声明开始返回行之前忽略的行数。
LIMIT 允许你检索由查询其他部分生成的行的某一部分。 如果给出了限制计数,那么返回的行数不会超过哪个限制。 如果给出了一个偏移量,那么开始返回行之前会忽略那个数量的行。
在使用 LIMIT 时, 一个好习惯是使用一个 ORDER BY 子句把结果行限制成一个唯一的顺序。 否则你会得到无法预料的查询返回的子集 --- 你可能想要第十行到第二十行, 但以什么顺序?除非你声明 ORDER BY,否则你不知道什么顺序。
从 PostgreSQL 7.0 开始, 查询优化器在生成查询规划时把 LIMIT 考虑进去了, 所以你很有可能因给出的 LIMIT 和 OFFSET 值不同而得到不同的 规划(生成不同的行序)。因此用不同的 LIMIT/OFFSET 值选择不同的查询结果的子集 将不会产生一致的结果,除非你用 ORDER BY 强制生成一个可预计的结果顺序。 这可不是毛病;这是 SQL 生来的特点,因为除非用了 ORDER BYE 约束顺序, SQL 不保证查询生成的结果有任何特定的顺序。
用法
将表 films 和表 distributors 连接在一起:
SELECT f.title, f.did, d.name, f.date_prod, f.kind
    FROM distributors d, films f
    WHERE f.did = d.did
 
           title           | did |   name           | date_prod | kind
---------------------------+-----+------------------+------------+----------
 The Third Man             | 101 | British Lion     | 1949-12-23 | Drama
 The African Queen         | 101 | British Lion     | 1951-08-11 | Romantic
 Une Femme est une Femme   | 102 | Jean Luc Godard | 1961-03-12 | Romantic
 Vertigo                   | 103 | Paramount        | 1958-11-14 | Action
 Becket                    | 103 | Paramount        | 1964-02-03 | Drama
 48 Hrs                    | 103 | Paramount        | 1982-10-22 | Action
 War and Peace             | 104 | Mosfilm          | 1967-02-12 | Drama
 West Side Story           | 105 | United Artists   | 1961-01-03 | Musical
 Bananas                   | 105 | United Artists   | 1971-07-13 | Comedy
 Yojimbo                   | 106 | Toho             | 1961-06-16 | Drama
 There's a Girl in my Soup | 107 | Columbia         | 1970-06-11 | Comedy
 Taxi Driver               | 107 | Columbia         | 1975-05-15 | Action
 Absence of Malice         | 107 | Columbia         | 1981-11-15 | Action
 Storia di una donna       | 108 | Westward         | 1970-08-15 | Romantic
 The King and I            | 109 | 20th Century Fox | 1956-08-11 | Musical
 Das Boot                  | 110 | Bavaria Atelier | 1981-11-11 | Drama
 Bed Knobs and Broomsticks | 111 | Walt Disney      |            | Musical
(17 rows)
统计用kind 分组的所有电影和组的列/字段的 len(长度)的和:
SELECT kind, SUM(len) AS total FROM films GROUP BY kind;
 
   kind   | total
----------+-------
 Action   | 07:34
 Comedy   | 02:58
 Drama    | 14:28
 Musical | 06:42
 Romantic | 04:38
(5 rows)
统计所有电影(films),组的列/字段 len(长度)的和,用 kind 分组并且显示小于5小时的组总和:
SELECT kind, SUM(len) AS total
    FROM films
    GROUP BY kind
    HAVING SUM(len) < INTERVAL '5 hour';
 
 kind     | total
----------+-------
 Comedy   | 02:58
 Romantic | 04:38
(2 rows)
下面两个例子是根据第二列 (name)的内容对单独的结果排序的经典的方法:
SELECT * FROM distributors ORDER BY name;
SELECT * FROM distributors ORDER BY 2;
 
 did |       name
-----+------------------
 109 | 20th Century Fox
 110 | Bavaria Atelier
 101 | British Lion
 107 | Columbia
 102 | Jean Luc Godard
 113 | Luso films
 104 | Mosfilm
 103 | Paramount
 106 | Toho
 105 | United Artists
 111 | Walt Disney
 112 | Warner Bros.
 108 | Westward
(13 rows)
这个例子演示如何获得表 distributors 和 actors的连接, 只将每个表中以字母 W 开头的取出来. 因为只取了不相关的行,所以关键字 ALL 被省略了:
distributors:               actors:
 did |     name              id |     name
-----+--------------        ----+----------------
 108 | Westward               1 | Woody Allen
 111 | Walt Disney            2 | Warren Beatty
 112 | Warner Bros.           3 | Walter Matthau
 ...                         ...
 
SELECT distributors.name
    FROM   distributors
    WHERE distributors.name LIKE 'W%'
UNION
SELECT actors.name
    FROM   actors
    WHERE actors.name LIKE 'W%'
 
      name
----------------
 Walt Disney
 Walter Matthau
 Warner Bros.
 Warren Beatty
 Westward
 Woody Allen
兼容性 SQL92 
扩展
PostgreSQL允许我们在一个查询里省略 FROM 子句。 这个特性是从最初的 PostQuel 查询语言里保留下来的 它的最直接用途就是计算简单的常量表达式的结果:
SELECT 2+2;
 
 ?column?
----------
        4
 
其它有些 DBMS 不能这么做,除非引入一个单行的伪表做 select 的 from.这个特性的另外一个不太明显的用途是把一个普通的从一个或多个表的 select 缩写:
SELECT distributors.* WHERE distributors.name = 'Westward';
 
 did | name
-----+----------
 108 | Westward
 
这样也可以运行是因为我们给查询中引用了但没有在 FROM 中提到的每个表都加了一个隐含的 FROM 项.尽管这是个很方便的写法,但它却容易误用.比如,下面的查询
SELECT distributors.* FROM distributors d;
 
可能就是个错误;用户最有可能的意思是
SELECT d.* FROM distributors d;
 
而不是下面的他实际上得到的无约束的连接
SELECT distributors.* FROM distributors d, distributors distributors;
 
为了帮助检测这种错误, PostgreSQL 7.1 以及以后的版本将在你使用一条即有隐含 FROM 特性又有明确的 FORM 子句的查询的时候给出警告.
SELECT 子句
在 规范里, 可选的关键字 "AS" 是多余的,可以忽略掉而不对语句产生任何影响. PostgreSQL 分析器在重命名列/字段时需要这个关键字, 因为类型扩展的特性会导致上下文语意不清. 不过,"AS" 在 FROM 项里是可选的.
DISTINCT ON 语法不是 的标准。 LIMIT 和 OFFSET 也不是。
在 里, 一个 ORDER BY 子句只可以使用在结果列名称或者序号上,而 GROUP BY 子句只能用于输入列/字段上. PostgreSQL 把这两个子句都扩展为允许另一种选择(但是如果出现冲突则使用标准的解释). PostgreSQL 还允许两个子句声明任意的表达式. 请注意,在表达式里出现的名称将总是被当做输入列/字段的名称,而不是结果列/字段名称.
UNION/INTERSECT/EXCEPT 子句
 的 UNION/INTERSECT/EXCEPT 语法允许一个附加的 CORRESPONDING BY 选项:
 
table_query UNION [ALL]
    [CORRESPONDING [BY (column [,...])]]
    table_query
    
CORRESPONDING BY 目前还不被 PostgreSQL支持.
--------------------------------------------------------------------------------
SET CONSTRAINTS
Name
SET CONSTRAINTS -- 设置当前事务的约束模式
Synopsis
SET CONSTRAINTS { ALL | constraint [, ...] } { DEFERRED | IMMEDIATE }
描述
SET CONSTRAINTS设置当前事务里的约束运算的特性. 在 IMMEDIATE 模式下,约束是在每条语句后面进行检查的. 在 DEFERRED 模式下,一直到事务提交时才检查约束.
从创建的时候开始,一个约束总是表现为下面三个特性之一: INITIALLY DEFERRED, INITIALLY IMMEDIATE DEFERRABLE,或 INITIALLY IMMEDIATE NOT DEFERRABLE. 第三个特性不会受 SET CONSTRAINTS影响.
目前只有外键(foreign key)约束受这个设置的影响. Check 和 unique约束总是有效地initially immediate not deferrable (初始化立即执行无推迟).
兼容性 SQL92
, SQL99
SET CONSTRAINT是 和 SQL99 里定义的.
--------------------------------------------------------------------------------
SET SESSION AUTHORIZATION
Name
SET SESSION AUTHORIZATION --  为当前会话设置会话用户标识符和当前用户标识符
Synopsis
SET SESSION AUTHORIZATION 'username'
描述
这条命令把当前 SQL 会话环境里的会话用户标识和当前用户标识设置为 username.
会话用户标识符一开始设置为(可能经过认证的) 客户端提供的用户名.当前用户标识符通常等于会话用户标识符, 但是可能在 "setuid" 的环境里或者类似的机制里临时改变. 当前用户标识符和权限检查相关.
只有在初始会话用户(认证了的用户) 有超级用户权限的时候才可以执行这条命令. 这个权限在联接的周期中得以保存;比如,我们可以暂时变身成非超级用户, 然后稍后切换回超级用户.
例子
SELECT SESSION_USER, CURRENT_USER;
 current_user | session_user
--------------+--------------
 peter        | peter
SET SESSION AUTHORIZATION 'paul';
SELECT SESSION_USER, CURRENT_USER;
 current_user | session_user
--------------+--------------
 paul         | paul
兼容性 SQL92
SQL99
SQL99 允许一些其它的表达式出现在文本 username 的位置上,不过这个东西实际上并不重要. PostgreSQL 允许标识符语法 ("username"),而 SQL 不允许. SQL 不允许在一个事务的过程中用这条命令; PostgreSQL 没有这个限制,因为没有什么理由 不允许这样用.标准中表示执行这条命令的权限要求是具体实现定义的.
--------------------------------------------------------------------------------
SET TRANSACTION
Name
SET TRANSACTION -- 设置当前事务的特性
Synopsis
SET TRANSACTION ISOLATION LEVEL { READ COMMITTED | SERIALIZABLE }
SET SESSION CHARACTERISTICS AS TRANSACTION ISOLATION LEVEL
        { READ COMMITTED | SERIALIZABLE }
描述
这条命令摄制事务隔离级别. SET TRANSACTION 命令为当前 SQL 事务 设置特性. 它对后面的事务没有影响. 这条命令在正在执行的事务使用了第一条查询或者修改数据的语句(Data Modify Language?)语句后就不能使用了( SELECT, INSERT,DELETE, UPDATE,FETCH, COPY).) SET SESSION CHARACTERISTICS 为一个会话中的每个事务设置缺省的隔离级别. SET TRANSACTION 可以为一个独立的 事务覆盖上面的设置.
事务的隔离级别决定一个事务在同时存在其它并行运行的事务时 它能够看到什么数据.
READ COMMITTED
一条语句只能看到在它开始之前的数据.这是缺省.
SERIALIZABLE
当前的事务只能看到在这次事务第一条查询或者修改数据的语句执行之前的数据.
小技巧: 说白了,serializable(可串行化)意味着两个事务 将把数据库保持在同一个状态,就好象这两个事务是严格地按照先后顺序执行地那样.
兼容性 SQL92
会话的缺省事务隔离级别也可以用命令
SET default_transaction_isolation = 'value'
以及在配置文件里设置. 参考管理员手册获取更多信息.
兼容性 SQL92
, SQL99
SERIALIZABLE 是 SQL 里面的缺省隔离级别. PostgreSQL并不提供 READ UNCOMMITTED 和REPEATABLE READ 隔离级别.因为我们使用了多版本并行控制,serializable(可串行化)级别 并非真的可串行化,参阅 用户手册 获取细节.
在 SQL 里还有两种事务特性可以用这条命令设置: 这个事务是否只读和诊断范围的大小.这两个概念都不被PostgreSQL支持.
--------------------------------------------------------------------------------
SET
Name
SET -- 改变运行时参数
Synopsis
SET variable { TO | = } { value | 'value' | DEFAULT }
SET TIME ZONE { 'timezone' | LOCAL | DEFAULT }
输入
variable
可设置的全局变量.
value
参数的新值.DEFAULT 可以用于声明把参数恢复为缺省值.允许使用字串数组,但是更复杂的结构需要用单引号或者双引号引起来.
描述
SET命令改变运行时配置参数. 可以改变的参数是:
CLIENT_ENCODING
NAMES
设置多字节客户端编码。声明的编码方式必须为后端支持。
这个特性只有在制作 PostgreSQL 的配置阶段声明了多字节(--enable-multibyte)支持后才生效。
DATESTYLE
设置日期/时间表示风格。有两个独立的配置需要设置: 缺省的日期/时间输出和语意含糊的输入的解释.
下面是日期/时间输出风格:
ISO
使用 ISO 8601-风格的日期和时间(YYYY-MM-DD HH:MM:SS)这是缺省设置.
SQL
使用 Oracle/Ingres-风格的日期和时间.请注意这个风格和 SQL 没有任何关系(SQL要求使用ISO 8601风格),这个 命名选项是历史原因.
PostgreSQL
使用传统 PostgreSQL格式
German
使用 dd.mm.yyyy 作为数字日期表达式.
下面的两个选项决定 "SQL" 和 "PostgreSQL" 两个选项的输出格式的子风格,以及优先的含糊日期输入的解释.
European
使用 dd/mm/yyyy 作为数字化的日期表现形式.
NonEuropean
US
使用 mm/dd/yyyy 作为数字日期表现形式.
SET DATESTYLE的值可以是来自第一列中的一个(输出风格), 或者是来自第二列中的一个(子风格),或者来自上面两个列表,并且用逗号分隔两个参数.
日期格式初始化可以用下面方法初始化:
设置 PGDATESTYLE 环境变量. 如果一个基于 libpq 的客户端的环境里设置了 PGDATESTYLE, libpq 将在联接启动时自动把DATESTYLE 设置成为 PGDATESTYLE 的值。 
用-o -e参数运行 postmaster可以把日期设置成 European. 
DateStyle 选项只是为了移植应用用的.要格式化你的日期/时间值来做选择,请用 to_char 家族的函数.
SEED
为随机数生成器设置内部种子.
value
被random范围函数使用的种子的值. 典型的值是介于0 和 1之间的浮点数, 这个数随后乘以 231-1.如果使用了超出范围的数值, 生成的积自动溢出.
种子还可以通过调用 setseed SQL 函数设置:
SELECT setseed(value);
    
SERVER_ENCODING
设置多字节服务器端编码方式.
这个特性只有在制作 PostgreSQL 的配置阶段声明了多字节支持后才生效。
TIME ZONE
TIMEZONE
为你的会话设置缺省时区.参数可以是一个 SQL 时间间隔常量, 一个整数或者双精度常量,或者一个代表宿主操作系统支持地时区字串.
用于时区的可能值取决于你的操作系统.例如,在Linux上 /usr/share/zoneinfo 包含时区的数据库.
下面是一些时区的有效值:
'PST8PDT'
把时区值设为 California.
'Portugal'
把时区值设为 Portugal.
'Europe/Rome'
把时区值设为 Italy
7
把时区设置为 GMP 以西 7 小时(等效于 PDT).
INTERVAL '08:00' HOUR TO MINUTE
把时区设置为 GMP 以西 8 小时(等效于 PST).
LOCAL
DEFAULT
把时区值设为你的本地时区(你的操作系统确省的那个).
如果声明了一个非法的时区,时区就设为GMT(在大多数系统上如此).
如果一个基于 libpq 的客户端的环境里设置了PGTZ, libpq 将在联接启动时自动把 TIMEZONE 设置成为PGTZ的值。
一个扩展的其它运行时参数列表可以在 管理员手册里找到.
使用 SHOW来显示当前 的参数设置.
诊断
SET VARIABLE
成功的返回信息.
ERROR: not a valid option name: name
你试图设置的参数不存在.
ERROR: permission denied
为了访问一些设置,你必须是超级用户.
ERROR: name can only be set at start-up
有些参数在服务器启动后就无法更改了.
例子
把日期时间风格设置为传统的 PostgreSQL风格,同时还有Europen(欧洲)风格:
SET DATESTYLE TO PostgreSQL,European;
把时区设置为 Berkeley, California, 使用双引号保存时区声明里大写字符的属性(注意这里的日期/时间格式是 ISO):
SET TIME ZONE "PST8PDT";
SELECT CURRENT_TIMESTAMP AS today;
  
         today
------------------------
 1998-03-31 07:41:21-08
设置时区为 Italy(注意这里要求的单或者双引号来操作特殊的字符):
SET TIME ZONE 'Europe/Rome';
SELECT CURRENT_TIMESTAMP AS today;
  
         today
------------------------
 1998-03-31 17:41:31+02
兼容性 SQL92
上面显示的第二种语法(SET TIME ZONE) 试图仿真 .不过,SQL只允许数字时区偏移. 所有其他参数设置(包括上面第一种语法)都是 PostgreSQL 扩展.
--------------------------------------------------------------------------------
SHOW
Name
SHOW -- 显示运行时参数的数值
Synopsis
SHOW name
SHOW ALL
输入
name
运行时参数的名称.参阅 SET获取列表.
ALL
显示所有当前会话参数.
描述
SHOW将显示当前运行时参数的数值. 这些变量可以通过 SET 语句来配置,或者在服务器启动时确定.
诊断
ERROR: not a valid option name: name
如果 variable 并不代表一个现存参数, 返回这个参数.
ERROR: permission denied
要获取某些参数,你必须是超级用户.
NOTICE: Time zone is unknown
如果没有设置 TZ 或 PGTZ 环境变量, 返回此信息.
例子
显示当前 DateStyle 的设置:
SHOW DateStyle;
NOTICE: DateStyle is ISO with US (NonEuropean) conventions
显示当前基因优化器 (geqo)设置:
SHOW GEQO;
NOTICE: geqo = true
兼容性 SQL92
SHOW命令是 PostgreSQL 扩展.
--------------------------------------------------------------------------------
TRUNCATE
Name
TRUNCATE  --  清空一个表
Synopsis
TRUNCATE [ TABLE ] name
输入
name
要清空的表。
输出
TRUNCATE
如果表成功清空输出此信息。
描述
TRUNCATE快速地从一个表中删除所有行。它和无条件的 DELETE 有同样的效果,不过因为它不做表扫描,因而快得多。 在大表上最有用。
我们不能在事务块(BEGIN/COMMIT 对) 里执行 TRUNCATE,因为没有办法对其回卷.
用法
截断表 bigtable∶
TRUNCATE TABLE bigtable;
  
兼容性 SQL92 
里没有 TRUNCATE 。
--------------------------------------------------------------------------------
UNLISTEN
Name
UNLISTEN  --  停止监听通知信息
Synopsis
UNLISTEN { notifyname | * }
输入
notifyname
早先注册过的通知条件名称.
*
所有此后端当前正在监听的注册都将被清除.
输出
UNLISTEN
表面该语句已经执行.
描述
UNLISTEN用于删除一个现有的已注册的 NOTIFY. UNLISTEN 取消当前 PostgreSQL 会话中的所有对通知条件 notifyname 监听. 特殊的条件通配符 "*" 则取消对当前会话的所有通知条件的监听.
NOTIFY 包含一些对 LISTEN 和 NOTIFY 的使用的更广泛的讨论.
注意
notifyname不必是一个有效的表名,而可以是任何少于32字符的有效字串名.
如果你 UNLISTEN 一个你没有监听的事件,后端不会报错. 每个后端在退出时都会自动执行 UNLISTEN *.
用法
提交一个现存的注册:
LISTEN virtual;
LISTEN
NOTIFY virtual;
NOTIFY
Asynchronous NOTIFY 'virtual' from backend with pid '8448' received
一旦执行了 UNLISTEN,以后的 NOTIFY 命令将被忽略:
UNLISTEN virtual;
UNLISTEN
NOTIFY virtual;
NOTIFY
-- notice no NOTIFY event is received
兼容性 SQL92 
里没有 UNLISTEN.
--------------------------------------------------------------------------------
UPDATE
Name
UPDATE  --  更新一个表中的行
Synopsis
UPDATE [ ONLY ] table SET col = expression [, ...]
    [ FROM fromlist ]
    [ WHERE condition ]
输入
table
现存表的名称.
column
表 table 中列/字段的名.
expression
赋予列/字段的一个有效的值或表达式.
fromlist
PostgreSQL 的一个非标准的扩展,允许别的表中的列/字段出现在 WHERE 条件里.
condition
请参考 SELECT 语句获得 WHERE 子句的进一步描述.
输出
UPDATE #
成功的返回信息. # 意味着更新的行数. 如果 # 等于 0 则没有行被更新.
描述
UPDATE改变满足条件的所有行的声明了的列/字段的值。 只有要更改的列/字段需要在语句中出现.
数组引用使用与 SELECT里一样的语法.也就是说,单个数组元素, 数组元素的一个范围或者是整个数组都可以用一个查询语句更新.
要更改表,你必须对它有写权限, 同样对 WHERE 条件里提到的任何表也要有读权限.
缺省时,UPDATE将更新所声明的表和所有子表的记录. 如果你希望只更新所声明的表,你应该使用ONLY子句.
用法
把字段 kind 里的词 "Drama" 用 "Dramatic" 代替:
UPDATE films
SET kind = 'Dramatic'
WHERE kind = 'Drama';
SELECT *
FROM films
WHERE kind = 'Dramatic' OR kind = 'Drama';
 code |     title     | did | date_prod |   kind   | len
-------+---------------+-----+------------+----------+-------
 BL101 | The Third Man | 101 | 1949-12-23 | Dramatic | 01:44
 P_302 | Becket        | 103 | 1964-02-03 | Dramatic | 02:28
 M_401 | War and Peace | 104 | 1967-02-12 | Dramatic | 05:57
 T_601 | Yojimbo       | 106 | 1961-06-16 | Dramatic | 01:50
 DA101 | Das Boot      | 110 | 1981-11-11 | Dramatic | 02:29
兼容性 SQL92 
 在定义的 UPDATE 语句上定义了一些不同的语法:
UPDATE table SET column = expression [, ...]
    WHERE CURRENT OF cursor
   
这里 cursor 表示一个打开的游标.
--------------------------------------------------------------------------------
VACUUM
Name
VACUUM  --  垃圾收集以及可选地分析一个数据库
Synopsis
VACUUM [ FULL ] [ FREEZE ] [ VERBOSE ] [ table ]
VACUUM [ FULL ] [ FREEZE ] [ VERBOSE ] ANALYZE [ table [ (column [, ...] ) ] ]
输入
FULL
选择"完全"清理,这样可以恢复更多的空间,但是花的时间更多并且在表上施加了排它锁.
FREEZE
选择激进的元组"冻结".
VERBOSE
为每个表打印一份详细的清理工作报告.
ANALYZE
更新用于优化器的统计信息,以决定执行查询的最有效方法.
table
要清理的表的名称.缺省时是当前数据库中的所有表.
column
要分析的具体的列/字段名称.缺省是所有列/字段.
输出
VACUUM
命令完成.
NOTICE: --Relation table--
表 table 的报告头.
NOTICE: Pages 98: Changed 25, Reapped 74, Empty 0, New 0; Tup 1000: Vac 3000, Crash 0, UnUsed 0, MinLen 188, MaxLen 188; Re-using: Free/Avail. Space 586952/586952; EndEmpty/Avail. Pages 0/74. Elapsed 0/0 sec.
表 table 自身的分析数据.
NOTICE: Index index: Pages 28; Tuples 1000: Deleted 3000. Elapsed 0/0 sec.
目标表的索引的分析.
描述
VACUUM回收已删除元组占据的存储空间. 在一般的 PostgreSQL 操作里,那些已经 DELETE 的元组或者被 UPDATE 过后过时的元组是没有从它们所属的表中物理删除的;在完成 VACUUM 之前它们仍然存在.因此我们有必须周期地运行 VACUUM, 特别是在常更新的表上.
如果没有参数,VACUUM 处理当前数据库里每个表, 如果有参数,VACUUM 只处理那个表.
VACUUM ANALYZE先执行一个 VACUUM 然后是给每个选定的表执行一个 ANALYZE. 对于日常维护脚本而言,这是一个很方便的组合.参阅 ANALYZE获取更多有关其处理的细节.
简单的 VACUUM (没有FULL) 只是简单地回收空间并且令其可以再次使用.这种形式的命令可以和对表的普通读写并行操作.VACUUM FULL 执行更广泛的处理,包括跨块移动元组,以便把表压缩到最少的磁盘块数目里.这种形式要慢许多并且在处理的时候需要在表上施加一个排它锁.
FREEZE是一种特殊用途的选项,它导致元组尽可能快地 标记为"冻结(frozen)",而不是等到它们已经相当老的时候 才标记.如果在同一个数据库上没有其它运行着的事务的时候完成这个命令,那么系统就保证在数据库里的所有元组都是"冻结(frozen)"的,因此不会有事务 ID 重叠的问题,而和数据库未清理的时间没有关系. 我们不建议把 FREEZE 用做日常用途.我们用它的唯一 目地是准备和用户定义的模板数据库联接的时候,或者是其它完全是只读的,不会等到日常维护性 VACUUM 操作的数据库.参阅管理员手册获取细节.
注意
我们建议在经常VACUUMM(清理)(至少每晚一次) 生产数据库, 以保证不断地删除失效的行.尤其是在增删了大量记录之后,对受影响的表执行 VACUUM ANALYZE 命令是一个很好的习惯.这样做将更新系统目录为最近的更改,并且允许 PostgreSQL 查询优化器在规划用户查询时有更好的选择.
我们不建议日常使用 FULL 选项,但是可以在特殊情况下 使用.一个例子就是在你删除了一个表的大部分行之后,希望从物理上缩小该表以减少磁盘空间占用.VACUUM FULL 通常要比单纯的 VACUUM 收缩更多表的尺寸.
用法
下面是一个在 regression (蜕变)数据库里某个表上执行 VACUUM的一个例子:
regression=> VACUUM VERBOSE ANALYZE onek;
NOTICE: --Relation onek--
NOTICE: Index onek_unique1: Pages 14; Tuples 1000: Deleted 3000.
        CPU 0.00s/0.11u sec elapsed 0.12 sec.
NOTICE: Index onek_unique2: Pages 16; Tuples 1000: Deleted 3000.
        CPU 0.00s/0.10u sec elapsed 0.10 sec.
NOTICE: Index onek_hundred: Pages 13; Tuples 1000: Deleted 3000.
        CPU 0.00s/0.10u sec elapsed 0.10 sec.
NOTICE: Index onek_stringu1: Pages 31; Tuples 1000: Deleted 3000.
        CPU 0.01s/0.09u sec elapsed 0.10 sec.
NOTICE: Removed 3000 tuples in 70 pages.
        CPU 0.02s/0.04u sec elapsed 0.07 sec.
NOTICE: Pages 94: Changed 0, Empty 0; Tup 1000: Vac 3000, Keep 0, UnUsed 0.
        Total CPU 0.05s/0.45u sec elapsed 0.59 sec.
NOTICE: Analyzing onek
VACUUM
  
兼容性 SQL92 
里没有 VACUUM 语句.
阅读(2396) | 评论(0) | 转发(0) |
0

上一篇:常用pl/sql(一)

下一篇:PL/SQL优化34条

给主人留下些什么吧!~~