MS Access 根据给定的日期范围选择查询字段
Posted
技术标签:
【中文标题】MS Access 根据给定的日期范围选择查询字段【英文标题】:MS Access Select Query fields based on date range given 【发布时间】:2011-06-24 21:40:44 【问题描述】:我已经接管了一家诊所的 Access 2003 数据库的管理工作。不幸的是,创建数据库的人对数据库知之甚少,并将所有内容都放在一个巨大的表中。所以现在我有一个名为 All Clinic Data 的表,其中包含以下字段(以及大约 40 个其他字段):PatientID, First Name, Last Name, Appt Date, OB at Appt, Billing Item #1, Second Appt Date, Reason for Second Appt, OB at Second Appt, Billing Item #2.
我知道这不是安排数据的最佳方式,并且计划在未来对数据库进行全面检修。但是,现在我需要创建仅包含特定日期范围内发生的约会信息的报告。
这是我目前用来填充我的报告的 SQL 查询,但如果其中一个在给定的日期范围内,它会从表中捕获患者的所有约会。
SELECT
Format([Input start date],"mm/dd/yy") & " through " & Format([Input end date],"mm/dd/yy") AS Expr1,
[All Clinic Data].[PatientID], [All Clinic Data].[Last Name],
[All Clinic Data].[First Name], [All Clinic Data].[Appt Date],
[All Clinic Data].[OB at Appt], [All Clinic Data].[Billing Item #1],
[All Clinic Data].[Second Appt Date], [All Clinic Data].[Reason for Second Appt],
[All Clinic Data].[OB at Second Appt], [All Clinic Data].[Billing Item #2]
FROM [All Clinic Data]
WHERE (
(([All Clinic Data].[Appt Date])>[Input start date] And
([All Clinic Data].[Appt Date])<[Input end date])
)
OR
(
(([All Clinic Data].[Second Appt Date])>[Input start date] And
([All Clinic Data].[Second Appt Date])<[Input end date])
)
ORDER BY [All Clinic Data].[Last Name];
注意输入开始日期和输入结束日期是查询运行时输入的参数。 我曾尝试使用 IIF 删除多余的数据,但我不知道如何构建报表,以便它仅显示给定日期范围内的预约日期和相关数据(OB 和计费项目)。
例子:
1, Sally, Jones, 1/04/2010, Dr.A, 2/05/2011, Dr. B, Flu
2, Jennifer, Baker, 7/05/2010, Dr.X, 15/05/2011, Dr. B, Checkup
3, Joe, Smith, 20/06/2010, Dr.S,
4, Tina, Turner, 17/05/2010, Dr.X, 15/06/2011, Dr. B, Checkup
如果 [输入开始日期] = 2010 年 5 月 1 日且 [输入结束日期] = 2010 年 5 月 31 日
我希望我的报告包含:
Sally, Jones,
1. 2/05/2011, Dr. B, Flu
Jennifer, Baker,
1. 7/05/2010, Dr.X
2. 15/05/2011, Dr.B, Checkup
Tina, Turner,
1. 17/05/2010, Dr.X
我希望这是足够的信息。感谢您的帮助。
更新 1 这是我尝试下面迈克建议的第一步。我使用 phn 作为稍后将获取的患者信息的标识符。我遇到了编译错误,而且我不够老练,无法知道自己做错了什么。有什么想法吗?
SELECT
Format([Input start date],"mm/dd/yy") & " through " & Format([Input end date],"mm/dd/yy") AS Expr1,
[All Clinic Data].PHN AS Phn, [All Clinic Data].[Appt Date] AS Date,
[All Clinic Data].[OB at Appt] AS OBName,
[All Clinic Data].[Billing Item #1] AS Billing
FROM [All Clinic Data]
WHERE ([All Clinic Data].[Appt Date]>[Input start date] And [All Clinic Data].[Appt Date]<[Input end date])
UNION
SELECT
Format([Input start date],"mm/dd/yy") & " through " & Format([Input end date],"mm/dd/yy") AS Expr1,
[All Clinic Data].PHN AS Phn, [All Clinic Data].[Second Appt Date] AS Date,
[All Clinic Data].[OB at Second App] AS OBName,
[All Clinic Data].[Billing Item #2] AS Billing FROM [All Clinic Data]
WHERE ([All Clinic Data].[Second Appt Date]>[Input start date] And [All Clinic Data].[Second Appt Date]<[Input end date]);
【问题讨论】:
您要求在 MM/DD/YYYY 和 MM/DD/YYYY 之间进行约会,但数据似乎存储为 DD/MM/YYYY。你能确认一下吗? 是的,我的数据存储为 DD/MM/YYYY。在我的报告中,我将其格式化为 MM/DD/YY。我在示例中长期输入了我的输入参数,据我所知,Access 为我将其转换为 DD/MM/YYYY,以便它可以进行比较。 我现在没有时间浏览它并测试代码,但我认为这是我要研究的方法: 1. 创建一个查询以选择您想要的每个人的第一个约会信息. 2. 创建查询以选择所有第二个约会信息。 3.将这两者结合起来并从中选择。将有分组问题需要解决。 HTH。 【参考方案1】:创建一个名为PatientAppointment
的查询:
SELECT
D.PatientID,
D.[Appt Date] AS ApptDate,
D.[OB at Appt] AS OBName
D.[Billing Item #1] AS Billing
UNION ALL SELECT
D.PatientID,
D.[Second Appt Date],
D.[OB at Second Appt],
D.[Billing Item #2];
请注意,无法在设计器中编辑此查询。您只能在 SQL 视图中使用它。然后,将此查询用作对此数据的所有查询的来源:
SELECT *
FROM
PatientAppointment PA
WHERE
PA.ApptDate >= [Input start date]
AND PA.ApptDate < [Input end date];
我不知道性能如何,但您可以尝试并告诉我们。基本上,将其视为您的约会表,甚至不处理主表中的这些列。这将是您慢慢开始更改应用程序的一种方式,因为最终您可以将其设为实际表并迁移数据。
这是一个可能的替代解决方案,可以,让我强调可以更好。或者更糟:
创建一个表,其中包含一列和一行。表或行的名称无关紧要,但将数据类型设为数字 Long。我假设您将此表命名为Dual
。然后进行同样的PatientAppointment
查询:
SELECT
D.PatientID,
Iif(A.ApptNum = 1, D.[Appt Date], D.[Second Appt Date]) ApptDate,
Iif(A.ApptNum = 1, D.[OB at Appt], D.[OB at Second Appt]) OBName,
Iif(A.ApptNum = 1, D.[Billing Item #1], D.[Billing Item #2]) Billing
FROM
[All Clinic Data] D
INNER JOIN [
SELECT 1 AS ApptNum FROM Dual
UNION ALL SELECT 2 FROM Dual
]. A ON 1 = 1
如果您在数据库中打开了“SQL 92 语法”,请告诉我,我将在最终查询中切换到更好的语法。
您也可以按照 cmets 中的建议执行 UNION ALL SELECT
方法(我建议不要只使用 UNION SELECT
,因为这会使引擎做更多的工作来消除重复项)。我无法立即发现您的查询有任何问题,请单独尝试每个单独的 SELECT 语句,看看是否有问题。
最后,如果您使用这些方法中的任何一种方法的性能太差,那么将我的Dual
查询与您的给定查询混合起来就可以解决问题。使用大 OR 条件执行查询,但将两个约会拆分为单独的行,如上面的 Dual
查询中所示。您需要添加一个附加条件来抑制与正确日期范围不匹配的行(因为其他约会已经匹配)。
【讨论】:
以上是关于MS Access 根据给定的日期范围选择查询字段的主要内容,如果未能解决你的问题,请参考以下文章