PostgreSQL,混合食物和食谱

时间:2014-01-09 20:26:48

标签: sql postgresql

在一段时间之前我有一个似乎要解决的problem,但事实并非如此,我必须更好地解释它并支持更合适的表格:

DROP TABLE IF EXISTS usedfood;  
CREATE TABLE usedfood 
   (food_code int, food_name text, qtyu integer, meas text);
INSERT INTO usedfood (food_code, food_name, qtyu, meas)
VALUES (10,  'spaghetti',        3, 'pcs'),
       (156, 'mayonnaise',       2, 'pcs'),
       (173, 'ketchup',          1, 'pcs'),
       (172, 'bolognese sauce',  2, 'pcs'),
       (173, 'ketchup',          1, 'pcs'),
       (175, 'worchester sauce', 2, 'pcs'),
       (177, 'parmesan',         1, 'pcs'),
       (10,  'spaghetti',        2, 'pcs'),
       (156, 'mayonnaise',       1, 'pcs');

DROP TABLE IF EXISTS ingredients;
CREATE TABLE ingredients
   (food_code int, ingr_code int, ingr_name text, qtyi decimal(11,3), meas text);
INSERT INTO ingredients (food_code, ingr_code, ingr_name, qtyi, meas)
VALUES (10,  1256, 'spaghetti rinf', 75, 'gramm'),
       (156, 1144, 'salt',          0.3, 'gramm'),
       (10,  1144, 'salt',          0.5, 'gramm'),
       (156, 1140, 'fresh egg',      50, 'gramm'),
       (172, 1138, 'tomato',         80, 'gramm'),
       (156, 1139, 'mustard',         5, 'gramm'),
       (172, 1136, 'clove',           1, 'gramm'),
       (156, 1258, 'oil',           120, 'gramm'),
       (172, 1135, 'laurel',        0.4, 'gramm'),
       (10,  1258, 'oil',           0.4, 'gramm'),
       (172, 1130, 'corned beef',    40, 'gramm');

这两张表代表食物清单和某些食物中使用的成分清单 然而,有些食物没有成分(这是一个问题)。

此查询计算并列出食品清单中食材和成分通过'food_code'逻辑连接的食品清单的使用情况:

SELECT SUM(f.qtyu) AS used_times,
       COALESCE(i.ingr_code, MAX(f.food_code)) AS code,
       COALESCE(i.ingr_name, MAX(f.food_name)) AS f_name,
       SUM(COALESCE(i.qtyi, 1) * f.qtyu)::decimal(11,3) AS qty,
       COALESCE(max(i.meas), max(f.meas)) AS meas
  FROM usedfood f LEFT JOIN ingredients i
    ON f.food_code = i.food_code
 GROUP BY i.ingr_code, i.ingr_name

但问题在于,所有没有成分的食物都被分组在一起而不是代码,被列为一种食物。这不是我想要的,我希望有些人能够从给定的表中找到并解决这个问题:

 2   173 ketchup            2.000 pcs
 1   175 parmesan           1.000 pcs
 2   177 worchester sauce   2.000 pcs
 8  1144 salt               3.400 gramm
 3  1140 fresh egg        150.000 gramm
 2  1138 tomato           160.000 gramm
 8  1258 oil              362.000 gramm
 2  1135 laurel             0.800 gramm
 5  1256 spaghetti rinf   375.000 gramm
 2  1130 corned beef       80.000 gramm
 3  1139 mustard           15.000 gramm
 2  1136 clove              2.000 gramm

2 个答案:

答案 0 :(得分:1)

尝试将子查询放入,这样您就可以更轻松地对列进行分组而无需有条件地选择两个值:

SELECT sum(temp.used_times), temp.code, temp.f_name, sum(temp.qty), max(temp.meas)
FROM (SELECT f.qtyu AS used_times,
             COALESCE(i.ingr_code, f.food_code) AS code,
             COALESCE(i.ingr_name, f.food_name) AS f_name,
             (COALESCE(i.qtyi, 1) * f.qtyu)::decimal(11,3) AS qty,
             COALESCE(i.meas, f.meas) AS meas
      FROM usedfood f LEFT JOIN ingredients i
      ON f.food_code = i.food_code) as temp
GROUP BY temp.code, temp.f_name
ORDER BY temp.code

答案 1 :(得分:1)

你在找这个吗?

SELECT SUM(f.qtyu) AS used_times,
       COALESCE(i.ingr_code, f.food_code) AS code,
       COALESCE(i.ingr_name, f.food_name) AS f_name,
       SUM(COALESCE(i.qtyi, 1) * f.qtyu)::decimal(11,3) AS qty,
       COALESCE(i.meas, f.meas) AS meas
  FROM usedfood f LEFT JOIN ingredients i
    ON f.food_code = i.food_code
 GROUP BY COALESCE(i.ingr_code, f.food_code), 
          COALESCE(i.ingr_name, f.food_name),
          COALESCE(i.meas, f.meas)
 ORDER BY code;

输出:

| USED_TIMES | CODE |           F_NAME | QTY |  MEAS |
|------------|------|------------------|-----|-------|
|          2 |  173 |          ketchup |   2 |   pcs |
|          2 |  175 | worchester sauce |   2 |   pcs |
|          1 |  177 |         parmesan |   1 |   pcs |
|          2 | 1130 |      corned beef |  80 | gramm |
|          2 | 1135 |           laurel | 0.8 | gramm |
|          2 | 1136 |            clove |   2 | gramm |
|          2 | 1138 |           tomato | 160 | gramm |
|          3 | 1139 |          mustard |  15 | gramm |
|          3 | 1140 |        fresh egg | 150 | gramm |
|          8 | 1144 |             salt | 3.4 | gramm |
|          5 | 1256 |   spaghetti rinf | 375 | gramm |
|          8 | 1258 |              oil | 362 | gramm |

这是 SQLFiddle 演示