@ -1,6 +1,6 @@
PostgreSQL(ポストグレス・キュー・エル)についてよくある質問とその解答(FAQ)
原文最終更新日: Mon Mar 18 14:34:57 ES T 2002
原文最終更新日: Fri Apr 26 23:03:46 ED T 2002
現在の維持管理者: Bruce Momjian (pgman@candle.pha.pa.us)
Maintainer of Japanese Translation: Jun Kuwamura (juk@postgresql.jp)
@ -73,14 +73,14 @@ docs/faq.html
操作上の質問
4.1) バイナリ・カーソルと通常カーソルとの違いは何ですか?
4.2) 最初の数行 のみを select するにはどうしますか?
4.2) 最初の数ロウ のみを select するにはどうしますか?
4.3) テーブルやその他の情報のリストを psql で見るにはどうしますか?
4.4) テーブルから列 の削除はどのようにしますか?
4.5) 行 、テーブル、データベースの最大サイズは?
4.4) テーブルからカラム の削除はどのようにしますか?
4.5) ロウ 、テーブル、データベースの最大サイズは?
4.6) 一般的なテキストファイルからデータを保存するには、データベースのディスク容
量はどのくらい必要ですか?
4.7) データベース内に定義されたテーブルやインデックスをどのようにして見つけ出し
ますか?
4.7) 定義されたテーブル、インデックス、データベース、および、ユーザをどのように
して見つけ出し ますか?
4.8) 問い合わせが遅いうえ、インデックスを使っている様子がありません。なぜですか
?
4.9) 問い合わせオブティマイザがどのように問い合わせを評価するかを見るにはどうし
@ -106,10 +106,11 @@ docs/faq.html
4.19) どのバージョンの PostgreSQL を走らせているのかを調べるにはどうしますか?
4.20) ラージオブジェクトの操作で、invalid large obj descriptorと出るのはなぜで
すか?
4.21) 現在の時刻がデフォルトとなるような列 はどのようにつくりますか?
4.21) 現在の時刻がデフォルトとなるようなカラム はどのようにつくりますか?
4.22) なぜ、INを使う副問い合わせがとても遅いのですか?
4.23) 外部結合(outer join)はどのように実現しますか?
4.24) 複数のデータベースを使う問い合わせはどのようにすればできますか?
4.25) 関数で複数のロウまたはカラムを返すにはどうしますか?
PostgreSQLの拡張についての質問
@ -750,7 +751,9 @@ postgreSQL
何という関数がどのくらい実行時間を食っているかを見るために、プロファイリング(
プロフィール付き)でコンパイルすることも可能です。そのバックエンドのプロフィー
ル・ファイルは pgsql/data/base/dbname ディレクトリに格納されるでしょう。クライ
アントのプロフィールはクライアントの現行ディレクトリに置かれるでしょう。
アントのプロフィールはクライアントの現行ディレクトリに置かれるでしょう。Linux
でまともなプロファイリングを行うには -DLINUX_PROFILE でコンパイルする必要があり
ます。
3.8) 接続しようとするときに 'Sorry, too many clients' が出るのはなぜですか?
@ -805,16 +808,16 @@ ORDER BY
詳述は、オンラインマニュアルで DECLARE を見て下さい。
4.2) 最初の数行 のみを SELECT するにはどうしますか?
4.2) 最初の数ロウ のみを SELECT するにはどうしますか?
オンラインマニュアルでFETCHを見てください。あるいは、SELECT ... LIMIT....を使っ
てみて下さい。
たとえ、欲しいのは最初の数行 だけでも、すべての問い合わせを評価しなくてはならな
いかもしれません。ORDER BY を持った問い合わせを考えてみて下さい。もし、ORDER BY
に合ったインデックスがあるとすると PostgreSQLは要求された最初の数行だけで評価で
きるかもしれませんが、でなれば、PostgreSQL は意図した行が生成されるまですべての
行 を評価しなければならないかもしれません。
たとえ、欲しいのは最初の数ロウ だけでも、すべての問い合わせを評価しなくてはなら
な いかもしれません。ORDER BY を持った問い合わせを考えてみて下さい。もし、ORDER
BY に合ったインデックスがあるとすると PostgreSQLは要求された最初の数ロウだけで評
価で きるかもしれませんが、でなれば、PostgreSQL は意図したロウが生成されるまです
べてのロウ を評価しなければならないかもしれません。
4.3) テーブルやその他の情報のリストを psql で見るにはどうしますか?
@ -823,22 +826,25 @@ psql
コマンドが含まれています。 psql に -E オプションをつけて起動すれば、与えたコマ
ンドを実行するための問い合わせが出力されます。
4.4) テーブルから列 の削除はどのようにしますか?
4.4) テーブルからカラム の削除はどのようにしますか?
ALTER TABLE DROP COLUMN はサポートしていませんが、その代わりにこうします:
SELECT ... -- 削除したい列以外の列をすべて選択します。
BEGIN;
LOCK TABLE old_table;
SELECT ... -- 削除したいカラム以外のカラムをすべて選択します。
INTO TABLE new_table
FROM old_table;
DROP TABLE old_table;
ALTER TABLE new_table RENAME TO old_table;
[訳注:列の追加は ALTER TABLE ADD COLUMN で行えます。]
COMMIT;
[訳注:カラムの追加は ALTER TABLE ADD COLUMN で行えます。]
4.5) 行 、テーブル、データベースの最大サイズは?
4.5) ロウ 、テーブル、データベースの最大サイズは?
制限は以下のとおりです。
データベースの最大サイズ? 制限無し (500GB のデータベースも存在します)
テーブルの最大サイズ? 16TB
行 の最大サイズ? 7.1以降で制限無し
ロウ の最大サイズ? 7.1以降で制限無し
フィールドの最大サイズ? 7.1以降で1GB
テーブル内での最大ロウ数? 制限無し
テーブル内での最大カラム数? カラムの型により250-1600
@ -865,7 +871,7 @@ ALTER TABLE DROP COLUMN
う。テキストの文字列の平均長さを20バイトと仮定すると、フラットファイルの大きさ
は約2.8MB です。このデータを含む PostgreSQL データベースファイルの大きさは次の
ように約6.4MBと見積もることができます:
36 bytes: 各行 のヘッダ(概算)
36 bytes: 各ロウ のヘッダ(概算)
24 bytes: 整数(int)フィールドとテキスト(text)フィールド
+ 4 bytes: ページ上のタップルへのポインタ
----------------------------------------
@ -886,29 +892,30 @@ ALTER TABLE DROP COLUMN
インデックスは、これほどのオーバヘッドは要求しませんが、インデックス付けされる
データを含む以上、それなりに大きくなります。
4.7) データベース内に定義されたテーブルやインデックスをどのようにして見つけ出し
ますか?
4.7) 定義されたテーブル、インデックス、データベース、および、ユーザをどのように
して見つけ出し ますか?
psql にはいろいろなバックスラッシュ・コマンドがあり、こうした情報を表示します。
バックスラッシュ・コマンドの種類を見るには \? を使って下さい。
また、pgsql/src/tutorial/syscat.source ファイルを走らせてみて下さい。それは、沢
山の SELECT 文により必要な情報をデータベースのシステム・テーブルから取り出して
例示してくれます。
例示してくれます。また、pg_ で始まるシステムテーブルにも記述されています。さら
に、psql -l はすべてのデータベースをリスト表示します。
4.8) 問い合わせが遅いうえ、インデックスを使っている様子がありません。なぜですか
?
インデックスは自動的にすべての問い合わせで使われるわけではありません。テーブル
が最小サイズより大きく、問い合わせでそのわずかなパーセンテージの行を選択する時
だけ、インデックスは使われます。これはインデックススキャンにより起こされるラン
ダムなディスクアクセスは、テーブルをストレートに読む順次走査よりも遅くなること
がときどきあるからです。
が最小サイズより大きく、問い合わせでそのわずかなパーセンテージのロウを選択する
時 だけ、インデックスは使われます。これはインデックススキャンにより起こされるラ
ン ダムなディスクアクセスは、テーブルをストレートに読む順次走査よりも遅くなるこ
と がときどきあるからです。
インデックスを使うかを決定するために、PostgreSQL はテーブルについての統計情報を
持たなければなりません。この統計情報は、VACUUM ANALYZEまたは、単に ANALYZE を使
って収集することができます。統計情報を使ってオブティマイザはテーブルの中に何行
あるか を知り、インデックスを使うべきかのの決定をより正しくできます。統計情報は
って収集することができます。統計情報を使ってオブティマイザはテーブルの中にある
ロウ数 を知り、インデックスを使うべきかのの決定をより正しくできます。統計情報は
最適な結合順や結合方法を決める上でも貴重なものもあります。統計情報の収集は、テ
ーブルの内容がかわると毎に繰返しなされるべきです。
@ -1003,7 +1010,7 @@ Type Internal Name Notes
"char" char 1 character
CHAR(#) bpchar 指定された固定長となるように空白が詰められる
VARCHAR(#) varchar 長さの上限の無いテキスト
TEXT text 長さの制限は最大行 長による
TEXT text 長さの制限は最大ロウ 長による
BYTEA bytea 可変長のバイト配列(null-byte safe)
内部名にお目にかかるのは、システム・カタログを調べるときや、エラーメッセージを
@ -1012,8 +1019,8 @@ BYTEA bytea
上記の型のうち後の4つの型は "varlena" 型です(すなわち、ディスクの最初の4バイ
トがデータ長で、それの後に実際のデータが続きます)。このように実際の空間は宣言さ
れた大きさよりも少し大きくなります。しかし、これらのデータ型はTOASTにより圧縮さ
れたり複数行 に渡って保存されたりして、ディスク上の空間は思ったより小さくなりま
す。
れたり複数ロウ に渡って保存されたりして、ディスク上の空間は思ったより小さくなり
ま す。
CHAR()はいつも長さが同じ文字列を保存するのに最適です。VARCHAR() は可変長の文字
列を保存するのに最適ですが、保存できる文字列の長さに制限があります。TEXT は長さ
@ -1022,8 +1029,8 @@ NULL
4.15.1) 通番(serial)/自動増分フィールドはどのようにつくりますか?
PostgreSQL は SERIAL データ型をサポートします。列上に通番とインデックスを自動作
成します。たとえば、
PostgreSQL は SERIAL データ型をサポートします。カラム上に通番とインデックスを自
動作 成します。たとえば、
CREATE TABLE person (
id SERIAL,
name TEXT
@ -1038,8 +1045,8 @@ PostgreSQL
通番についてのもっと詳しい情報は、オンラインマニュアルで create_sequence をご覧
下さい。
また、各行 のOIDフィールドを一意値として使うこともできます。しかしながら、もしも
データベースをダンプしてりロードする必要がある場合は、OIDを温存するために
また、各ロウ のOIDフィールドを一意値として使うこともできます。しかしながら、もし
も データベースをダンプしてりロードする必要がある場合は、OIDを温存するために
pg_dump で -oオプションを使うか、または、COPY WITH OIDSオプションを使う必要があ
ります。 Bruce Momjian の(http://www.PostgreSQL.org/docs/aw_pgsql_book)の
Numbering Rowsの章にありあます。
@ -1054,7 +1061,7 @@ Numbering Rows
そうして、new_id に保存した新しい値を他の問い合わせに(たとえば、person テーブル
に対する外部キー(foreign key)のように)使うとよいでしょう。自動的に作られた
SEQUENCEオブジェクトの名前は、<table>_<serialcolumn>_seq のようになり、このうち
、table と serialcolumn はそれぞれテーブルの名前とSERIAL列 の名前です。
、table と serialcolumn はそれぞれテーブルの名前とSERIALカラム の名前です。
あるいは、与えられたSERIAL値を、それが既定値として挿入された後で(after)、
currval() 関数を使って取り出すこともできます。たとえば、
@ -1080,19 +1087,19 @@ OID
4.16) OID とは何ですか? TID とは何ですか?
OID とは一意の行 ID に対する PostgreSQL の答えです。PostgreSQL の中でつくられる
すべての行 は一意の OID を得ます。initdb で発生される OID はすべて 16384
OID とは一意のロウ ID に対する PostgreSQL の答えです。PostgreSQL の中でつくられ
るすべてのロウ は一意の OID を得ます。initdb で発生される OID はすべて 16384
(backend/access/transam.h から)より小さな値です。initdb 後のすべての OID (ユー
ザ作成)はそれ以上の値になります。既定では、これらすべての OIDは一つのデーブルや
データベース内に留まらず、PostgreSQL インストレーション全体の中で一意です。
PostgreSQL はテーブル間の行 を結びつけるために、そのシステムテーブル内に OID を
使います。この OID は特定のユーザの行 を識別するためや結合の中で使われることがで
きます。OID の値を保存するためには OID 型を列に使うことを奨めます。より速くアク
セスするために OID フィールドにインデックスを作ることができます。 OID は、全て
のデータベースで使われる中央領域から、全ての新しい行に割り当てられます。OID を
他の何かに変えたい、あるいは元の OID もテーブルと一緒にコピーしたいのなら、でき
なくはありません。
PostgreSQL はテーブル間のロウ を結びつけるために、そのシステムテーブル内に OID
を 使います。この OID は特定のユーザのロウ を識別するためや結合の中で使われること
がで きます。OID の値を保存するためには OID 型をカラムに使うことを奨めます。より
速くアク セスするために OID フィールドにインデックスを作ることができます。 OID
は、全て のデータベースで使われる中央領域から、全ての新しいロウに割り当てられま
す。OID を 他の何かに変えたい、あるいは元の OID もテーブルと一緒にコピーしたいの
なら、できな くはありません。
CREATE TABLE new (old_oid oid, mycol int);
SELECT old_oid, mycol INTO new FROM old;
COPY new TO '/tmp/pgtable';
@ -1104,9 +1111,9 @@ OID
う。誰もこれが起きたと報告してくる人はいませんでしたが、そうなる前にこの制限を
取り除くことを計画しています。
TID は特定の物理行 をそのブロックとオフセット値で識別するために使われます。TID
は行が修正されたり再ロードされると変わります。それらの TID は、物理行を指すため
にインデックス記載で使われます。
TID は特定の物理ロウ をそのブロックとオフセット値で識別するために使われます。TID
はロウが修正されたり再ロードされると変わります。それらの TID は、物理ロウを指す
ため にインデックス記載で使われます。
4.17) PostgreSQL で使われるいくつかの用語の意味は何ですか?
@ -1115,8 +1122,8 @@ TID
・ テーブル(table)、関係(relation)、クラス(class)
・ 行 (row)、レコード(record)、タップル(tuple)
・ 列 (column)、フィールド(field)、属性(attribute)
・ ロウ (row)、レコード(record)、タップル(tuple)
・ カラム (column)、フィールド(field)、属性(attribute)
・ 取得(retrieve)、選択(select)
・ 置換(replace)、更新(update)
・ 追加(append)、挿入(insert)
@ -1157,23 +1164,23 @@ psql
現在は、PostgreSQLのトランザクションのコミット時にラージ・オブジェクト・ハンド
ルを閉じることにより、lo_openコマンドが完了した直後に強制的にルールを実行します
。このため、最初にハンドルに対して何かをしようとすると、invalid large obj
descriptor(ラージオブジェクトの記述子が不正)となります。それで、もし、トランザ
クションを使うのを忘れると、(少なくともほとんどの時間)働いていたコードがエラ
ーメッセージを出すのです。
descriptor(ラージ・ オブジェクトの記述子が不正)となります。それで、もし、トラン
ザ クションを使うのを忘れると、(少なくともほとんどの時間)働いていたコードがエ
ラ ーメッセージを出すのです。
もし、ODBCのようなクライアントインターフェースをお使いなら、auto-commit offを設
定する必要があるかもしれません。
4.21) 現在の時刻がデフォルトとなるような列 はどのようにつくりますか?
4.21) 現在の時刻がデフォルトとなるようなカラム はどのようにつくりますか?
CURRENT_TIMESTAMPを使います:
CREATE TABLE test (x int, modtime timestamp DEFAULT >CURRENT_TIMESTAMP );
4.22) なぜ、INを使う副問い合わせがとても遅いのですか?
現在、外部問い合わせの各行 について副問い合わせの結果を順番にスキャンすることに
より、副問い合わせを外部問い合わせに結合しています。当面はINをEXISTSで置き換え
ることです:
現在、外部問い合わせの各ロウ について副問い合わせの結果を順番にスキャンすること
に より、副問い合わせを外部問い合わせに結合しています。当面はINをEXISTSで置き換
え ることです:
SELECT *
FROM tab
WHERE col1 IN (SELECT col2 FROM TAB2)
@ -1193,12 +1200,12 @@ SELECT *
SELECT *
FROM t1 LEFT OUTER JOIN t2 USING (col);
これらの象徴的な問い合わせでは t1.col を t2.col と結合して、t1 の結合されなかっ
た行(t2 と一致しなかった行 )も返しています。RIGHT 結合は t2 の結合されなかった行
を加えるでしょう。FULL 結合は、一致した行に t1 と t2 からは結合されなかった行を
返すでしょう。OUTER という言葉はオプションで LEFT, RIGHT, または FULL などの結
合を仮定されています。以前のリリースでは外部結合(outer join)をUNION と NOT IN
を使ってシミュレートできます。たとえば、tab1 と tab2 を結合するときは、次の問い
合わせで二つのテーブルを外部結合します。
たロウ(t2 と一致しなかったロウ )も返しています。RIGHT 結合は t2 の結合されなかっ
たロウ を加えるでしょう。FULL 結合は、一致したロウに t1 と t2 からは結合されなか
ったロウを 返すでしょう。OUTER という言葉はオプションで LEFT, RIGHT, または FULL
などの結 合を仮定されています。以前のリリースでは外部結合(outer join)をUNION と
NOT IN を使ってシミュレートできます。たとえば、tab1 と tab2 を結合するときは、
次の問い 合わせで二つのテーブルを外部結合します。
SELECT tab1.col1, tab2.col2
FROM tab1, tab2
WHERE tab1.col1 = tab2.col1
@ -1218,6 +1225,12 @@ PostgreSQL
もちろん、クライアントは同時に異なる複数のデータベースへ接続してそこにある情報
をマージすることはできます。
4.25) 関数で複数のロウまたはカラムを返すにはどうしますか?
もし、PL/pgSQL 関数でrefcursorsを使うと結果の組を返すことができます。 http://
developer.postgresql.org/docs/postgres/plpgsql-cursors.html の 23.7.3.3 節をご
覧下さい。
━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━
PostgreSQLの拡張についての質問
@ -1250,7 +1263,7 @@ PostgreSQL
[訳注:
日本語版の製作については以下の通りです。
最終更新日: 2002年04月05 日
最終更新日: 2002年05月08 日
翻訳者: 桑村 潤 (Jun Kuwamura <juk@postgresql.jp>)
このFAQの和訳の作成にあたり協力をしてくださった方々(敬称は略させていただきます):