【问题标题】:Combine SUM and CAST - not working?结合 SUM 和 CAST - 不起作用?
【发布时间】:2013-08-11 20:23:45
【问题描述】:

PostgreSQL Unicode 9.01 不喜欢:

SELECT table1.fielda,
SUM (CAST (table2.fielda AS INT)) AS header.specific
FROM *etc*

SUM-CAST 有什么问题?

错误信息:

列表达式不正确:'SUM (CAST (specifics_nfl_3pl_work_order_item.delivery_quantity AS INT))

查询:

SELECT specifics_nfl_3pl_work_order.work_order_number,
specifics_nfl_3pl_work_order.goods_issue_date,
specifics_nfl_3pl_work_order.order_status_id,
SUM (CAST (specifics_nfl_3pl_work_order_item.delivery_quantity AS INT)) AS units
FROM public.specifics_nfl_3pl_work_order specifics_nfl_3pl_work_order,
public.specifics_nfl_3pl_work_order_item specifics_nfl_3pl_work_order_item,
public.specifics_nfl_order_status specifics_nfl_order_status
WHERE specifics_nfl_3pl_work_order.order_status_id In (3,17,14) 
AND specifics_nfl_3pl_work_order_item.specifics_nfl_work_order_id=
specifics_nfl_3pl_work_order.id 
AND ((specifics_nfl_3pl_work_order.sold_to_id<>'0000000000') 
AND (specifics_nfl_3pl_work_order.goods_issue_date>={d '2013-08-01'}))

如果你能提供帮助,那就太好了。

【问题讨论】:

  • header.specific 是什么?
  • 缺少:表定义、Postgres 版本、错误消息、查询说明。
  • 感谢 Erwin:我现在已经发布了实际代码。感谢您的回复。
  • 顺便说一句:对我来说它看起来像 ORM 输出。
  • PostgreSQL Unicode 9.01ODBC 驱动程序 版本;请select version() 获取实际的 PostgreSQL 服务器版本。也就是说,如果它也是 9.0.1,立即升级:该版本有一个已知的安全漏洞,并且您还缺少 12 个点的修复版本。说真的,升级到 9.0.13.

标签: postgresql casting sum


【解决方案1】:

如果我是你,那么我会执行以下步骤:

  • 为您的表格提供短别名
  • 格式化查询
  • 使用正确的 ANSI 连接:
  • 删除函数名和 (

select
    o.work_order_number,
    o.goods_issue_date,
    o.order_status_id,
    sum(cast(oi.delivery_quantity as int)) as units
from public.specifics_nfl_3pl_work_order as o
    inner join public.specifics_nfl_3pl_work_order_item as oi on
       oi.specifics_nfl_work_order_id = o.id
    -- inner join public.specifics_nfl_order_status os -- seems redundant
where
    o.order_status_id In (3,17,14) and
    o.sold_to_id <> '0000000000' and
    o.goods_issue_date >= {d '2013-08-01'}

其实我觉得你这里需要分组:

select
    o.work_order_number,
    o.goods_issue_date,
    o.order_status_id,
    sum(cast(oi.delivery_quantity as int)) as units
from public.specifics_nfl_3pl_work_order as o
    inner join public.specifics_nfl_3pl_work_order_item as oi on
       oi.specifics_nfl_work_order_id = o.id
where
    o.order_status_id In (3,17,14) and
    o.sold_to_id <> '0000000000' and
    o.goods_issue_date >= {d '2013-08-01'}
group by
    o.work_order_number,
    o.goods_issue_date,
    o.order_status_id

如果它仍然不起作用 - 尝试评论 sum 并查看它是否有效?

【讨论】:

  • +1 以正确的格式重写查询。很好地抓住了失踪的GROUP BY。这可能是错误的直接原因。还有更多问题...
  • 感谢 @ErwinBrandstetter,可读性是我的首要任务之一,这就是我如此喜欢 SQL 和 Python 的原因 :)
【解决方案2】:

但是你有一个 table2 还是只有 table1?

尝试:
选择 table1.fielda,
SUM (CAST (table1.fielda AS INT)) 作为“header.specific”
FROM

【讨论】:

    【解决方案3】:

    除了@Roman already cleared up什么之外,这里还有更多问题:

    SELECT o.work_order_number
          ,o.goods_issue_date
          ,o.order_status_id
          ,SUM(CAST(oi.delivery_quantity AS INT)) AS units -- suspicious
    FROM   public.specifics_nfl_3pl_work_order o,
    JOIN   public.specifics_nfl_3pl_work_order_item oi
                                         ON oi.specifics_nfl_work_order_id = o.id 
    CROSS  JOIN public.specifics_nfl_order_status os -- probably wrong
    WHERE  o.order_status_id IN (3,17,14)
    AND    o.sold_to_id <> '0000000000'              -- suspicious
    AND    o.goods_issue_date> = {d '2013-08-01'}    -- nonsense
    GROUP  BY 1, 2, 3
    
    • o.goods_issue_date&gt; = {d '2013-08-01'}句法废话。也许你的意思是:
      o.goods_issue_date&gt; = '2013-08-01'

    • 您的 specifics_nfl_order_status 列表中有表 specifics_nfl_order_status,但没有任何表达式将其连接到其余部分。这实际上会导致 CROSS JOIN,这会导致笛卡尔积,并且几乎可以肯定是以非常昂贵的方式出错:每一行都与其余的每一行相结合:
      CROSS JOIN public.specifics_nfl_order_status os
      删除表(因为您不使用它)或添加WHEREON 子句将其连接到其余部分。请注意,它不仅仅是多余的,它会对结果产生巨大影响。

    • 这个WHERE 子句很可疑:
      AND o.sold_to_id &lt;&gt; '0000000000'
      似乎您将数字存储为字符串或以其他方式混淆两者。 此外,CAST (oi.delivery_quantity AS INT) 应该不需要开始。该列应该是数据类型integer 或其他适当的数字类型。请务必使用正确的data types

    • search_path 的默认设置包括public,您可能不需要模式限定表。代替public.specifics_nfl_3pl_work_order,使用:
      specifics_nfl_3pl_work_order

    • GROUP BY 1, 2, 3 正在使用位置参数,只是以下的符号快捷方式:
      GROUP BY o.work_order_number, o.goods_issue_date, o.order_status_id
      Details in the manual.

    • 根据 cmets,您使用 MS Query 创建查询。这不是最好的想法。生成您提供给我们的那种劣质代码。在使用 PostgreSQL 时,您可能希望摆脱它。

    【讨论】:

    • 哇!谢谢大家“教育”我。现在我回到电脑前,我将浏览所有这些内容。你慷慨地帮助了一个新手。我现在打算减少对 MS Query 的依赖,并自己学习如何做。感谢您不认为这篇文章是在浪费您的时间。我会仔细研究的。
    • 顺便说一句,所有代码,包括 o.goods_issue_date&gt; = {d '2013-08-01'} 废话,都是由 MS Query 生成的,除了 SUM(CAST) - 因为 MS Query 不这样做。但是当我添加该行时,查询停止工作。
    • ... 是的,确实数据库经常将数字存储为文本(我无法控制)——这就是我要解决的问题——无法添加文本数字。但在sold_to_id 的情况下,它是帐号 - 所以文本是可以的。
    • 成功了(两天后)。现在我要自己尝试一个 - 没有 MS Query - 用于我报告的另一个元素。
    • @user2670949:恭喜!如果你需要它,这里有一些建议how to change the data type for table columns
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2019-06-27
    • 1970-01-01
    • 2018-11-18
    • 1970-01-01
    • 1970-01-01
    • 2018-06-05
    相关资源
    最近更新 更多