在PostgreSQL 8.4.13中我有两张代表纸牌游戏的牌桌(每张牌都有3名玩家)以及这些游戏的得分结果。玩家由id
列标识,游戏按gid
标识:
# \d pref_games
Table "public.pref_games"
Column | Type | Modifiers
--------+-----------------------------+----------------------------------------------------------
gid | integer | not null default nextval('pref_games_gid_seq'::regclass)
rounds | integer | not null
stamp | timestamp without time zone | default now()
Indexes:
"pref_games_pkey" PRIMARY KEY, btree (gid)
Referenced by:
TABLE "pref_scores" CONSTRAINT "pref_scores_gid_fkey" FOREIGN KEY (gid) REFERENCES pref_games(gid) ON DELETE CASCADE
# \d pref_scores
Table "public.pref_scores"
Column | Type | Modifiers
---------+-----------------------+-----------
id | character varying(32) | not null
gid | integer | not null
money | integer | not null
last_ip | inet |
quit | boolean |
Indexes:
"pref_scores_pkey" PRIMARY KEY, btree (id, gid)
"pref_scores_gid_index" btree (gid)
Foreign-key constraints:
"pref_scores_gid_fkey" FOREIGN KEY (gid) REFERENCES pref_games(gid) ON DELETE CASCADE
"pref_scores_id_fkey" FOREIGN KEY (id) REFERENCES pref_users(id) ON DELETE CASCADE
我试图找出一个id='OK261593357402'
的玩家是否玩过id='MR3689735717800138910'
玩家 - 这样我就可以让他们在我的网站上互相评分。
我想我需要在perform true
上拨打inner join
- 这是正确的吗?
所以我在尝试:
# select * from pref_games g inner join pref_scores s on (s.gid=g.gid) where s.id='OK261593357402';
gid | rounds | stamp | id | gid | money | last_ip | quit
---------+--------+----------------------------+----------------+---------+-------+----------------+------
2124241 | 20 | 2013-05-01 12:26:54.052086 | OK261593357402 | 2124241 | 28 | 93.232.91.105 | f
2125575 | 17 | 2013-05-01 16:53:21.090822 | OK261593357402 | 2125575 | 32 | 93.232.91.105 | f
2125881 | 20 | 2013-05-01 17:47:26.15633 | OK261593357402 | 2125881 | -31 | 93.232.91.105 | f
2126242 | 0 | 2013-05-01 18:41:06.769132 | OK261593357402 | 2126242 | 0 | 93.232.91.105 | f
2126244 | 0 | 2013-05-01 18:41:12.495192 | OK261593357402 | 2126244 | 0 | 93.232.91.105 | t
2126259 | 0 | 2013-05-01 18:42:39.974518 | OK261593357402 | 2126259 | 0 | 93.232.91.105 | t
2126613 | 33 | 2013-05-01 19:27:11.88462 | OK261593357402 | 2126613 | -132 | 93.232.91.105 | f
2126813 | 0 | 2013-05-01 19:57:05.23061 | OK261593357402 | 2126813 | 0 | 93.232.91.105 | t
2127299 | 20 | 2013-05-01 20:36:42.021133 | OK261593357402 | 2127299 | 136 | 93.232.91.105 | f
2127821 | 0 | 2013-05-01 21:33:32.168757 | OK261593357402 | 2127821 | 0 | 93.232.91.105 | f
2127830 | 0 | 2013-05-01 21:34:47.694645 | OK261593357402 | 2127830 | 0 | 93.232.91.105 | t
2128012 | 21 | 2013-05-01 22:04:03.850061 | OK261593357402 | 2128012 | 55 | 93.232.91.105 | f
2129551 | 13 | 2013-05-02 10:08:37.348426 | OK261593357402 | 2129551 | -32 | 79.250.39.175 | f
2129818 | 13 | 2013-05-02 11:21:50.998484 | OK261593357402 | 2129818 | 71 | 79.250.39.175 | f
2130467 | 11 | 2013-05-02 13:55:00.034698 | OK261593357402 | 2130467 | -79 | 79.250.39.175 | f
2130470 | 0 | 2013-05-02 13:55:41.298932 | OK261593357402 | 2130470 | 0 | 79.250.39.175 | f
2130476 | 0 | 2013-05-02 13:56:22.359713 | OK261593357402 | 2130476 | 0 | 79.250.39.175 | f
.....
但是我只看到上面的id='OK261593357402'
,即我期待看到他所有的游戏合作伙伴,但他们没有交付。
我也试过了:
# select * from pref_games g left outer join pref_scores s on (s.gid=g.gid) where s.id='OK261593357402';
gid | rounds | stamp | id | gid | money | last_ip | quit
---------+--------+----------------------------+----------------+---------+-------+----------------+------
2124241 | 20 | 2013-05-01 12:26:54.052086 | OK261593357402 | 2124241 | 28 | 93.232.91.105 | f
2125575 | 17 | 2013-05-01 16:53:21.090822 | OK261593357402 | 2125575 | 32 | 93.232.91.105 | f
2125881 | 20 | 2013-05-01 17:47:26.15633 | OK261593357402 | 2125881 | -31 | 93.232.91.105 | f
2126242 | 0 | 2013-05-01 18:41:06.769132 | OK261593357402 | 2126242 | 0 | 93.232.91.105 | f
2126244 | 0 | 2013-05-01 18:41:12.495192 | OK261593357402 | 2126244 | 0 | 93.232.91.105 | t
2126259 | 0 | 2013-05-01 18:42:39.974518 | OK261593357402 | 2126259 | 0 | 93.232.91.105 | t
2126613 | 33 | 2013-05-01 19:27:11.88462 | OK261593357402 | 2126613 | -132 | 93.232.91.105 | f
2126813 | 0 | 2013-05-01 19:57:05.23061 | OK261593357402 | 2126813 | 0 | 93.232.91.105 | t
...
不幸的是同样的结果......
我是否应该将一系列select
与exists in
结合使用?
答案 0 :(得分:1)
select pg.*, ps.id, ps2.id
from
pref_games pg
inner join
pref_scores ps on pg.gid = ps.gid
inner join
pref_scores ps2 on ps.gid = ps2.gid
where
ps.id = 'OK261593357402'
and ps2.id != 'OK261593357402'
答案 1 :(得分:1)
我试图找出一个
玩过id='OK261593357402'
的玩家是否有 曾与玩家id='MR3689735717800138910'
使用{strong> plpgsql 中的IF EXISTS ...
比使用PERFORM
IF FOUND ...
的{{1}}更优雅/更简单/更优雅:
IF EXISTS (
SELECT 1
FROM pref_scores p1
JOIN pref_scores p2 USING (gid)
WHERE p1.id = 'OK261593357402'
AND p2.id = 'MR3689735717800138910'
) THEN
-- do stuff
END IF;
您根本不需要表pref_games
来回答您的问题。