2011-09-14 16 views
8

Utilizzo di MS Access. Mi dispiace che il titolo sia vago - semplicemente non so esattamente come descrivere il tipo di problema, so solo che ho bisogno di unire due tabelle o query per risolverlo.Access SQL join question

Ho una tabella OrgHistory che mostra che l'organizzazione di ogni persona (per ID) si è unito a una certa data (si può solo essere un membro di un'org alla volta):

Person | Org | JoinDate 
----------------------- 
123 | abc | 3/2/2011 
456 | abc | 4/23/1925 
123 | def | 5/12/2011 

ho anche un Activities tavolo:

Person | Activity | ActivityDate 
-------------------------------- 
123 | eat  | 3/23/2011 
123 | sleep | 6/25/2011 
456 | walk  | 7/20/1985 

voglio sapere, per ogni record Activities, quale organizzazione la persona era un membro del alla data dell'attività. Sto pensando che questo potrebbe comportare la conversione dei valori JoinDate in un insieme di intervalli e corrispondenti all'intervallo appropriato, ma sono un po 'confuso su come progettare la query in questo caso, come posso creare intervalli e abbinare un valore individuale per un intervallo?

Non credo che partition() funzioni perché non sto tentando di contenere più valori JoinDate in una quantità nota di bucket.

+0

Sono d'accordo il vostro 'tavolo OrgHistory' manca un attributo' LeaveDate': si dovrebbe aggiungere una nuova colonna 'LeaveDate' alla tua tabella di base, aggiungere una chiave sequenziata per garantire che i periodi non possano sovrapporsi per la stessa persona (suggerimento: hai bisogno di un vincolo' CHECK'), quindi scrub i dati ** una volta ** (@ Banjoe la query sembra promettente per questo). – onedaywhen

+0

+1 @onedaywhen - per l'utilizzo di una data di partenza anziché di un booleano attivo/innattivo. Molte persone non ritengono di dover tornare indietro storicamente per trovare l'appartenenza. – JeffO

risposta

5

Non posso promettere questo è il modo più efficiente, ma funziona in Access con i dati del test che hai fornito:

SELECT a.person, a.activity, 
     (
     SELECT TOP 1 org 
      FROM orghistory AS o 
     WHERE o.person = a.person 
       AND o.joindate <= a.activitydate 
     ORDER 
      BY o.joindate DESC 
     ) AS Org 
    FROM activities AS a; 
+0

grazie! buona idea di prendere la data di appartenenza più alta che è <= la data di attività, che ha molto senso. – sigil