回答

收藏

两个相关表之间的SQL SELECT数据不在特定日期范围内

技术问答 技术问答 248 人阅读 | 0 人回复 | 2023-09-13

我有2个多对多表,并有一个表将它们连接起来。
* [, w5 {; ?" N  q! K% W1 G. g4 b) L( n( e9 @
id
) r& r, }2 R7 Ename* y4 m( }+ q7 V5 t

$ E8 }: q& u  p& O4 ?/ O; k9 ~报告
) |8 F3 U* M2 P- N/ a+ Qid
% M+ O" b' [. T+ {! E3 y- ~, u* A1 xperformanceDate9 V. k9 Z5 \9 }+ ^4 L' ^  H
title; G$ @2 r9 h; a( p! U8 H

) M5 d6 q" |/ o: D报告_官员! B5 v- |# `  W  ]! E
Officer_id
+ i, @. _7 \+ N6 t" l6 `, qreport_id
; o) ~+ {$ ^, ~9 H" V( s* t* h
8 M$ [) B$ I2 W
我想选择在一定时间范围内从未与报告关联或尚未与报告关联的所有人员。. W9 S9 F4 ~3 `
到目前为止,我已经尝试了以下方法(以下内容对我不起作用!):
; d- z2 K  U) P8 P% |6 `  I3 YSELECT * 1 V3 B3 a. J3 i4 R5 }! @% ?% t
  FROM Officer   b( h+ ^& [2 @; J, R9 C
       LEFT JOIN report_officer
: |: o9 r8 N4 b            ON Officer.id = report_officer.officer_id
3 Q5 y1 j# Z/ |8 N' w1 N       LEFT JOIN Report 7 e  B# S  r  J# @: T6 F, w
            ON Report.id = report_officer.report_id0 L6 \4 {1 Z% j; _% i# p% d4 ]
WHERE (performanceDate IS NULL ' \: A- f) u9 @
        OR performanceDate  "2014-04-01 00:00:00"9 y$ q2 G* ?; T4 H0 w& `
        )
( V# `& @/ y" W, A; D. }7 p我的左联接查询仅在警官仅在特定时间范围内与报告相关联时才起作用,但在他们具有多个报告时失败。
$ D9 Y, i& F$ m% |6 ^$ k结果:
( K3 R% G+ a  t- {( l. W( q! C2 B+------------+-----------------+
: ~7 o: f; U/ q| officer_id | performanceDate |* I0 V1 p/ T5 l, L5 `: v* v
+------------+-----------------+
1 q2 \$ w" C7 K1 Y, [' R9 ]|        130 | NULL            | # good( L! u( [" j& f3 a
|        134 | 2014-03-02      | # bad - officer_id 134 has a performanceDate  ! O' W& `. a( k! H5 D) q& c
|        134 | 2014-03-09      | # on 2014-3-30, I do not want this in the results.  @8 f" ]1 z+ @: C/ X0 j
|        134 | 2014-03-16      | #
  g9 V+ U& h- d|        135 | 2014-03-02      | # good1 l: _; h% }7 w' l: r- ^9 _
+------------+-----------------+
, S# T" ?  w& o; X! R: e2 i( Osqlfiddle http3 J5 p$ I. Y9 U1 n( R
**://sqlfiddle.com/#!2/1bf72/3

3 K* |- [3 t8 V& u& n- o& U8 C1 Y0 C: @) Y
关于如何进行这项工作的任何想法?: ?' D% H) G7 j8 l/ V1 g
理想情况下,我想使此操作与ORM尽可能简单。我使用的是学说,并且不希望开始使用完全自定义的代码(因此,如果只能使用联接来完成,那将是很好的选择)。我虽然有一种不好的感觉,但我需要一个子查询。. B# ^& N: ]. Q! Y9 N1 a
                - v, Y0 \0 ]5 {! c- d
解决方案:
' I0 ?  P% Y4 D- p7 e2 B                3 E2 y6 B: A5 k% L6 ?7 O6 f
, B3 e* F. D0 v0 t) Z' |

- T% J0 [2 W& I9 R! ^                感谢大家在这个问题上的帮助。我的最终解决方案是使用GROUP BYandHAVING子句。+ ^9 |9 j+ \. v* `1 H+ I7 |8 {
@Iserni,我不需要SELECT在该时间范围内拥有0个报告的军官,我可以SELECT使用在时间范围之外的所有具有报告的军官或具有空报告的军官HAVING。
' t  R1 l/ v4 U5 k- b. }, G: O0 K这是我的最终代码:* M3 Y$ q1 ^. F) s+ R
SELECT Officer.id AS OfficerID, Officer.name, Report.id AS ReportID, max(performanceDate) as maxPerfDate FROM Officer& N4 c% W1 O- j0 i. n# a  c
LEFT JOIN report_officer ON Officer.id = report_officer.officer_id& T$ {& {$ o) L& v; @; `1 y
LEFT JOIN Report ON Report.id = report_officer.report_id6 \; U( n) L) A2 J% n7 m1 b9 N9 S. L
GROUP BY Officer.id HAVING maxPerfDate is null OR + D) x) y/ r/ N, f7 }! a
           maxPerfDate  "2014-04-01 00:00:00";
. ]& S9 `# r; w4 B' H这样做的好处是,我可以利用performanceDate来报告该官员上次提交报告的时间,或者报告该人员从未创建过报告。建议的所有其他解决方案都取消了检索+ J" K/ [% }, L8 u4 c, L) S. Q
人员上次创建报告的时间的 宝贵信息的能力。
分享到:
您需要登录后才可以回帖 登录 | 立即注册

本版积分规则