Postgres使用默认设置(sql FIDLE)选择最高顺序的设置

Postgres使用默认设置(sql FIDLE)选择最高顺序的设置,sql,postgresql,postgresql-9.4,Sql,Postgresql,Postgresql 9.4,假设我有一些设置的作用域是用户,但总是有一个默认设置(当user\u id为NULL时): 设置: name | value | user_id | confirmed ________________________________________ fav_drink | coke | NULL | NULL # the default fav_drink | pepsi | 1 | false fav_drink | sprite |

假设我有一些设置的作用域是用户,但总是有一个默认设置(当user\u id为NULL时):

设置

   name   | value  | user_id | confirmed
________________________________________
fav_drink | coke   |  NULL   |   NULL     # the default
fav_drink | pepsi  |    1    |   false
fav_drink | sprite |    1    |   true
fav_band  | elvis  |  NULL   |   true     # the default
fav_band  | beatles|    1    |   false
fav_sport | hockey |  NULL   |   true     # the default
我想做的是获取用户的所有设置,按名称分组,首选(1)确认为真,(2)确认为假,或(3)默认设置,结果是:

    name   | value  | user_id | confirmed
________________________________________
fav_drink | sprite |    1    |   true
fav_band  | beatles|    1    |   false
fav_sport | hockey |  NULL   |   true 
如何在Postgres中构造查询来实现这一点?类似(我意识到这是粗略的伪代码):

(我正在使用postgres 9.x)


基于false为0的逻辑,true os 1和null合并为-1

已更新

t=# with a as (
SELECT name, value, user_id, max(coalesce(confirmed::int,-1)) over (partition by name), coalesce(confirmed::int,-1)
from settings
WHERE user_id = 1 OR user_id IS NULL
)
select name,value,user_id,coalesce::boolean::text
  from a
where max= coalesce
order by 1;
   name    | value  | user_id | coalesce
-----------+--------+---------+----------
 fav_band  | elvis  |         | true
 fav_drink | sprite |       1 | true
 fav_sport | hockey |         | true
(3 rows)

这里fav_band的用户id为null(与OP不同),因为
elvis
已确认为true,甲壳虫乐队确认为false,因此true为“first”

我认为如果您将其视为一个视图,并用多个表构建它,您会发现使用这些数据更容易:一个是
活动
带有
活动,默认名称(外键)
;另一个
活动名称
,即
活动(外键),活动名称
;第三个是
用户
,具有
用户id
和其他数据;第四个是用于
用户id、活动、活动名称和已确认的
的联接表
选项
。注意,互易外键使初始化表变得有点棘手,但是可以推迟引用完整性检查

SELECT users.*, activities.activity, 
       COALESCE(activity_name, default_name), confirmed
FROM activities NATURAL JOIN activity 
     LEFT NATURAL JOIN (users NATURAL JOIN choices)
WHERE user_id = 1
ORDER BY confirmed DESC NULLS LAST;

唯一的缺点是,对于没有确认的活动,用户数据中会出现空白(默认选择)。这是可以解决的。但首先我建议你考虑如何规范表格。< / P>这太棒了!如果默认设置已确认设置为true,该如何工作?(我更新了上面的问题,将该场景包括在内)但为什么会将默认设置为true?你的整个前提是
NULL
是默认值的标记。我不明白从结构上我是如何故意区分确认的eq true和默认确认的eq true的。我想在这种情况下,您可能需要另一个专栏来说明差异,或者我把它放在SQL小提琴中,但它似乎不起作用
SELECT users.*, activities.activity, 
       COALESCE(activity_name, default_name), confirmed
FROM activities NATURAL JOIN activity 
     LEFT NATURAL JOIN (users NATURAL JOIN choices)
WHERE user_id = 1
ORDER BY confirmed DESC NULLS LAST;