Поля MS Access Select Query на основе заданного диапазона дат - PullRequest
3 голосов
/ 25 июня 2011

Я взял на себя управление базой данных Access 2003 для медицинской клиники. К сожалению, человек, который создал БД, мало что знал о базах данных и бросил все в одну ОГРОМНУЮ таблицу. Итак, сейчас у меня есть таблица под названием «Все данные клиники» со следующими полями (и около 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 

Если [Дата начала ввода] = 1 мая 2010 года и [Дата окончания ввода] = 31 мая 2010 года

Я бы хотел, чтобы мой отчет содержал:

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]);

1 Ответ

1 голос
/ 25 июня 2011

Создайте запрос с именем 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», дайте мне знать, и я переключусь на лучший синтаксис в этом последнем запросе.

Вы также можете использовать метод UNION ALL SELECT, как было предложено в комментариях (я рекомендую использовать только UNION SELECT, потому что это заставляет движок выполнять больше работы по устранению дубликатов). Я не могу сразу увидеть что-то не так с вашим запросом, попробуйте каждый отдельный оператор SELECT, чтобы увидеть, если у вас есть проблемы.

Наконец, если ваша производительность с любым из этих методов слишком ужасна, то гибрид моего запроса Dual с вашим заданным запросом может помочь. Сделайте ваш запрос, как вы показали, с большим условием ИЛИ, но разделите две встречи на отдельные строки, как в запросе Dual выше. Вы захотите поставить дополнительное условие для подавления строк, которые не соответствуют правильному диапазону дат (потому что другие встречи сделали).

...