【问题标题】:How to prevent a value from being multiplied due to user inputs?如何防止由于用户输入而使值相乘?
【发布时间】:2017-04-02 04:55:51
【问题描述】:

我正在制作一个健身追踪网站。用户可以添加减肥目标并使用卡路里计算器来计算他们从某些运动中损失了多少卡路里。我已经实现了一个进度条,它显示了用户卡路里损失的进度。它还显示了两个值,一个是用户损失的卡路里总数,另一个是用户想要减少的目标卡路里数。

当我添加多个目标时,目标卡路里数值是正确的,但是,显示用户损失了多少卡路里的值似乎乘以该用户输入的目标数。

我正在努力研究如何防止这种情况发生,以及无论设定了多少目标,我都在努力显示用户损失了多少卡路里的价值。

例如,一个用户总共燃烧了 1310 卡路里。当用户添加第二个减肥目标时,此卡路里损失值翻倍至 2620,而无需用户输入任何减肥活动。

这是我用过的查询...

$sql = "SELECT 
      SUM(calories) as calories
      , CASE g.weightunit
          WHEN 'lbs' THEN 3500
          ELSE 7700
        END * weightlost  as target_calories 
    FROM (SELECT * FROM goal ORDER BY weightlost DESC) g 
        INNER JOIN tracklog t USING (userid)
    WHERE userid = ? ";
$stmt = $con->prepare($sql);
$stmt->bind_param('i', $_SESSION['userid']);
$stmt->execute();
$stmt->bind_result($calories, $target);
$res = $stmt->fetch();

【问题讨论】:

  • 编辑您的问题并提供示例数据和所需的结果。
  • 这对于您使用的查询类型是正常的。为什么你的桌子上有一个重量单位,你用它做什么?如果它根据不同的目标发生变化怎么办?
  • @SamiKuhmonen 需要重量单位,因为用户的目标显示在他们的帐户仪表板上,以便他们可以跟踪他们设置的内容。他们只能从磅或公斤中选择。
  • 似乎不清楚哪些变量与哪些数据相关。 (即,将失重作为 target_calories ......那么是从减重中计算总卡路里还是计算需要燃烧的目标卡路里量?)无论如何,我认为你的乘法一定是因为你正在检索多行和总是将燃烧的卡路里相加(乘以目标数量)。我建议为用户循环遍历每个目标并以这种方式添加单元,而不是从一个查询中获取它们。
  • @Vbudo 它的目标是需要燃烧的卡路里量。好的,谢谢,我试试看!

标签: php sql


【解决方案1】:

考虑将单元级别goal加入聚合级别tracklog,然后通过userid 加入。现在,您在单元级别加入两者,然后聚合,对多个匹配项进行多次求和。

SELECT t.SumCalories, 
       CASE WHEN g.weightunit = 'lbs' THEN 3500 ELSE 7700 END *
           g.weightlost As Target_calories 
FROM goal g
INNER JOIN 
  (SELECT sub.userid, SUM(sub.calories) as SumCalories      
   FROM tracklog sub
   GROUP BY sub.userid) t 
USING (userid)
WHERE g.userid = ?
ORDER BY g.weightlost DESC

顺便说一句,您可能正在使用 MySQL 并将 ONLY_FULL_GROUP_ON 设置为 off,因为引擎不会因为在 GROUP BY 子句中没有指定的非聚合列而出现语法错误。

所有其他 RDBMS 都会为此抛出错误。作为最佳实践,始终使用GROUP BY 在聚合查询中指定分组以避免不可靠的结果。

【讨论】:

    猜你喜欢
    • 2014-02-14
    • 1970-01-01
    • 2015-10-05
    • 1970-01-01
    • 2020-05-08
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2013-12-13
    相关资源
    最近更新 更多