【问题标题】:mysql to postgresql query conversionmysql 到 postgresql 查询转换
【发布时间】:2014-06-15 17:28:01
【问题描述】:

我在 MySql 中有这个查询,我想知道,在 postgresql 中可以吗? 我想知道它是否应该是我需要改变的东西:)

我最关心的是不应该按功能分组 可以在后期执行。

我愿意考虑迁移到 postgres 的可能性,我想知道 如果我使用的当前查询可以完成工作!

提前感谢您的帮助, vinc

    SELECT
     #GROUP BY
   dc.region as Region
 ,(DATEDIFF(CURRENT_TIMESTAMP,cc.activated_at)) AS 'Listing Age'
 ,cc.sku AS SKU
 ,CONCAT(dc.venture_url,cc.urlkey_details) as URL
 , cc.status 'Listing Status'
# REGION
, region.name_en Region
 ,(CASE WHEN is_agent=1 THEN supplier.name ELSE concat(supplier.name, ' (private)') END) AS Agent
 # Car type
 , ct.label_en as 'Vehicle Type'
,(Case 
    WHEN cc.fk_catalog_attribute_option_global_condition=1 THEN 'New'
    ELSE 'Other' END) AS 'Condition'
, ca.name_en as Brand

FROM 
 catalog_product_visible cpv

join catalog_config cc on cc.country_id = cpv.country_id and cc.id_catalog_config = cpv.fk_catalog_config

    left join
    dwh_country dc on dc.country_id = cc.country_id

  JOIN supplier AS supplier ON supplier.country_id = cc.country_id AND supplier.id_supplier = cc.product_owner

 LEFT JOIN
 (SELECT 
 profile_isocode,
 date_format(report_date,'%x-%v') as date,
 sum(coalesce((case when event_action IN ('Email Lead Success', 'Contact Submit Sucess') OR event_category = 'Email Lead Success' then total_events end),0)) as EmailLead,
 sum(coalesce((case when event_action IN ('Phone Lead Success', 'Show number Top', 'Show number Bottom', 'Show number Agency') OR event_category IN ('Phone Lead Success') then total_events end),0)) as PhoneLead,
 sum(coalesce((case when event_category IN ('SMS Lead Success') then total_events end),0)) as SMSLead
 FROM dwh_eventlistings c
 WHERE (event_action in ('Contact Submit Sucess')
 GROUP BY 1,2,3,4,5,6)  AS leads ON leads.profile_isocode = pv.profile_isocode AND leads.listing_id = pv.listing_id AND leads.date = date_format(pv.report_date,'%x-%v')

 LEFT JOIN catalog_simple AS cs ON cs.fk_catalog_config = cc.id_catalog_config AND cs.country_id = cc.country_id

WHERE supplier.name not like '%test%' and URL not like '%test%'

GROUP BY 
country, sku, report_week, source, medium, campaign

【问题讨论】:

标签: mysql sql postgresql group-by


【解决方案1】:

是的,您正在使用 MySQL 的某些功能在 PostgreSQL 上不起作用。

  • # 是非标准注释字符supported only by MySQL。在 PostgreSQL 中,使用 --/* */

  • 在给定别名 Region 的情况下,您的选择列表中有两个不同的列,然后您尝试 GROUP BY 该列,我认为这会引发错误或导致未定义的行为。

  • 在您的子查询中,您使用GROUP BY 1,2,3,4,5,6,即使只有五列。

  • 在您的子查询中,GROUP BY 列是聚合表达式(如 SUM())是没有意义的。

  • 在您的子查询中,您不要关闭 WHERE 子句中的括号,因此该查询也无法在 MySQL 中运行。

  • 您的查询违反了the single-value rule。您在选择列表中使用了几个列,这些列未在 GROUP BY 子句中列出,也未在聚合函数中列出。事实上,您在GROUP BY 子句中列出您拥有的列是令人费解的。

    MySQL 对GROUP BY 语义更加宽容。请参阅我对MySQL GROUP BY behavior 的回答以获得解释。

我认为您对 GROUP BY 的作用有一些基本的误解。要了解更多信息,我建议您阅读这篇由 SQL 专家和 author Roland Bouman 撰写的关于 Debunking GROUP BY myths 的优秀博文。

【讨论】:

  • PostgreSQL 确实支持 GROUP BY 列的序号。
  • @klin,谢谢你,我没有方便的 PG 实例来测试它。据我所知,文档提到了ORDER BY 的列序号,但没有提到GROUP BY 的列序号。我将编辑该声明。但是,在 OP 的查询中按 SUM() 分组是没有意义的。
  • 简单的规则是GROUP BY 子句中的所有列构成结果集的“逻辑”主键。结果集中的所有其他字段在功能上都依赖于它。
  • 值得注意的是,为了原始海报的利益,这些都不太可能成为阻止使用 PostgreSQL 的阻碍。必须先修复损坏的查询。
  • @wildplasser,谢谢,这是一种很好的思考方式。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 2021-08-01
  • 2019-06-22
  • 2021-10-30
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多