我需要一点帮助头脑风暴查询。我有一个销售表,每个餐厅位置有两行(每天)。一行是AM销售,另一行是PM销售。 AM销售实际上只是AM销售,然而,PM销售是AM销售和PM销售的组合。因此,为了提取PM销售额,您必须从中减去AM销售行。
---------------------------------------------------------
date | id | meridiem | daily_sales | cover_counts |
---------------------------------------------------------
2012-03-22 |103 | AM | 2956.32 | 175 |
2012-03-22 |103 | PM | 12124.62 | 484 |
---------------------------------------------------------
我有一个查询来计算每人平均预计的午餐(来自AM销售),并且效果很好。它基本上从过去6周的销售数据中提取前四周,并对它们进行平均。 (注:每人的平均值是通过按销售额除以销售额计算得出的)。
$statement = "SELECT directory.location, ROUND((SUM(sales.daily_sales / sales.cover_counts) / 4), 2) AS lppa
FROM t_directory directory
LEFT JOIN t_sales sales
ON sales.site_id = directory.site_id
AND DAYOFWEEK(sales.business_date) = DAYOFWEEK(:date1)
AND sales.business_date < DATE_SUB(:date2, INTERVAL 14 DAY)
AND sales.business_date >= DATE_SUB(:date3, INTERVAL 42 DAY)
AND sales.meridiem = 'AM'
WHERE directory.active = 1
GROUP BY directory.site_id
ORDER BY directory.site_id ASC
LIMIT :totalLocations";
$statementHandle = $this->dbHandle->prepare($statement);
$statementHandle->bindValue(':date1', $this->date, PDO::PARAM_STR);
$statementHandle->bindValue(':date2', $this->date, PDO::PARAM_STR);
$statementHandle->bindValue(':date3', $this->date, PDO::PARAM_STR);
$statementHandle->bindValue(':totalLocations', $this->totalLocations, PDO::PARAM_INT);
$statementHandle->execute();
$lppa = $statementHandle->fetchAll(PDO::FETCH_ASSOC);
现在我想计算每人平均晚餐。为了做到这一点,在进行任何数学计算之前,我必须分别从PM销售和封面中减去AM销售和保险。是否有一种简单的方法将所有这些实现到一个查询中?我显然可以用PHP做到这一点,但我只是好奇如何在查询中实现这一点。任何帮助或见解将不胜感激。如果需要更多细节,请告诉我。
答案 0 :(得分:2)
您可以再次加入t_sales,然后过滤“PM”
SELECT DIRECTORY.location,
Round(( SUM(salesPM.daily_sales - salesAM.daily_sales /
salesPM.cover_counts - salesAM.cover_counts) / 4 ), 2)
AS lppaPM
FROM t_directory DIRECTORY
LEFT JOIN t_sales salesAM
ON salesAM.site_id = DIRECTORY.site_id
AND Dayofweek(salesAM.business_date) = Dayofweek(:date1)
AND salesAM.business_date < DATE_SUB(:date2, INTERVAL 14 DAY)
AND salesAM.business_date >= DATE_SUB(:date3, INTERVAL 42 DAY)
AND salesAM.meridiem = 'AM'
LEFT JOIN t_sales salespm
ON salesAM.site_id = salesPM.site_id
AND salesAM.business_date = salesPM.business_date
AND salespm.meridiem = 'PM'
WHERE DIRECTORY.active = 1
GROUP BY DIRECTORY.site_id
ORDER BY DIRECTORY.site_id ASC
LIMIT :totalLocations
注意:此解决方案假设
{Site_ID, business_Date, meridiem}
是唯一的答案 1 :(得分:1)
从连接条件中删除它:
AND sales.meridiem = 'AM'
然后你可以选择:
ROUND((SUM(case when sales.meridiem = 'AM'
then sales.daily_sales / sales.cover_counts end) / 4), 2) as AMSum
ROUND((SUM(case when sales.meridiem = 'PM'
then sales.daily_sales / sales.cover_counts end) / 4), 2) as PMSum
要从PM中减去AM,您可以:
SUM(case sales.meridiem
when 'PM' then sales.daily_sales / sales.cover_counts
when 'AM' then - sales.daily_sales / sales.cover_counts
end) as am_minus_pm