|
Chapter 8. 继承让我们创建两个表.表 capitals 包含各州的首府,同时也是cities表. 自然而然,表 capitals 应该从 表 cities 继承下来. CREATE TABLE cities ( name text, population float, altitude int -- (in ft) ); CREATE TABLE capitals ( state char(2) ) INHERITS (cities); 在本例中,一条 capitals 的记录 继承 所有父表 cities 的字段 (name,population,和 altitude). 字段 name 的类型是 text , PostgreSQL 用于变长ASCII字符串的本机类型. 字段 population 的类型是 float , PostgreSQL 用于双精度浮点数的类型. 表 capitals 多一个字段,state,表明首府所在的州. 在 PostgreSQL 里, 一个表可以从0到多个其他表继承下来,一个查询可以 检索一个表的所有记录,或是检索该表和其所有后代的记录.
例如,下面查询将找出所有海拔 500 英尺及以上的城市(包括州首府): SELECT name, altitude FROM cities WHERE altitude > 500; 将返回: +----------+----------+ |name | altitude | +----------+----------+ |Las Vegas | 2174 | +----------+----------+ |Mariposa | 1953 | +----------+----------+ |Madison | 845 | +----------+----------+
另一方面,如果要找出不包括州首府在内的所有海拔超过500英尺的城市, 查询应该是这样的: SELECT name, altitude FROM ONLY cities WHERE altitude > 500; +----------+----------+ |name | altitude | +----------+----------+ |Las Vegas | 2174 | +----------+----------+ |Mariposa | 1953 | +----------+----------+
这里的 cities 前面的 "ONLY" 表面该查询应该只对 cities 进行查找 而不包括继承级别低于 cities 的表.许多我们已经讨论过的命令 -- SELECT , UPDATE 和 DELETE -- 支持这个 "ONLY" 符号. 有时候你可能想知道某条记录来自哪个表.在每个表里我们都有一个系统属性叫 TABLEOID ,它可以告诉你源表是谁: SELECT c.tableoid, c.name, c.altitude FROM cities c WHERE c.altitude > 500; 结果是: +---------+----------+----------+ |tableoid |name | altitude | +---------+----------+----------+ |37292 |Las Vegas | 2174 | +---------+----------+----------+ |37280 |Mariposa | 1953 | +---------+----------+----------+ |37280 |Madison | 845 | +---------+----------+----------+ 如果你和 pg_class 表做一个连接,你就可以看到真正的表名: SELECT p.relname, c.name, c.altitude FROM cities c, pg_class p WHERE c.altitude > 500 and c.tableoid = p.oid; which returns: +---------+----------+----------+ |relname |name | altitude | +---------+----------+----------+ |capitals |Las Vegas | 2174 | +---------+----------+----------+ |cities |Mariposa | 1953 | +---------+----------+----------+ |cities |Madison | 845 | +---------+----------+----------+
继承特性的一个局限性是索引(包括唯一约束)和外键约束只施用于 单个表,而不包括它们的继承的子表.因此,在上面的例子里, 声明另外一个表的字段 REFERENCES cities(name) 将允许其它表包含城市名但不含首府名.这个缺陷可能在未来的 某个版本中得到修补. |