Примечание
Для доступа к этой странице требуется авторизация. Вы можете попробовать войти или изменить каталоги.
Для доступа к этой странице требуется авторизация. Вы можете попробовать изменить каталоги.
Visual Basic предоставляет Join
и Group Join
операторы запросов для объединения содержимого нескольких коллекций по общим значениям коллекций. Эти значения называются ключевыми значениями. Разработчики, знакомые с понятиями реляционных баз данных, будут распознавать оператор Join
как INNER JOIN и оператор Group Join
как, фактически, LEFT OUTER JOIN.
Примеры в данной теме демонстрируют несколько способов объединения данных с помощью клауз Join
и Group Join
запроса.
Создание проекта и добавление примеров данных
Создание проекта, содержащего примеры данных и типов
Чтобы запустить примеры в этом разделе, откройте Visual Studio и добавьте новый проект консольного приложения Visual Basic. Дважды щелкните файл Module1.vb, созданный Visual Basic.
В примерах в этом разделе используются типы
Person
и данныеPet
из следующего примера кода. Скопируйте этот код в модуль по умолчаниюModule1
, созданный Visual Basic.Private _people As List(Of Person) Private _pets As List(Of Pet) Function GetPeople() As List(Of Person) If _people Is Nothing Then CreateLists() Return _people End Function Function GetPets(ByVal people As List(Of Person)) As List(Of Pet) If _pets Is Nothing Then CreateLists() Return _pets End Function Private Sub CreateLists() Dim pers As Person _people = New List(Of Person) _pets = New List(Of Pet) pers = New Person With {.FirstName = "Magnus", .LastName = "Hedlund"} _people.Add(pers) _pets.Add(New Pet With {.Name = "Daisy", .Owner = pers}) pers = New Person With {.FirstName = "Terry", .LastName = "Adams"} _people.Add(pers) _pets.Add(New Pet With {.Name = "Barley", .Owner = pers}) _pets.Add(New Pet With {.Name = "Boots", .Owner = pers}) _pets.Add(New Pet With {.Name = "Blue Moon", .Owner = pers}) pers = New Person With {.FirstName = "Charlotte", .LastName = "Weiss"} _people.Add(pers) _pets.Add(New Pet With {.Name = "Whiskers", .Owner = pers}) ' Add a person with no pets for the sake of Join examples. _people.Add(New Person With {.FirstName = "Arlene", .LastName = "Huff"}) pers = New Person With {.FirstName = "Don", .LastName = "Hall"} ' Do not add person to people list for the sake of Join examples. _pets.Add(New Pet With {.Name = "Spot", .Owner = pers}) ' Add a pet with no owner for the sake of Join examples. _pets.Add(New Pet With {.Name = "Unknown", .Owner = New Person With {.FirstName = String.Empty, .LastName = String.Empty}}) End Sub
Class Person Public Property FirstName As String Public Property LastName As String End Class Class Pet Public Property Name As String Public Property Owner As Person End Class
Выполните внутреннее соединение с помощью оператора Join
INNER JOIN объединяет данные из двух коллекций. Элементы, для которых совпадают указанные значения ключей, включаются. Все элементы из любой коллекции, у которых нет соответствующего элемента в другой коллекции, исключаются.
В Visual Basic LINQ предоставляет два варианта выполнения INNER JOIN: неявное соединение и явное соединение.
Неявное соединение указывает коллекции, которые необходимо объединить в From
предложении, и определяет соответствующие ключевые поля в предложении Where
. Visual Basic неявно присоединяется к двум коллекциям на основе указанных ключевых полей.
Явное присоединение можно указать с помощью Join
предложения, если необходимо указать, какие ключевые поля следует использовать в соединении. В этом случае Where
предложение по-прежнему можно использовать для фильтрации результатов запроса.
Выполнение внутреннего соединения с помощью предложения Join
Добавьте следующий код в
Module1
модуль в проекте, чтобы просмотреть примеры неявного и явного внутреннего соединения.Sub InnerJoinExample() ' Create two lists. Dim people = GetPeople() Dim pets = GetPets(people) ' Implicit Join. Dim petOwners = From pers In people, pet In pets Where pet.Owner Is pers Select pers.FirstName, PetName = pet.Name ' Display grouped results. Dim output As New System.Text.StringBuilder For Each pers In petOwners output.AppendFormat( pers.FirstName & ":" & vbTab & pers.PetName & vbCrLf) Next Console.WriteLine(output) ' Explicit Join. Dim petOwnersJoin = From pers In people Join pet In pets On pet.Owner Equals pers Select pers.FirstName, PetName = pet.Name ' Display grouped results. output = New System.Text.StringBuilder() For Each pers In petOwnersJoin output.AppendFormat( pers.FirstName & ":" & vbTab & pers.PetName & vbCrLf) Next Console.WriteLine(output) ' Both queries produce the following output: ' ' Magnus: Daisy ' Terry: Barley ' Terry: Boots ' Terry: Blue Moon ' Charlotte: Whiskers End Sub
Выполните левое внешнее соединение, используя оператор объединения групп
LEFT OUTER JOIN включает все элементы из левой коллекции соединения и только соответствующие значения из правой коллекции соединения. Все элементы из правой коллекции соединения, которые не имеют соответствующего элемента в левой коллекции, исключаются из результата запроса.
Предложение Group Join
фактически выполняет левое внешнее соединение. Разница между тем, что обычно называется left outer join, и тем, что возвращает Group Join
, заключается в том, что Group Join
группирует результаты из правой коллекции соединения для каждого элемента в левой коллекции. В реляционной базе данных функция LEFT OUTER JOIN возвращает негруппированные результаты, в результате которых каждый элемент в результате запроса содержит соответствующие элементы из обеих коллекций в соединении. В этом случае элементы из левой коллекции соединения повторяются для каждого соответствующего элемента из правой коллекции. После выполнения следующей процедуры вы увидите, как это выглядит.
Результаты Group Join
запроса можно получить в виде негруппированного результата, расширив запрос, чтобы вернуть элемент для каждого сгруппированного результата запроса. Для этого необходимо убедиться, что вы запрашиваете с использованием метода DefaultIfEmpty
сгруппированной коллекции. Это гарантирует, что элементы из левой коллекции соединения всегда включаются в результат запроса, даже когда у них нет соответствующих результатов из правой коллекции соединения. Вы можете добавить код в запрос, чтобы предоставить значение результата по умолчанию, если из правой коллекции соединения нет соответствующего значения.
Выполнение левого внешнего соединения с помощью предложения "Объединение групп"
Добавьте следующий код в
Module1
модуль в проекте, чтобы просмотреть примеры как сгруппированного левого внешнего соединения, так и негруппированного левого внешнего соединения.Sub LeftOuterJoinExample() ' Create two lists. Dim people = GetPeople() Dim pets = GetPets(people) ' Grouped results. Dim petOwnersGrouped = From pers In people Group Join pet In pets On pers Equals pet.Owner Into PetList = Group Select pers.FirstName, pers.LastName, PetList ' Display grouped results. Dim output As New System.Text.StringBuilder For Each pers In petOwnersGrouped output.AppendFormat(pers.FirstName & ":" & vbCrLf) For Each pt In pers.PetList output.AppendFormat(vbTab & pt.Name & vbCrLf) Next Next Console.WriteLine(output) ' This code produces the following output: ' ' Magnus: ' Daisy ' Terry: ' Barley ' Boots ' Blue Moon ' Charlotte: ' Whiskers ' Arlene: ' "Flat" results. Dim petOwners = From pers In people Group Join pet In pets On pers Equals pet.Owner Into PetList = Group From pet In PetList.DefaultIfEmpty() Select pers.FirstName, pers.LastName, PetName = If(pet Is Nothing, String.Empty, pet.Name) ' Display "flat" results. output = New System.Text.StringBuilder() For Each pers In petOwners output.AppendFormat( pers.FirstName & ":" & vbTab & pers.PetName & vbCrLf) Next Console.WriteLine(output.ToString()) ' This code produces the following output: ' ' Magnus: Daisy ' Terry: Barley ' Terry: Boots ' Terry: Blue Moon ' Charlotte: Whiskers ' Arlene: End Sub
Выполнение соединения с помощью составного ключа
Вы можете использовать ключевое слово And
в предложении Join
или Group Join
для идентификации нескольких ключевых полей, которые следует использовать при сопоставлении значений из присоединяемых коллекций. Ключевое And
слово указывает, что все указанные поля ключей должны совпадать для соединения элементов.
Чтобы выполнить соединение, используя составной ключ
Добавьте следующий код в
Module1
модуль в проекте, чтобы просмотреть примеры соединения, использующего составной ключ.Sub CompositeKeyJoinExample() ' Create two lists. Dim people = GetPeople() Dim pets = GetPets(people) ' Implicit Join. Dim petOwners = From pers In people Join pet In pets On pet.Owner.FirstName Equals pers.FirstName And pet.Owner.LastName Equals pers.LastName Select pers.FirstName, PetName = pet.Name ' Display grouped results. Dim output As New System.Text.StringBuilder For Each pers In petOwners output.AppendFormat( pers.FirstName & ":" & vbTab & pers.PetName & vbCrLf) Next Console.WriteLine(output) ' This code produces the following output: ' ' Magnus: Daisy ' Terry: Barley ' Terry: Boots ' Terry: Blue Moon ' Charlotte: Whiskers End Sub
Запуск кода
Добавление кода для запуска примеров
Замените
Sub Main
в модулеModule1
вашего проекта следующим кодом, чтобы запустить примеры, приведенные в этом разделе.Sub Main() InnerJoinExample() LeftOuterJoinExample() CompositeKeyJoinExample() Console.ReadLine() End Sub
Нажмите клавишу F5, чтобы запустить примеры.