Access - FULL OUTER JOIN без использования UNION, поэтому набор записей можно обновлять - PullRequest
0 голосов
/ 27 апреля 2011

Если я использую UNION для набора записей подчиненной формы в Access, запрещается делать этот набор записей обновляемым.

Проблема в том, что мне нужно иметь возможность обновить набор записей.

У меня есть дватаблицы - один из них - список сотрудников (сотрудников).Другой - это запись количества билетов, которые каждый сотрудник закрыл за день.В результате эта таблица (INCTech) использует EmployeeID и Date в качестве объединенного первичного ключа, поскольку каждый сотрудник может иметь только одну запись для данной даты.

Я не могу использовать LEFT OUTER JOIN для полученияполный список сотрудников, потому что он исключит любого сотрудника, у которого есть запись в INCTech за дату, отличную от указанной даты.Это не работает:

SELECT INCTech.EmployeeID, INCTech.Assigned, INCTech.Closed, INCTech.Submitted,
INCTech.StillOpen, INCTech.TheDate, Employees.FirstName, Employees.LastName
FROM Employees LEFT JOIN INCTech ON Employees.EmployeeID = INCTech.EmployeeID
WHERE Employees.GroupID = 8 AND (INCTech.TheDate = #4/15/2011# OR 
INCTech.TheDate IS NULL)

Потому что, если у сотрудника есть запись для даты, отличной от 15.04.2011, он не соответствует ни одному из двух критериев даты - Дата не равна NULLбольше, но это также не указанная дата.

Мой запрос, который работает:

SELECT Employees.EmployeeID, Employees.FirstName, Employees.LastName,
Employees.FirstName & " " & Employees.LastName AS FullName, INCTech.TheDate,
INCTech.Assigned, INCTech.Closed, INCTech.Submitted, INCTech.StillOpen,
Employees.GroupID
FROM Employees
LEFT OUTER JOIN INCTech ON
Employees.EmployeeID=INCTech.EmployeeID 
WHERE (INCTech.TheDate)=Calendar.Value AND Employees.GroupID = ddlGroup.Value
UNION
SELECT Employees.EmployeeID, Employees.FirstName, Employees.LastName, 
Employees.FirstName & " " & Employees.LastName AS FullName, NULL AS TheDate, 
NULL AS Assigned, NULL AS Closed, NULL As Submitted, NULL As StillOpen, 
Employees.GroupID 
FROM Employees 
LEFT OUTER JOIN INCTech ON Employees.EmployeeID=INCTech.EmployeeID 
WHERE Employees.EmployeeID NOT IN 
(SELECT INCTech.EmployeeID FROM INCTech WHERE INCTech.TheDate=Calendar.Value) 
AND Employees.GroupID = ddlGroup.Value

Но так как я должен использовать UNION для этого, результирующий набор записей читается кактолько.Это не сработает - мне нужно иметь возможность изменять или добавлять данные для ежедневной записи каждого сотрудника.

Помощь!

Ответы [ 3 ]

1 голос
/ 28 апреля 2011

Создание формы с этим запросом в качестве источника записи:

SELECT e.EmployeeID, Date() AS TheDate, e.LastName, e.FirstName
FROM Employees AS e
ORDER BY e.LastName, e.FirstName;

Добавьте подчиненную форму, которая использует INCTech в качестве источника записи.

Использовать EmployeeID; TheDate в качестве дочерних полей ссылки и основных полей ссылок.

Выберите «Одна форма» в качестве представления по умолчанию для подчиненной формы. Set Navigation Buttons = No. Установите для свойства Cycle значение Текущая запись.

Затем для любой записи Сотрудника в главной форме ваша подчиненная форма отобразит соответствующую строку INCTech (тот же сотрудник, та же дата), если есть строка, или позволит добавить строку, если ее нет.

Но вы, вероятно, захотите отредактировать данные INCTech для дат, отличных от сегодняшних. В этом случае вы можете добавить несвязанный элемент управления текстового поля в заголовок основной формы, скажем, txtWhichDate, и позволить пользователю ввести значение даты. В этом случае вы можете настроить запрос главной формы так, чтобы он ссылался на значение текстового поля вместо Date ().

SELECT e.EmployeeID, Forms!YourFormName!txtWhichDate AS TheDate, e.LastName, e.FirstName
FROM Employees AS e
ORDER BY e.LastName, e.FirstName;

Или вы можете добавить код в событие после обновления txtWhichDate, чтобы обновить источник записи, чтобы он соответствовал.

0 голосов
/ 28 апреля 2011

Вы не сможете включить несколько таблиц в набор записей и сделать его обновляемым.Ваша форма должна редактировать таблицу записей сотрудников и ссылаться на таблицу INCTech как подчиненную форму.

В противном случае вы можете создать запрос для отображения всех ваших данных с объединениями и несколькими таблицами, но вам придется кодировать операторы обновления для обеих таблиц, чтобы они выполнялись при изменении строки.Вам необходимо отфильтровать строку для обновления на основе EmployeeID и EmployeeID и TheDate или таблицы INCTech.Выполните поиск для обновления нескольких таблиц в Access.

Это решит ваш главный вопрос:

Select E.* 
  , I.TheDate
from Employees as E
Left Outer Join (
  Select * 
  from INCTech 
  Where TheDate = #4/15/2001#) as I
on E.EmployeeID = I.EmployeeID
0 голосов
/ 28 апреля 2011

Я думаю, проблема в том, что ваше условие WHERE ограничивает результаты из таблицы INCTech теми записями, которые соответствуют Calendar.Value.

То, что вы можете попробовать сделать, - это создать отдельный запрос для извлечениязаписей из INCTech и примените предложение WHERE INCTech.TheDate = Calendar.Value в запросе.

В своем основном запросе, используйте ссылку на этот запрос вместо таблицы INCTech, используя LEFT JOIN.

. Это должно вернутьзаписи сотрудника и отображают соответствующие данные для каждой записи сотрудника, в которой есть совпадение в запросе на основе таблицы INCTech.

...