【问题标题】:How to implement INTERSECT in MySQL如何在 MySQL 中实现 INTERSECT
【发布时间】:2021-05-02 04:03:27
【问题描述】:

这是我当前的查询。我今天发现了 INTERSECT,但是 MySQL 不支持它。谁能给我一些关于如何改进这个查询的建议?它为我提供了我正在寻找的结果,但速度相当缓慢。

如果有帮助,我正在与运动队合作,并过滤统计数据。我过滤主队,然后是客队。我使用了 count(id) 方法,因为我只想返回在 both 查询中找到的灯具 ID,所以我认为 INTERSECT 会很完美。

    select id, count(id) as count from (
    
    select f.id, f.etc, etc
    from fixtures f
    inner join team_stats t on f.id = t.fixture_id and f.league_id = t.league_id and f.home_id = t.team_id
    where f.status in ('FT', 'AET', 'PEN', 'FT_PEN') and
    unix < 1619927451 and
    played_overall between '11' and '60' and
    scored_1h_home_avg between '0.7' and '6' and 
    o05_1h_goals_overall_per between '76' and '100' and 
    first_goal_total_avg between '0' and '35' and 
    scored_o05_1h_home_per >= 69
    
    UNION ALL
    
    select f.id, f.etc, etc
    from fixtures f
    inner join team_stats t on f.id = t.fixture_id and f.league_id = t.league_id and f.away_id = t.team_id
    where f.status in ('FT', 'AET', 'PEN', 'FT_PEN') and
    unix < 1619927451 and
    played_overall between '11' and '60' and
    conceded_1h_away_avg between '0.7' and '6' and 
    first_goal_total_avg between '0' and '35' and 
    o05_1h_goals_away_per between '77' and '100'
)    
    x group by id HAVING count(id) > 1

【问题讨论】:

标签: mysql sql mysql-8.0


【解决方案1】:

你可以使用exists得到你想要的:

select f.id
from fixtures f
inner join team_stats t on f.id = t.fixture_id and f.league_id = t.league_id and f.home_id = t.team_id
where f.status in ('FT', 'AET', 'PEN', 'FT_PEN') and
unix < 1619927451 and
played_overall between '11' and '60' and scored_1h_home_avg between '0.7' and '6' and o05_1h_goals_overall_per between '76' and '100' and first_goal_total_avg between '0' and '35' and scored_o05_1h_home_per >= 69

and exists(

select 1
from fixtures f2
inner join team_stats t on f2.id = t.fixture_id and f2.league_id = t.league_id and f2.away_id = t.team_id
where f2.status in ('FT', 'AET', 'PEN', 'FT_PEN') and
unix < 1619927451 and
played_overall between '11' and '60' and
conceded_1h_away_avg between '0.7' and '6' and first_goal_total_avg between '0' and '35' and o05_1h_goals_away_per between '77' and '100'
and f1.id=f2.id)

另一种变体是在没有union all 的情况下组合两个查询。如果您的查询产生正确的答案,那么这也应该这样做。

select id, count(id) as i_count 
from fixtures f
inner join team_stats t on f.id = t.fixture_id and f.league_id = t.league_id 
where f.status in ('FT', 'AET', 'PEN', 'FT_PEN') and
unix < 1619927451 and
played_overall between '11' and '60'    

and ((f.home_id = t.team_id and and scored_1h_home_avg between '0.7' and '6'  o05_1h_goals_overall_per between '76' and '100' and first_goal_total_avg between '0' and '35' and scored_o05_1h_home_per >= 69)
or (f.away_id = t.team_id and conceded_1h_away_avg between '0.7' and '6' and first_goal_total_avg between '0' and '35' and o05_1h_goals_away_per between '77' and '100'))

group by id HAVING count(id) > 1

【讨论】:

  • 谢谢你的这些。我发现使用 PHP 查找重复 ID 的 UNION ALL 实际上要快得多。这很常见吗?我认为直接使用 SQL 即可。
【解决方案2】:

如果我的理解正确,两个查询中的相同点:

select f.id, f.etc, etc
from fixtures f join
     team_stats t
     on f.id = t.fixture_id and f.league_id = t.league_id and f.away_id = t.team_id
where f.status in ('FT', 'AET', 'PEN', 'FT_PEN') and
      unix < 1619927451 and
      played_overall between '11' and '60' and
      conceded_1h_away_avg between '0.7' and '6' and 
      first_goal_total_avg between '0' and '35'

那么你想要这两个条件:

scored_o05_1h_home_per >= 69
o05_1h_goals_away_per between '77' and '100'

如果是这样,聚合可能是最简单的解决方案:

select f.id, f.etc, etc
from fixtures f join
     team_stats t
     on f.id = t.fixture_id and f.league_id = t.league_id and f.away_id = t.team_id
where f.status in ('FT', 'AET', 'PEN', 'FT_PEN') and
      unix < 1619927451 and
      played_overall between '11' and '60' and
      conceded_1h_away_avg between '0.7' and '6' and 
      first_goal_total_avg between '0' and '35'
group by f.id
having sum(scored_o05_1h_home_per >= 69) > 0 and
       sum(o05_1h_goals_away_per between '77' and '100')

我还注意到您在看起来像数字的地方使用单引号。如果这些确实是数字,则删除单引号。不要混合类型。如果值存储为字符串,则比较是字符串,而不是数字,并且可能不会达到您的预期。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2010-09-25
    • 2021-07-11
    • 1970-01-01
    • 1970-01-01
    • 2020-11-15
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多