#sql #ms-access #join #vba
#sql #ms-access #Присоединиться #vba
Вопрос:
У меня есть запрос, выполняемый с помощью инструкции SQL. Я получаю правильные результаты, просто каждый результат повторяется в запросе 4 раза. Я не понимаю, почему я получаю 4 копии одного и того же результата.
Вот мой код для формы:
Dim strTables As String
Private Sub btnFollowUpQs_Click()
If (btnFollowUpQs.Value = True) Then
Set db = CurrentDb()
Set rs = db.OpenRecordset(btnFollowUpQs.Caption)
Dim fld As DAO.Field
For Each fld In rs.Fields
Me.lstVariablesFollowUpQs.AddItem (fld.Name)
Next
Set fld = Nothing
db.Close
strTables = strTables "," btnFollowUpQs.Caption
Else
lstVariablesFollowUpQs.RowSource = ""
strTables = Replace(strTables, "," btnFollowUpQs.Caption, "")
End If
Debug.Print strTables
End Sub
Private Sub btnBaseline_Click()
If (btnBaseline.Value = True) Then
Set db = CurrentDb()
Set rs = db.OpenRecordset(btnBaseline.Caption)
Dim fld As DAO.Field
For Each fld In rs.Fields
Me.lstVariablesBaseline.AddItem (fld.Name)
Next
Set fld = Nothing
db.Close
strTables = strTables "," btnBaseline.Caption
Else
lstVariablesBaseline.RowSource = ""
strTables = Replace(strTables, "," btnBaseline.Caption, "")
End If
Debug.Print strTables
End Sub
Private Sub btnTreatments_Click()
If (btnTreatments.Value = True) Then
Set db = CurrentDb()
Set rs = db.OpenRecordset(btnTreatments.Caption)
Dim fld As DAO.Field
For Each fld In rs.Fields
Me.lstVariablesTreatments.AddItem (fld.Name)
Next
Set fld = Nothing
db.Close
strTables = strTables "," btnTreatments.Caption
Else
lstVariablesTreatments.RowSource = ""
strTables = Replace(strTables, "," btnTreatments.Caption, "")
End If
Debug.Print strTables
End Sub
Private Sub btnQuestionnaires_Click()
If (btnQuestionnaires.Value = True) Then
Set db = CurrentDb()
Set rs = db.OpenRecordset(btnQuestionnaires.Caption)
Dim fld As DAO.Field
For Each fld In rs.Fields
Me.lstVariablesQuestionnaires.AddItem (fld.Name)
Next
Set fld = Nothing
db.Close
strTables = strTables "," btnQuestionnaires.Caption
Else
lstVariablesQuestionnaires.RowSource = ""
strTables = Replace(strTables, "," btnQuestionnaires.Caption, "")
End If
Debug.Print strTables
End Sub
Private Function createSQL(ByRef lstCtrl As Control, v() As String) As String
Dim count As Integer
count = 0
With lstCtrl
For Each varSelected In .ItemsSelected
If Not IsNull(varSelected) Then
Dim sel As String
sel = (lstCtrl.Column(0, varSelected))
strSQL = strSQL sel amp; " " amp; v(count) amp; " AND "
End If
count = count 1
Next
End With
createSQL = strSQL
End Function
Private Sub btnBuildQuery_Click()
If Left(strTables, 1) = "," Then
strTables = Right(strTables, Len(strTables) - 1)
End If
Dim tables() As String
tables = Split(strTables, ",")
Dim strSQL As Variant
strSQL = "SELECT * FROM " amp; strTables amp; " WHERE "
For Each Table In tables
Dim values() As String
Select Case Table
Case "tblPatientHistoryBaseline"
values = Split(txtSearchValueBaseline, ",")
strSQL = strSQL createSQL(lstVariablesBaseline, values)
Case "tblQuestionnaires"
values = Split(txtSearchValueQuestionnaires, ",")
strSQL = strSQL createSQL(lstVariablesQuestionnaires, values)
Case "tblTreatments"
values = Split(txtSearchValueTreatments, ",")
strSQL = strSQL createSQL(lstVariablesTreatments, values)
Case "tblFollowUpQs"
values = Split(txtSearchValueFollowUpQs, ",")
strSQL = strSQL createSQL(lstVariablesFollowUpQs, values)
End Select
Next
strSQL = Left(strSQL, Len(strSQL) - 5)
Debug.Print (strSQL)
Dim qdf As QueryDef
Set qdf = CurrentDb.CreateQueryDef("qry" amp; txtQueryName, strSQL)
DoCmd.OpenQuery qdf.Name
End Sub
Вот что возвращает запрос:
LastName FirstName ID Visit
Line Georgia 1234567 0
Line Georgia 1234567 0
Line Georgia 1234567 0
Line Georgia 1234567 0
Doe Jane 0123456 0
Doe Jane 0123456 0
Doe Jane 0123456 0
Doe Jane 0123456 0
Вот образец SQL, который я сгенерировал:
SELECT * FROM tblQuestionnaires, tblPatientHistoryBaseline WHERE Visit = 0 AND LastName Like '*e*'
Я предполагаю, что что-то не так с моим SQL, но я не могу понять, что.
Спасибо!
‘РЕДАКТИРОВАТЬ—————— Фамилия взята из tblPatientHistoryBaseline, Визит взят из tblQuestionnaires
Комментарии:
1. Как это
tblQuestionnaires
связано сtblPatientHistoryBaseline
? Правильное ОБЪЕДИНЕНИЕ, вероятно, исправит это.2. У них только один и тот же идентификационный номер (связанный). Как бы вы присоединились к ним?
Ответ №1:
Вы не указываете, как tblQuestionnaires
это связано с tblPatientHistoryBaseline
? Правильное JOIN
решение, вероятно, исправит это:
SELECT *
FROM tblQuestionnaires AS q
INNER JOIN tblPatientHistoryBaseline AS ph ON q.ID = ph.ID
WHERE Visit = 0
AND LastName Like '*e*'
Я не совсем уверен, из какой таблицы исходят поля в вашем выборе. Приведенный выше запрос может по-прежнему создавать дубликаты, если в любой таблице имеется несколько записей. Если это так, вы можете добавить оператор DISTINCT в запрос и указать нужное вам поле:
SELECT DISTINCT LastName, FirstName, ph.ID, Visit
FROM tblQuestionnaires AS q
INNER JOIN tblPatientHistoryBaseline AS ph ON q.ID = ph.ID
WHERE Visit = 0
AND LastName Like '*e*'
Редактировать:
SELECT DISTINCT ph.ID, q.fieldname, ph.fieldname, t.fieldname, f.fieldname
FROM tblQuestionnaires AS q
INNER JOIN tblPatientHistoryBaseline AS ph ON q.ID = ph.ID
INNER JOIN tblTreatments AS t ON t.ID = ph.ID
INNER JOIN tblFollowUp AS f ON f.ID = ph.ID
WHERE Visit = 0
AND LastName Like '*e*'
Комментарии:
1. В запросе может быть до 4 таблиц — все с соответствующими идентификационными номерами.
2. Как будет выглядеть синтаксис для всех 4 таблиц, находящихся в запросе?? (tblTreatments и tblFollowUp) Если вы не возражаете! Большое вам спасибо!!!
3. Что
ID
представляет поле? ЯвляетсяID
ли поле специфичным для пациента?4. Смотрите мое редактирование. Вам нужно будет указать точные поля, которые вам нужны в запросе.
5. Потрясающе!! Спасибо вам большое, задержитесь !! 🙂
Ответ №2:
В этом случае их объединение обязательно. Например, ваш код должен быть написан так, чтобы указывать только совпадающие строки из таблицы вопросника. Это,
SELECT *
FROM tblQuestionnaires, tblPatientHistoryBaseline
WHERE Visit = 0
AND LastName Like '*e*'
AND tblQuestionnaires.id = tblPatientHistoryBaseline.id
Но я бы также рекомендовал использовать более новый (в любом случае, прошедшее десятилетие) синтаксис:
SELECT *
FROM tblQuestionnaires q
INNER JOIN tblPatientHistoryBaseline b
ON q.id = b.id
WHERE q.Visit = 0
AND b.LastName Like '*e*'
Я не уверен, откуда взялся ваш столбец VISIT или ваш столбец LASTNAME, но если вы добавите к ним соответствующий псевдоним, все будет хорошо.