设置select中返回的空字段的默认值

时间:2012-11-01 20:15:45

标签: mysql sql postgresql select

给出两个表:

image(id, cat_id, name)
image_translation(id, title, desc, lang)

(名称和ID是唯一的)

查询以选择特定文件的所有翻译:

SELECT c.id           AS c__id, 
       c.cat_id       AS c__cat_id, 
       c.name         AS c__name, 
       c2.id          AS c2__id, 
       c2.title       AS c2__title, 
       c2.desc        AS c2__desc, 
       c2.lang        AS c2__lang, 
FROM   image c 
       LEFT JOIN image_translation c2 
              ON c.id = c2.id 
WHERE  ( c1.name = 'file.jpg' ) 

返回:

c__id | c__cat_id  | c2__id    | c__name   | c2__title     | cs__desc     | c2__lang
------+------------+-----------+-----------+---------------+--------------+--------- 
114   | 2          | 114       | file.jpg  | default title | default desc | en
114   | 2          | 114       | file.jpg  | NULL          | desc in de   | de
114   | 2          | 114       | file.jpg  | title in fr   | ''           | fr

要选择特定语言的特定文件的翻译, 显然我需要添加where子句。

但是它返回默认的行内容,可能在翻译中包含空字段。

如何将结果与默认值合并,并使用默认值覆盖empy字段?为lang en 返回默认值:

SELECT c2.title       AS c2__title, 
       c2.desc        AS c2__desc, 
       c2.lang        AS c2__lang, 
FROM   image c 
       LEFT JOIN image_translation c2 
              ON c.id = c2.id 
WHERE  ( c1.name = 'file.jpg' ) 
AND WHERE ( c2.lang = 'en')

我期望的样本结果:

对于德语:

-- AND WHERE ( c2.lang = 'de' ) 

c__id | c__cat_id | c2__id    | c__name   | c2__title     | cs__desc     | c2__lang
-----+------------+-----------+-----------+---------------+--------------+--------- 
114  | 2          | 114       | file.jpg  | default title | desc in de   | de

代表法语:

-- AND WHERE ( c2.lang = 'fr' ) 

c__id | c__cat_id | c2__id    | c__name   | c2__title     | cs__desc     | c2__lang
-----+------------+-----------+-----------+---------------+--------------+--------- 
114  | 2          | 114       | file.jpg  | title in fr   | default desc | fr

如何在一个智能查询中正确执行此操作?

(我使用MySQL和Doctrine ORM与I18N行为)

2 个答案:

答案 0 :(得分:4)

我不知道你是否要求这个简单的查询:

对于'fr':

SELECT c2.title AS c2__title, 
       coalesce( nullif( c2.desc, '') , c3.desc )   AS desc, 
       coalesce( nullif( c2.lang, '') , c3.lang  )  AS lang, 
FROM   image c 
LEFT JOIN image_translation c2 
              ON c2.lang = 'fr' and c.id = c2.id 
LEFT JOIN image_translation c3
              ON c3.lang = 'en' and c.id = c3.id 
WHERE  ( c1.name = 'file.jpg' ) 

答案 1 :(得分:2)

你可以做两个left joins,第二个寻找默认语言。然后case可以在两者之间做出决定:

select case 
       when it1.title = '' or it1.title is null then it2.title 
       else it1.title 
       end as title
,      case 
       when it1.desc = '' or it1.desc is null then it2.desc
       else it1.desc
       end as desc
from   image i
left join
       image_translation it1
on     c.id = c2.id 
       and it1.lang1 = 'fr'
left join
       image_translation it2
on     c.id = c2.id 
       and it2.lang1 = 'en'
where  i.name = 'file.jpg'