Compartilhar via


Como executar junções internas (Guia de Programação em C#)

Em termos de banco de dados relacional, uma associação interna produz um conjunto de resultados no qual cada elemento da coleção primeiro aparece uma vez para cada elemento correspondente na segunda coleção. Se um elemento na primeira coleção não tiver nenhum elemento correspondente, ele não aparecerá no conjunto de resultados. O Join método, que é chamado pelo join cláusula C# implementa uma associação interna.

Este tópico mostra como executar quatro variações de uma associação interna:

  • Uma associação interna simple que correlaciona os elementos de duas fontes de dados com base em uma chave simple.

  • Uma associação interna que correlaciona os elementos de dados de duas origens com base em um composto chave. Uma chave composta, o que é uma chave que consiste em mais de um valor, permite que você correlacione os elementos com base em mais de uma propriedade.

  • A associação múltipla em qual associação sucessiva operações são acrescentadas uns aos outros.

  • Uma associação interna que é implementada usando uma associação de grupo.

Exemplo

Exemplo de associação de chave simples

O exemplo a seguir cria duas coleções que contêm objetos dos dois tipos definidos pelo usuário, Person e Pet. A consulta usa a join cláusula em C# para corresponder à Person objetos com Pet objetos cuja Owner é que Person. O select cláusula C# define qual serão a aparência de objetos resultantes. Neste exemplo, os objetos resultantes são tipos anônimos que consistem em nome do proprietário e o nome do bicho de estimação.

        class Person
        {
            public string FirstName { get; set; }
            public string LastName { get; set; }
        }

        class Pet
        {
            public string Name { get; set; }
            public Person Owner { get; set; }
        }

        /// <summary> 
        /// Simple inner join. 
        /// </summary> 
        public static void InnerJoinExample()
        {
            Person magnus = new Person { FirstName = "Magnus", LastName = "Hedlund" };
            Person terry = new Person { FirstName = "Terry", LastName = "Adams" };
            Person charlotte = new Person { FirstName = "Charlotte", LastName = "Weiss" };
            Person arlene = new Person { FirstName = "Arlene", LastName = "Huff" };
            Person rui = new Person { FirstName = "Rui", LastName = "Raposo" };

            Pet barley = new Pet { Name = "Barley", Owner = terry };
            Pet boots = new Pet { Name = "Boots", Owner = terry };
            Pet whiskers = new Pet { Name = "Whiskers", Owner = charlotte };
            Pet bluemoon = new Pet { Name = "Blue Moon", Owner = rui };
            Pet daisy = new Pet { Name = "Daisy", Owner = magnus };

            // Create two lists.
            List<Person> people = new List<Person> { magnus, terry, charlotte, arlene, rui };
            List<Pet> pets = new List<Pet> { barley, boots, whiskers, bluemoon, daisy };

            // Create a collection of person-pet pairs. Each element in the collection 
            // is an anonymous type containing both the person's name and their pet's name. 
            var query = from person in people
                        join pet in pets on person equals pet.Owner
                        select new { OwnerName = person.FirstName, PetName = pet.Name };

            foreach (var ownerAndPet in query)
            {
                Console.WriteLine("\"{0}\" is owned by {1}", ownerAndPet.PetName, ownerAndPet.OwnerName);
            }
        }

        // This code produces the following output: 
        // 
        // "Daisy" is owned by Magnus
        // "Barley" is owned by Terry
        // "Boots" is owned by Terry
        // "Whiskers" is owned by Charlotte
        // "Blue Moon" is owned by Rui

Observe que o Person de objeto cuja LastName é "Huff" não aparece no resultado definido porque não há nenhum Pet objeto que tem Pet.Owner igual a Person.

Exemplo de associação de chave composta

Em vez de correlacionar os elementos com base em apenas uma propriedade, você pode usar uma chave composta para comparar os elementos com base em várias propriedades. Para fazer isso, especifique a função de seletor de chave de cada coleção para retornar um tipo anônimo que consiste nas propriedades que você deseja comparar. Se você rotular as propriedades, eles devem ter o mesmo rótulo em um tipo anônimo do cada chave. As propriedades também devem aparecer na mesma ordem.

O exemplo a seguir usa uma lista de Employee objetos e uma lista de Student objetos para determinar quais funcionários estão também os alunos. Esses dois tipos de tem um FirstName e um LastName propriedade do tipo String. As funções que cria as chaves de associação a partir de elementos de cada lista retornam um tipo anônimo que consiste o FirstName e LastName propriedades de cada elemento. A operação de ingresso compara essas chaves compostas de igualdade e retorna pares de objetos de cada lista onde coincidir com o nome e o sobrenome.

        class Employee
        {
            public string FirstName { get; set; }
            public string LastName { get; set; }
            public int EmployeeID { get; set; }
        }

        class Student
        {
            public string FirstName { get; set; }
            public string LastName { get; set; }
            public int StudentID { get; set; }
        }

        /// <summary> 
        /// Performs a join operation using a composite key. 
        /// </summary> 
        public static void CompositeKeyJoinExample()
        {
            // Create a list of employees.
            List<Employee> employees = new List<Employee> {
                new Employee { FirstName = "Terry", LastName = "Adams", EmployeeID = 522459 },
                 new Employee { FirstName = "Charlotte", LastName = "Weiss", EmployeeID = 204467 },
                 new Employee { FirstName = "Magnus", LastName = "Hedland", EmployeeID = 866200 },
                 new Employee { FirstName = "Vernette", LastName = "Price", EmployeeID = 437139 } };

            // Create a list of students.
            List<Student> students = new List<Student> {
                new Student { FirstName = "Vernette", LastName = "Price", StudentID = 9562 },
                new Student { FirstName = "Terry", LastName = "Earls", StudentID = 9870 },
                new Student { FirstName = "Terry", LastName = "Adams", StudentID = 9913 } };

            // Join the two data sources based on a composite key consisting of first and last name, 
            // to determine which employees are also students.
            IEnumerable<string> query = from employee in employees
                                        join student in students
                                        on new { employee.FirstName, employee.LastName }
                                        equals new { student.FirstName, student.LastName }
                                        select employee.FirstName + " " + employee.LastName;

            Console.WriteLine("The following people are both employees and students:");
            foreach (string name in query)
                Console.WriteLine(name);
        }

        // This code produces the following output: 
        // 
        // The following people are both employees and students: 
        // Terry Adams 
        // Vernette Price

Exemplo de associação de múltiplos

Qualquer número de operações de associação pode ser anexado a si para realizar uma associação múltipla. Cada join cláusula C# correlaciona uma fonte de dados especificada com os resultados da associação anterior.

O exemplo a seguir cria três coleções: uma lista de Person objetos, uma lista de Cat objetos e uma lista de Dog objetos.

O primeiro join cláusula C# corresponde a pessoas e gatos com base em um Person correspondentes do objeto Cat.Owner. Ele retorna uma seqüência de tipos anônimos que contêm o Person objeto e Cat.Name.

A segunda join cláusula C# correlaciona os tipos anônimos retornados pela primeira associação com Dog objetos na lista fornecida de cães, com base em uma chave composta que consiste o Owner propriedade do tipo Persone a primeira letra do nome do animal. Ele retorna uma seqüência de tipos anônimos que contêm o Cat.Name e Dog.Name propriedades de cada par correspondente. Como esta é uma associação interna, apenas os objetos da primeira fonte de dados que têm uma correspondência na segunda fonte de dados são retornados.

        class Person
        {
            public string FirstName { get; set; }
            public string LastName { get; set; }
        }

        class Pet
        {
            public string Name { get; set; }
            public Person Owner { get; set; }
        }

        class Cat : Pet
        { }

        class Dog : Pet
        { }

        public static void MultipleJoinExample()
        {
            Person magnus = new Person { FirstName = "Magnus", LastName = "Hedlund" };
            Person terry = new Person { FirstName = "Terry", LastName = "Adams" };
            Person charlotte = new Person { FirstName = "Charlotte", LastName = "Weiss" };
            Person arlene = new Person { FirstName = "Arlene", LastName = "Huff" };
            Person rui = new Person { FirstName = "Rui", LastName = "Raposo" };
            Person phyllis = new Person { FirstName = "Phyllis", LastName = "Harris" };

            Cat barley = new Cat { Name = "Barley", Owner = terry };
            Cat boots = new Cat { Name = "Boots", Owner = terry };
            Cat whiskers = new Cat { Name = "Whiskers", Owner = charlotte };
            Cat bluemoon = new Cat { Name = "Blue Moon", Owner = rui };
            Cat daisy = new Cat { Name = "Daisy", Owner = magnus };

            Dog fourwheeldrive = new Dog { Name = "Four Wheel Drive", Owner = phyllis };
            Dog duke = new Dog { Name = "Duke", Owner = magnus };
            Dog denim = new Dog { Name = "Denim", Owner = terry };
            Dog wiley = new Dog { Name = "Wiley", Owner = charlotte };
            Dog snoopy = new Dog { Name = "Snoopy", Owner = rui };
            Dog snickers = new Dog { Name = "Snickers", Owner = arlene };

            // Create three lists.
            List<Person> people =
                new List<Person> { magnus, terry, charlotte, arlene, rui, phyllis };
            List<Cat> cats =
                new List<Cat> { barley, boots, whiskers, bluemoon, daisy };
            List<Dog> dogs =
                new List<Dog> { fourwheeldrive, duke, denim, wiley, snoopy, snickers };

            // The first join matches Person and Cat.Owner from the list of people and 
            // cats, based on a common Person. The second join matches dogs whose names start 
            // with the same letter as the cats that have the same owner. 
            var query = from person in people
                        join cat in cats on person equals cat.Owner
                        join dog in dogs on  
                        new { Owner = person, Letter = cat.Name.Substring(0, 1) }
                        equals new { dog.Owner, Letter = dog.Name.Substring(0, 1) }
                        select new { CatName = cat.Name, DogName = dog.Name };

            foreach (var obj in query)
            {
                Console.WriteLine(
                    "The cat \"{0}\" shares a house, and the first letter of their name, with \"{1}\".", 
                    obj.CatName, obj.DogName);
            }
        }

        // This code produces the following output: 
        // 
        // The cat "Daisy" shares a house, and the first letter of their name, with "Duke".
        // The cat "Whiskers" shares a house, and the first letter of their name, with "Wiley".

Associação interna usando agrupados exemplo ingressar

O exemplo a seguir mostra como implementar uma associação interna por meio de uma associação de grupo.

Na query1, a lista de Person objetos é o grupo associado à lista de Pet objetos com base na Person correspondentes a Pet.Owner propriedade. A associação de grupo cria uma coleção dos grupos de intermediários, onde cada grupo consiste em um Person objeto e uma seqüência de correspondência Pet objetos.

Adicionando um segundo from cláusula à consulta, essa seqüência de seqüências é combinada (ou achatada) em uma seqüência mais longa. O tipo dos elementos da seqüência final é especificado pelo select cláusula. Neste exemplo, se o tipo é um tipo anônimo que consiste o Person.FirstName e Pet.Name propriedades para cada par correspondente.

O resultado de query1 é equivalente ao conjunto de resultados que teria sido obtido usando o join cláusula sem a into cláusula para realizar uma junção interna. O query2 variável demonstra essa consulta equivalente.

        class Person
        {
            public string FirstName { get; set; }
            public string LastName { get; set; }
        }

        class Pet
        {
            public string Name { get; set; }
            public Person Owner { get; set; }
        }

        /// <summary> 
        /// Performs an inner join by using GroupJoin(). 
        /// </summary> 
        public static void InnerGroupJoinExample()
        {
            Person magnus = new Person { FirstName = "Magnus", LastName = "Hedlund" };
            Person terry = new Person { FirstName = "Terry", LastName = "Adams" };
            Person charlotte = new Person { FirstName = "Charlotte", LastName = "Weiss" };
            Person arlene = new Person { FirstName = "Arlene", LastName = "Huff" };

            Pet barley = new Pet { Name = "Barley", Owner = terry };
            Pet boots = new Pet { Name = "Boots", Owner = terry };
            Pet whiskers = new Pet { Name = "Whiskers", Owner = charlotte };
            Pet bluemoon = new Pet { Name = "Blue Moon", Owner = terry };
            Pet daisy = new Pet { Name = "Daisy", Owner = magnus };

            // Create two lists.
            List<Person> people = new List<Person> { magnus, terry, charlotte, arlene };
            List<Pet> pets = new List<Pet> { barley, boots, whiskers, bluemoon, daisy };

            var query1 = from person in people
                         join pet in pets on person equals pet.Owner into gj
                         from subpet in gj
                         select new { OwnerName = person.FirstName, PetName = subpet.Name };

            Console.WriteLine("Inner join using GroupJoin():");
            foreach (var v in query1)
            {
                Console.WriteLine("{0} - {1}", v.OwnerName, v.PetName);
            }

            var query2 = from person in people
                         join pet in pets on person equals pet.Owner
                         select new { OwnerName = person.FirstName, PetName = pet.Name };

            Console.WriteLine("\nThe equivalent operation using Join():");
            foreach (var v in query2)
                Console.WriteLine("{0} - {1}", v.OwnerName, v.PetName);
        }

        // This code produces the following output: 
        // 
        // Inner join using GroupJoin(): 
        // Magnus - Daisy 
        // Terry - Barley 
        // Terry - Boots 
        // Terry - Blue Moon 
        // Charlotte - Whiskers 
        // 
        // The equivalent operation using Join(): 
        // Magnus - Daisy 
        // Terry - Barley 
        // Terry - Boots 
        // Terry - Blue Moon 
        // Charlotte - Whiskers

Compilando o código

  • Crie um novo projeto de aplicativo de Console em Visual Studio.

  • Adicione uma referência a System.Core.dll se já não é referenciado.

  • Incluir o System.Linq espaço para nome.

  • Copie e cole o código do exemplo no arquivo Program. cs, abaixo do Main método. Adicionar uma linha de código para o Main método para chamar o método que você colou no.

  • Execute o programa.

Consulte também

Tarefas

Como executar junções agrupadas (Guia de Programação em C#)

Como executar junções externas esquerdas (Guia de Programação em C#)

Como unir duas coleções (C#) (LINQ to XML)

Referência

Join

GroupJoin

Tipos anônimos (Guia de Programação em C#)

Conceitos

Operações join

Tipos anônimos (Visual Basic)