{"id":19663363,"url":"https://github.com/jonasaacampos/guia-sql","last_synced_at":"2025-02-27T03:31:35.025Z","repository":{"id":43230685,"uuid":"511155953","full_name":"jonasaacampos/guia-sql","owner":"jonasaacampos","description":"Além de exercícios com questões reais de negócios, você pode usar os códigos disponibilizados para espadir seus horizontes sobre banco de dados.","archived":false,"fork":false,"pushed_at":"2022-07-06T14:40:21.000Z","size":1082,"stargazers_count":17,"open_issues_count":0,"forks_count":0,"subscribers_count":2,"default_branch":"main","last_synced_at":"2025-01-10T02:13:19.809Z","etag":null,"topics":["data-science","database","dataquery","sql"],"latest_commit_sha":null,"homepage":"","language":null,"has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"mit","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/jonasaacampos.png","metadata":{"files":{"readme":"ReadMe.md","changelog":null,"contributing":null,"funding":null,"license":"LICENSE","code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null}},"created_at":"2022-07-06T13:49:02.000Z","updated_at":"2024-11-11T01:40:55.000Z","dependencies_parsed_at":"2022-09-22T13:31:01.554Z","dependency_job_id":null,"html_url":"https://github.com/jonasaacampos/guia-sql","commit_stats":null,"previous_names":[],"tags_count":0,"template":false,"template_full_name":null,"repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/jonasaacampos%2Fguia-sql","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/jonasaacampos%2Fguia-sql/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/jonasaacampos%2Fguia-sql/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/jonasaacampos%2Fguia-sql/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/jonasaacampos","download_url":"https://codeload.github.com/jonasaacampos/guia-sql/tar.gz/refs/heads/main","host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":240972658,"owners_count":19887004,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2022-07-04T15:15:14.044Z","host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":["data-science","database","dataquery","sql"],"created_at":"2024-11-11T16:14:17.883Z","updated_at":"2025-02-27T03:31:34.972Z","avatar_url":"https://github.com/jonasaacampos.png","language":null,"readme":"\u003cp align=\"center\"\u003e\n\t  \u003ca href='https://jonasaacampos.github.io/portfolio/'\u003e\n      \u003cimg alt=\"SQL\" src=\"https://img.shields.io/static/v1?color=red\u0026label=Dev\u0026message=SQL\u0026style=for-the-badge\u0026logo=SQL\"/\u003e\n      \u003c/a\u003e\n\u003c/p\u003e\n\n\u003cimg alt=\"Java\" src=\"img/sql_logo.png\" width=150 align=right\u003e\n\n\u003ch1\u003eSQL - um guia para autoditadas\u003c/h1\u003e\n\nNotas, projetos e insights gerados ao longo dos meus estudos de SQL, com o objetivo de documentar o aprendizado para futuras consultas e auxiliar interessados e estudantes da área. Além de exercícios com questões reais de negócios, você pode usar os códigos disponibilizados para expadir seus horizontes sobre banco de dados.\n\nDivirta-se!\n\n\u003ch2\u003ePra quem este guia não é\u003c/h2\u003e\n\n- [ ] Você deseja aprender sobre SQL em 10 horas ou menos?\n- [ ] Você tem preguiça de ler e de fazer exercícios com casos reais?\n\nSe você respondeu sim para quaisquer uma destas perguntas, **este documento não é para você**. Vasculhe meu repositório à procura de outros projetos que talvez te ajude.\n\n[![](https://img.shields.io/badge/feito%20com%20%E2%9D%A4%20por-jaac-cyan)](https://jonasaacampos.github.io/portfolio/)\n[![LinkedIn Badge](https://img.shields.io/badge/LinkedIn-Profile-informational?style=flat\u0026logo=linkedin\u0026logoColor=white\u0026color=0D76A8)](https://www.linkedin.com/in/jonasaacampos)\n\n\u003ch2\u003eCobertura do conteúdo estudado\u003c/h2\u003e\n\n    Repositório em constante atualização. Volte sempre ;D\n    \n- [X] Introdução\n- [X] Criação do ambiente\n- [X] Ordenamento\n- [X] Filtros\n- [X] Funções de agregação\n- [X] Agrupamento de dados\n- [X] JOINs\n- [X] JOINS + GROUP BY\n- [ ] Variáveis\n- [ ] Manipulação de Strins e Datas\n- [ ] Funções condicionais\n- [ ] SQL views\n- [ ] CRUD\n- [ ] Functions\n- [ ] Store Procedures\n- [ ] Window Functions\n- [ ] Regex\n\n-------\n## Table of Contents\n\n- [Table of Contents](#table-of-contents)\n- [Introdução (Começe por aqui)](#introdução-começe-por-aqui)\n  - [🎲🎲Dados 🎲🎲](#dados-)\n  - [**Banco de Dados**](#banco-de-dados)\n  - [**SQL**](#sql)\n  - [SGBD](#sgbd)\n  - [MySQL, SQL Server, Oracle ou PostgreSQL?](#mysql-sql-server-oracle-ou-postgresql)\n  - [SQL Server (Preparação do ambiente)](#sql-server-preparação-do-ambiente)\n  - [Preparando ambiente](#preparando-ambiente)\n    - [Windows](#windows)\n    - [Linux](#linux)\n- [Conhecendo a base de dados](#conhecendo-a-base-de-dados)\n- [SELECT](#select)\n  - [SELECT TOP(N) || SELECT TOP(N) PERCENT](#select-topn--select-topn-percent)\n  - [SELECT DISTINCT](#select-distinct)\n  - [AS](#as)\n  - [Resumo](#resumo)\n  - [Exercícios](#exercícios)\n- [Ordenação de dados (ORDER BY)](#ordenação-de-dados-order-by)\n- [Filtro de dados (WHERE)](#filtro-de-dados-where)\n    - [Exercícios com WHERE](#exercícios-com-where)\n  - [IN](#in)\n  - [LIKE](#like)\n  - [BETWEEN](#between)\n  - [IS NULL // IS NOT NULL](#is-null--is-not-null)\n  - [Exercícios](#exercícios-1)\n- [Funções de Agregação](#funções-de-agregação)\n  - [SUM](#sum)\n  - [COUNT](#count)\n  - [COUNT DISTINCT](#count-distinct)\n  - [MIN E MAX](#min-e-max)\n  - [AVG](#avg)\n  - [Exercícios](#exercícios-2)\n- [GROUP BY](#group-by)\n  - [GROUP BY + ORDER BY](#group-by--order-by)\n  - [GROUP BY + WHERE + ORDER BY](#group-by--where--order-by)\n  - [HAVING](#having)\n  - [Exercícios](#exercícios-3)\n- [JOINS no SQL](#joins-no-sql)\n  - [Chave Primária e Chave Estrangeira](#chave-primária-e-chave-estrangeira)\n  - [Tabela Fato e Tabela Dimensão](#tabela-fato-e-tabela-dimensão)\n  - [Tipos de JOIN](#tipos-de-join)\n  - [**Exemplo dos JOINS**](#exemplo-dos-joins)\n  - [Exercícios](#exercícios-4)\n- [JOINS + Agrupamentos](#joins--agrupamentos)\n  - [Exercícios](#exercícios-5)\n  - [Variáveis](#variáveis)\n- [Contato](#contato)\n- [Crédito das imagens](#crédito-das-imagens)\n\n## Introdução (Começe por aqui)\n\n### 🎲🎲Dados 🎲🎲\n\nDado é uma informação sobre alguma coisa.\n\nEm uma empresa, os dados cumprem um papel tão importante quanto qualquer outro bem. Porém, para extrair o melhor de um dado, não basta tê lo, é preciso organizá lo para então entendê lo.\n\n### **Banco de Dados**\n\nBancos de dados são conjuntos de tabelas, com alguma relação entre si, com dados sobre pessoas, lugares ou coisas.\n\nDados isolados possuem valor. Dados organizados e agrupados possuem mais valor ainda.\n\n    \u003e Dado ➡️ Tabela ➡️ Banco de dados\n\n### **SQL**\n\nO SQL(Structured Query Language) é uma linguagem padrão para trabalhar com bancos de dados relacionais. Se trata de uma linguagem de programação que permite a manipulação dos\n\ndados em um banco de dados.\n\nImagine uma tabela com os dados de todas as vendas\n\n![Screenshot_1.jpg](img/Screenshot_1.jpg)\n\nPara exibir todas as vendas com valor maior que R$1.000 podemos usar uma consulta (query), que retornará uma nova tabela.\n\n```sql\nSELECT * FROM tabela_vendas WHERE valor \u003e 1000\n```\n\n![Screenshot_2.jpg](img/Screenshot_2.jpg)\n\n### SGBD\n\nUm SGBD permite ao desenvolvedor trabalhar com diferentes tabelas de um banco de dados através de uma interface. Além da interface temos um servidor, onde são armazenados os bancos de dados.\n\nAbaixo, temos os 4 principais programas para SGBDs (todos utilizam o SQL como linguagem de programação).\n\n| SGBD                                                                                                        | Descrição                                                                                                                                    |\n| ----------------------------------------------------------------------------------------------------------- | :------------------------------------------------------------------------------------------------------------------------------------------- |\n| \u003cimg alt=\"MySQL\" src=\"https://cdn-icons-png.flaticon.com/512/919/919836.png\" width=150 align=right\u003e         | MySQL: É um SGBD relacional de código aberto, usado na maioria das aplicações gratuitas. A interface de código utilizada é o MySQLWorkbench. |\n| \u003cimg alt=\"SQL Oracle\" src=\"https://cdn-icons-png.flaticon.com/512/5969/5969229.png\" width=150 align=right\u003e  | Oracle: O SGBD da Oracle é focado em empresas de médio e grande porte. A interface de código utilizada é o SQL Developer.                    |\n| \u003cimg alt=\"SQL Server\" src=\"https://cdn-icons-png.flaticon.com/512/5968/5968364.png\" width=150 align=right\u003e  | SQL Server: O SQL Server é o SGBD criado pela Microsoft, também para bancos de dados relacionais. A interface de código utilizada é o SSMS.  |\n| \u003cimg alt=\"SQL Postgre\" src=\"https://cdn-icons-png.flaticon.com/512/5968/5968277.png\" width=150 align=right\u003e | Postgre SQL: Criado em 1989 e ainda um dos mais utilizados no mundo. A interface de código utilizada é o pgAdmin.                            |\n\n----\n\n### MySQL, SQL Server, Oracle ou PostgreSQL?\n\n\u003cp align=\"center\"\u003e\n\u003cimg alt=\"Keanu Reeves choices a SQL SBD\" src=\"https://media3.giphy.com/media/MgkBTmxt18lGg/giphy.gif\"\u003e\n\u003c/p\u003e\n\n\u003e Qualquer um serve. 👨🏾‍💻 O SQL você vai precisar aprender em qualquer um dos casos.\n\nO SQL é usado como a linguagem padrão em todos os sistemas de gerenciamento de banco de dados relacional. No entanto, o SQL possui algumas vertentes que dependem de cada sistema de gerenciamento de banco de dados, onde cada SGBD incorpora à linguagem algumas funcionalidades e recursos extras.\n\n\n![Untitled](img/Untitled.png)\n\n- **TSQL, ou T SQL (Transaction SQL)**\n    \n    É uma versão aprimorada do SQL que contém algumas extensões. Originalmente desenvolvido pela Sybase e agora é propriedade da Microsoft. O T SQL adiciona alguns recursos avançados ao SQL para torná-lo mais poderoso, como variáveis declaradas, controle de transação, tratamento de erros e exceções, operações com *strings,* processamento de data e hora, etc\n- **PLSQL ou Procedural Language /SQL**\n    É outra forma estendida de SQL que é usada pela Oracle para seu banco de dados. A principal diferença entre o T SQL e o PL SQL é a maneira como eles lidam com variáveis, procedimentos armazenados e funções integradas. TSQL também é considerado mais fácil e simples de entender, enquanto PL SQL incorpora maior complexidade.\n- **PL-pgSQL**\n    É uma linguagem procedural específica do PostgreSQL baseada em SQL. Semelhante ao T SQL e PL SQL, ele adiciona alguns recursos avançados ao SQL, como loops, variáveis, tratamento de erros e exceções, etc.\n---\n\n### SQL Server (Preparação do ambiente)\n\nAqui vai um guia para a instalação das ferramentas necessárias para manipulação de banco de dados. Aqui usarei o SQL Server.\n\n\u003cdetails\u003e\n\u003csummary\u003e\u003cstrong\u003ePreparando ambiente\u003c/strong\u003e\u003c/summary\u003e\n\n### Preparando ambiente\n\n#### Windows\n\n- [ ]  SQL Server Developer Edition\n- [ ]  [SSMS](https://docs.microsoft.com/pt-br/sql/ssms/download-sql-server-management-studio-ssms?redirectedfrom=MSDN\u0026view=sql-server-ver16)\n- [ ]  ContosoBIdemoBAK.exe (extrair arquivo)\n\n#### Linux\n\n```bash\n# importe a chave pública da microsoft\nwget -qO- https://packages.microsoft.com/keys/microsoft.asc | sudo apt-key add -\n\n# confira a versaão do seu linux\nhostnamectl\n\n# Registre o repositório do Ubuntu do Microsoft SQL Server para o SQL Server 2019:\n# UBuntu 20.04\nsudo add-apt-repository \"$(wget -qO- https://packages.microsoft.com/config/ubuntu/20.04/mssql-server-2019.list)\"\n\n# atualize a lista de repositórios e instale o SQL server\nsudo apt-get update | sudo apt-get install -y mssql-server\n\n# execute o instalador\nsudo /opt/mssql/bin/mssql-conf setup\n\n#Após a instação, confira se o serviço está em execução\nsystemctl status mssql-server --no-pager\n\n## Como SGBD utilize o Dbeaver (ou outro de sua preferência)\n```\n\n- Para restaurar o Banco de dados da Contoso\n    \n    ![Untitled](img/Untitled%201.png)\n    \n    ![Untitled](img/Untitled%202.png)\n    \n\u003c/details\u003e\n\n---\n\n[🏠 Retornar ao índice](#table-of-contents)\n\n## Conhecendo a base de dados\n\n![A empresa Contoso Corporation é uma empresa multinacional fictícia ( com sede em Paris e com escritórios espalhados ao longo de todo o mundo. Realiza fabricação, vendas e suporte, com mais de **100.000 produtos**. Por ser uma empresa multinacional, utiliza um SGBD da Microsoft (SQL Server) para centralizar e manipular o grande volume de dados associados ao negócio. Possui mais de **25 mil funcionários** espalhados ao longo das dezenas de escritórios no mundo.](https://docs.microsoft.com/pt-br/microsoft-365/media/contoso-overview/contoso-overview-fig1.png?view=o365-worldwide)\n\nA empresa Contoso Corporation é uma empresa multinacional fictícia ( com sede em Paris e com escritórios espalhados ao longo de todo o mundo. Realiza fabricação, vendas e suporte, com mais de **100.000 produtos**. Por ser uma empresa multinacional, utiliza um SGBD da Microsoft (SQL Server) para centralizar e manipular o grande volume de dados associados ao negócio. Possui mais de **25 mil funcionários** espalhados ao longo das dezenas de escritórios no mundo.\n\n\n---\n\n[🏠 Retornar ao índice](#table-of-contents)\n\n## SELECT\n\n\u003e Comando SELECT ... FROM : retorna todas as linhas da tabela, independente das colunas selecionadas\n\u003e \n\n```sql\n/*Seleciona todas as colunas de uma determinada tabela*/\nSELECT * FROM DimCustomer\nSELECT * FROM DimStore;\nSELECT * FROM DimProduct\n\n/*Traz somente informações úteis para a aplicação usuário final*/\nSELECT StoreKey, StoreName, StorePhone FROM dimStore;\nSELECT ProductName, BrandName FROM DimProduct\n\n-- isso é um comentário de uma linha\n/*\n isso é um comentário de bloco\n*/\n```\n\n![Exibindo todos os dados da tabela de lojas (SELECT * FROM DimStore;) ... Mas eu gostaria de APENAS o nome, o código e o telefone das lojas!](img/Untitled%203.png)\n\nExibindo todos os dados da tabela de lojas (SELECT * FROM DimStore;) ... Mas eu gostaria de APENAS o nome, o código e o telefone das lojas!\n\n![Voilà! (SELECT StoreKey, StoreName, StorePhone FROM dimStore;)](img/Untitled%204.png)\n\n\u003e Voilà! (SELECT StoreKey, StoreName, StorePhone FROM dimStore;)\n\n---\n\n### SELECT TOP(N) || SELECT TOP(N) PERCENT\n\n\u003e SELECT TOP(n) || SELECT TOP(n) PERCENT : retorna as N primeiras linhas\n\n```sql\n/*1. Crie uma consulta que retorne as 10 primeiras linhas da tabela produtos*/\nSELECT TOP(10) * FROM DimProduct\n\n/*2. Crie uma consulta que retorne as 10% primeiras linhas da tabela produtos*/\nSELECT TOP(10) PERCENT * FROM DimProduct\n\n-- a tabela FactSales (vendas) possui cerca de 3 MILHÕES de linhas\nSELECT TOP(100) * FROM FactSales\n```\n\n### SELECT DISTINCT\n\n\u003e SELECT DISTINCT : Retorna os valores distintos de uma tabela\n\u003e \n\n```sql\n/* 1. Retorne todos os valores distindos da coluna ColorName da tabela dimProdutc*/\nSELECT \n\tDISTINCT ColorName\nFROM\n\tDimProduct\n\n/*2. Quais os departamento existem na empresa (tabela DimEmployee)*/\nSELECT\n\tDISTINCT DepartmentName\nFROM\n\tDimEmployee\n```\n\n### AS\n\n\u003e AS : Renomeia colunas (aliasing) na consulta\n\u003e \n\n```sql\n/*Selecione 3 colunas da tabela dimProduct: ProdutcName, BrandName e ColorName*/\n\nSELECT\n\tProductName AS Produto,\n\tBrandName\tAS Marca,\n\tColorName\tAS Cor\nFROM\n\tDimProduct\n\n-- O uso de 'aspas' é obrigatório caso o nome do campo seja composto.\n```\n\n### Resumo\n\n```sql\nSELECT * FROM tabela \n--exibe toda a tabela\n\nSELECT Coluna1, Coluna2, ..., FROM tabela \n--exibe apenas colunas selecionadas\n\nSELECT DISTINCT Coluna1 * FROM tabela \n--exibe valores únicos de determinada coluna\n\nSELECT TOP(N) * FROM tabela\nSELECT TOP(N) PERCENT * FROM tabela\n--exibe os primeiros N registros//primeiros % registros\n\nSELECT Coluna1 AS 'Novo Nome' FROM tabela\n--renomeia as colunas consultadas\n```\n\n### Exercícios\n\n\u003cdetails\u003e\n\u003csummary\u003e\u003cstrong\u003eExercícios e respostas\u003c/strong\u003e\u003c/summary\u003e\n\n1. Você é responsável por controlar os dados de clientes e de produtos da sua empresa. O que você precisará fazer é confirmar se:\n    1. Existem 2.517 produtos cadastrados na base e, se não tiver, você deverá reportar ao seu gestor para saber se existe alguma defasagem no controle dos produtos.\n    2. Até o mês passado, a empresa tinha um total de 19.500 clientes na base de controle. Verifique se esse número aumentou ou reduziu.\n    - **Solução Exercício 1:**\n        \n        ```sql\n        --A. Verificando quantidade de produtos cadastrados\n        SELECT \n        \tDISTINCT ProductName\n        FROM \n        \tDimProduct\n        /*A consulta trouxe 2.517 registros, portanto não há defasagem no controle de produtos*/\n        \n        -- B. Verificando quantidade de clientes atual\n        SELECT\n        \t*\n        FROM\n        \tDimCustomer\n        /*A consulta listou 18.869 registros, portanto o número de cadastros de clientes reduziu comparado ao mês anterior*/\n        ```\n        \n2. Você trabalha no setor de marketing da empresa Contoso e acaba de ter uma ideia de oferecer descontos especiais para os clientes no dia de seus aniversários. Para isso, você vai precisar listar todos os clientes e as suas respectivas datas de nascimento, além de um contato.\n    1. Selecione as colunas: CustomerKey, FirstName, EmailAddress, BirthDate da tabela dimCustomer.\n    2. Renomeie as colunas dessa tabela usando o alias (comando AS).\n    - **Solução Exercício 2:**\n        \n        ```sql\n        -- verificando as colunas da tabela clientes\n        SELECT TOP(10) * FROM  DimCustomer\n        \n        -- A. mostre apenas informações úteis para o marketing para a campanha de aniversário\n        -- b. Renomeie as colunas usando o comando AS\n        \n        SELECT\n        \tCustomerKey\t\tAS 'ID',\n        \tFirstName\t\tAS 'Nome',\n        \tEmailAddress\tAS 'e-mail',\n        \tBirthDate\t\tAS 'Data Nacimento'\n        FROM\n        \tDimCustomer\n        ```\n        \n        ![Untitled](img/Untitled%205.png)\n        \n3. A Contoso está comemorando aniversário de inauguração de 10 anos e pretende fazer uma ação de premiação para os clientes. A empresa quer presentear os primeiros clientes desde a inauguração. Você foi alocado para levar adiante essa ação. Para isso, você terá que\nfazer o seguinte:\n    1. A Contoso decidiu presentear os primeiros 100 clientes da história com um vale compras de R$ 10.000. Utilize um comando em SQL para retornar uma tabela com os primeiros 100 primeiros clientes da tabela dimCustomer (selecione todas as colunas).\n    2.  A Contoso decidiu presentear os primeiros 20% de clientes da história com um vale compras de R$ 2.000. Utilize um comando em SQL para retornar 20% das linhas da sua tabela dimCustomer (selecione todas as colunas). \n    3. Adapte o código do item a) para retornar apenas as 100 primeiras linhas, mas apenas as colunas FirstName, EmailAddress, BirthDate. \n    4. Renomeie as colunas anteriores para nomes em português\n    - **Solução Exercício 3:**\n        \n        ```sql\n        -- A. Selecione os 100 primeiros registros da tabela de clientes\n        SELECT TOP(100) * FROM  DimCustomer\n        \n        -- B. Selecione os primeiros 20% dos clientes\n        SELECT TOP(20) PERCENT * FROM DimCustomer\n        \n        -- C. Exiba apenas as colunas  FirstName, EmailAddress, BirthDate. \n        SELECT\n        \tFirstName,\n        \tEmailAddress,\n        \tBirthDate\n        FROM\n        \tDimCustomer\n        \n        -- D. Renomeia as colunas para português\n        SELECT\n        \tFirstName\t\t  AS Nome,\n        \tEmailAddress\tAS 'e-mail',\n        \tBirthDate\t\t  AS nascimento\n        FROM\n        \tDimCustomer\n        ```\n        \n4. A empresa Contoso precisa fazer contato com os fornecedores de produtos para repor o estoque. Você é da área de compras e precisa descobrir quem são esses fornecedores. Utilize um comando em SQL para retornar apenas os nomes dos fornecedores na tabela dimProduct e renomeie essa nova coluna da tabela.\n    - **Solução Exercício 4:**\n        \n        ```sql\n        -- verificando tabela de produtos\n        SELECT TOP(10) * FROM DimProduct\n        -- exiba o nome dos fornecedores\n        SELECT \n        \tDISTINCT Manufacturer AS 'Fornecedores'\n        FROM \n        \tDimProduct\n        ```\n        \n        ![Untitled](img/Untitled%206.png)\n        \n5. O seu trabalho de investigação não para. Você precisa descobrir se existe algum produto registrado na base de produtos que ainda não tenha sido vendido. Tente chegar nessa informação. Obs: caso tenha algum produto que ainda não tenha sido vendido, você não precisa descobrir qual é, é suficiente saber se teve ou não algum produto que ainda não foi vendido.\n    - **Solução Exercício 5:**\n        \n        ```sql\n        -- verificando tabela de produtos\n        SELECT * FROM DimProduct\n        \n        /*Existem 2.517 registros*/\n        \n        -- Verificando tabela de Vendas (cerca de 3 milhões de registros...)\n        SELECT TOP(10) * FROM FactSales\n        \n        SELECT\n        \tDISTINCT ProductKey\n        FROM\n        \tFactSales\n        \n        /*consulta trouxe 2.516 registros, logo pode-se afirmar que existe 1 produto que não foi vendido*/\n        ```\n              \n\u003c/details\u003e\n\n---\n\n[🏠 Retornar ao índice](#table-of-contents)\n\n## Ordenação de dados (ORDER BY)\n\n\u003e ORDER BY é usado para ordenar os valores de uma tabela em ordem crescente ou decrescente\n\n```sql\nSELECT TOP(100) * FROM DimStore\nORDER BY EmployeeCount\n-- quando não especifico a sequência da ordenação, o resultado trará a ordenação ASC (ascendente)\n```\n\n```sql\n/* SELECIONE AS 10 PRIMEIRAS LINHAS DA TABELA DE PRODUTOS, \nE ORDENE DE ACORDO COM O CUSTO*/\nSELECT\n\tTOP(10) \n\tProductName,\n\tUnitCost,\n\tWeight\nFROM\n\tDimProduct\nORDER BY UnitCost DESC, Weight DESC\n```\n\n## Filtro de dados (WHERE)\n\n\u003e WHERE é um filtro de dados. Traz somente registros que atendam determinada condição\n\u003e \n\n```sql\n--  Quantos produtos custam mais de U$1.000?\nSELECT\n\tProductName AS Produto,\n\tUnitPrice\tAS Preço\nFROM\n\tDimProduct\nWHERE UnitPrice \u003e= 1000\nORDER BY UnitPrice\n```\n\n**Filtro de texto**\n\n```sql\n-- Quantas marcas existem na tabela de produtos?\nSELECT DISTINCT BrandName FROM DimProduct\n/* Existem 11 Marcas*/\n\n-- Quantos produtos da marca Wide World Importers estão cadastrados\nSELECT DISTINCT * FROM DimProduct\nWHERE BrandName = 'Wide World Importers'\n/*173 produtos*/\n```\n\n**Filtro de data**\n\n```sql\n-- Quantos clientes nasceram após 31/12/1970\nSELECT * FROM DimCustomer\nWHERE BirthDate \u003e= '1970-12-31'\nORDER BY BirthDate DESC\n```\n\n**Operadores Lógicos**\n\n```sql\nSELECT * FROM DimProduct\n\n-- produtos da Fabrikam da cor preta\nSELECT * FROM DimProduct\nWHERE BrandName = 'Fabrikam' AND ColorName='Black'\n\n-- produtos da Contoso ou Fabrikam. (Em geral usa-se o OR dentro de uma mesma coluna)\nSELECT * FROM DimProduct\nWHERE BrandName = 'Contoso' OR BrandName='Fabrikam'\n\n--todos os funcionários, exceto o Marketing\nSELECT * FROM DimEmployee\nWHERE NOT DepartmentName = 'Marketing'\n```\n\n#### Exercícios com WHERE\n\n\u003cdetails\u003e\n\u003csummary\u003e\u003cstrong\u003eRespostas e exercícios\u003c/strong\u003e\u003c/summary\u003e\n    \n    ```sql\n    -- 1. Selecione todas as linhas da tabela dimEmployee cujos funcionários sejam do sexo feminino do departamento de finanças\n    SELECT * FROM\tDimEmployee\n    WHERE Gender = 'F' AND DepartmentName = 'Finance' \n    \n    -- 2. Mostre todas as linhas com os produtos vermelhos com valor de venda maior ou igual a U$100 da marca Contoso.\n    SELECT * FROM DimProduct\n    WHERE BrandName = 'Contoso' AND ColorName = 'red' AND UnitPrice \u003e= 100\n    \n    -- 3. Exiba todas as linhas dos produtos das marcas Litware, Fabrikam ou Pretos\n    SELECT * FROM DimProduct\n    WHERE BrandName = 'Fabrikam' OR BrandName = 'Litware' OR ColorName = 'Black'\n    ORDER BY ColorName\n    \n    -- 4. Selecione todas as linhas da tabela dimSalesTerrutory (locais de abrangência das vendas) do continente europeu, exceto da Itália.\n    SELECT * FROM DimSalesTerritory\n    WHERE SalesTerritoryGroup = 'Europe' AND NOT SalesTerritoryCountry = 'Italy'\n    \n    -- 5. Mostre todas as linhas da tablea de produtos (dimProduct) cuja cor seja Preta ou Vermelho da Marca Fabrikam\n    SELECT * FROM DimProduct\n    WHERE (ColorName = 'Black' OR ColorName = 'Red') AND BrandName = 'Fabrikam'\n    ```\n\u003c/details\u003e \n\n### IN\n\n\u003e O operador IN permite que sejam especificados múltiplos critérios dentro do WHERE **é uma alternativa reduzida ao OR**\n\u003e \n\n```sql\nSELECT * FROM DimProduct\nWHERE ColorName IN ('Silver', 'Blue', 'White', 'Red', 'Black')\n\nSELECT * FROM DimEmployee\nWHERE DepartmentName IN ('Production', 'Marketing', 'Engineering')\nORDER BY DepartmentName\n```\n\n### LIKE\n\n\u003e O LIKE é usado em conjunto com o WHERE para **procurar por um determinado padrão em uma coluna**.\n\u003e \n\n```sql\n--Mostre todos os produtos MP3 player\nSELECT * FROM DimProduct\nWHERE ProductName LIKE '%MP3 Player%'\n\n--Mostre todas os produtos cuja descrição COMECE com 'Type'\nSELECT * FROM DimProduct\nWHERE ProductDescription LIKE 'Type%'\n```\n\nO sinal de **%** representa zero, um ou múltiplos caracteres.\n\nO **_** representa um único caractere\n\n![Untitled](img/Untitled%207.png)\n\n### BETWEEN\n\n\u003e O BETWEEN seleciona valores em um intervalo Estes valores podem ser números, textos ou datas\n\n```sql\nSELECT * FROM DimProduct\nWHERE UnitPrice BETWEEN 50 AND 100\n\nSELECT * FROM DimProduct\nWHERE UnitPrice NOT BETWEEN 50 AND 100\n```\n\n*O BETWEEN é inclusivo ou seja, os valores dos extremos (valor inicial e valor final) também são incluídos no intervalo*\n\n**Filtrando intervalo de datas**\n\n```sql\nSELECT * FROM DimEmployee\nWHERE HireDate BETWEEN '2000-01-01' AND '2000-12-31'\n```\n\n### IS NULL // IS NOT NULL\n\n\u003e Podemos encontrar valores nulos (em branco) em uma tabela\n\n```sql\n-- Exibe somente clientes PJ\nSELECT * FROM DimCustomer\nWHERE CompanyName IS NOT NULL\n```\n\n### Exercícios\n\n\u003cdetails\u003e\n\u003csummary\u003e\u003cstrong\u003eRespostas e Exercícios\u003c/strong\u003e\u003c/summary\u003e\n\n1. Você é o gerente da área de compras e precisa criar um relatório com as TOP 100 vendas, de acordo com a quantidade vendida. Você precisa fazer isso em 10min pois o diretor de compras solicitou essa informação para apresentar em uma reunião.\nUtilize seu conhecimento em SQL para buscar essas TOP 100 vendas, de acordo com o total vendido (SalesAmount).\n    - **Resposta Exercício 1**\n        \n        ```sql\n        -- Mostre as top 100 vendas com maior quantidade vendida\n        SELECT \n        \tTOP(100) *\t\n        FROM \n        \tFactSales\n        ORDER BY \n        \tSalesQuantity DESC\n        ```\n        \n2. Os TOP 10 produtos com maior UnitPrice possuem exatamente o mesmo preço. Porém, a empresa quer diferenciar esses preços de acordo com o peso (Weight) de cada um.\nO que você precisará fazer é ordenar esses top 10 produtos, de acordo com a coluna de UnitPrice e, além disso, estabelecer um critério de desempate, para que seja mostrado na ordem, do maior para o menor.  \nCaso ainda assim haja um empate entre 2 ou mais produtos, pense em uma forma de criar um segundo critério de desempate (além do peso).\n    - **Resposta Exercício 2**\n        \n        ```sql\n        -- \n        SELECT \n        \tTOP(10) *\t\n        FROM \n        \tDimProduct\n        ORDER BY \n        \tUnitPrice DESC, \n        \tWeight DESC,\n        \tColorID\n        ```\n        \n3. Você é responsável pelo setor de logística da empresa Contoso e precisa dimensionar o transporte de todos os produtos em categorias, de acordo com o peso.\nOs produtos da categoria A, com peso acima de 100kg, deverão ser transportados na primeira leva.\nFaça uma consulta no banco de dados para descobrir quais são estes produtos que estão na categoria A.\n    1. Você deverá retornar apenas 2 colunas nessa consulta: Nome do Produto e Peso.\n    2. Renomeie essas colunas com nomes mais intuitivos.\n    3. Ordene esses produtos do mais pesado para o mais leve.\n    - **Resposta Exercício 3**\n        \n        ```sql\n        -- Exiba todos os produtos com peso maior que 100kg. traga apenas coluna de nome e peso\n        SELECT\n        \tProductName AS Produto,\n        \tWeight\t\tAS Peso\n        FROM\n        \tDimProduct\n        WHERE \n        \tWeight \u003e 100\n        ORDER BY\n        \tWeight DESC\n        ```\n        \n        ![Untitled](img/Untitled%208.png)\n        \n4. Você foi alocado para criar um relatório das lojas registradas atualmente na Contoso.\n    1. a) Descubra quantas lojas a empresa tem no total. Na consulta que você deverá fazer à tabela DimStore, retorne as seguintes informações: StoreName, OpenDate, EmployeeCount\n    2. Renomeeie as colunas anteriores para deixar a sua consulta mais intuitiva.\n    3. Dessas lojas, descubra quantas (e quais) lojas ainda estão ativas.\n        - **Resposta Exercício 4**\n            \n            ```sql\n            -- Quantas lojas estão registradas na Contoso hoje?\n            SELECT \n            \tStoreName\t\tAS 'Nome da Loja',\n            \tOpenDate\t\tAS 'Data de Abertura',\t\n            \tEmployeeCount\tAS 'Número de funcionários'\n            FROM\n            \tDimStore\n            --WHERE Status = 'On' --294 lojas ativas\n            --WHERE Status = 'Off' --12 lojas ativas\n            \n            /* A Contoso possui na data atual 306 lojas cadastras, \n            \tsendo deste montante 264 ativas e 12 inativas.\n            */\n            \n            --SELECT TOP(10) * FROM DIMSTORE\n            ```\n            \n5.  O gerente da área de controle de qualidade notificou à Contoso que todos os produtos Home Theater da marca Litware, disponibilizados para venda no dia 15 de março de 2009, foram identificados com defeitos de fábrica.\nO que você deverá fazer é identificar os ID’s desses produtos e repassar ao gerente para que ele possa notificar as lojas e consequentemente solicitar a suspensão das vendas desses produtos.\n    - **Resposta Exercício 5**\n        \n        ```sql\n        -- Informe uma lista de IDs dos produtos Home Theater da Litware, vendidos a partir de 15/03/2009 para serem retirados da venda\n        --SELECT TOP(10) * FROM DimProduct\n        SELECT \n        \t*\n        FROM \n        \tDimProduct\n        WHERE\n        \tBrandName = 'Litware' AND \n        \t--ProductDescription LIKE '%Home Theater%' AND\n        \tAvailableForSaleDate = '20090315'\n        -- filtro para 'home theather' quebra a consulta por conta do formato do campo de data (time series)\n        \n        /*Dos produtos com defeito, precisam ser retirados da venda os cujos ID são: 198, 214 e 230*/\n        ```\n        \n6. Imagine que você precise extrair um relatório da tabela DimStore, com informações de lojas. Mas você precisa apenas das lojas que não estão mais funcionando atualmente.\n    1. Utilize a coluna de Status para filtrar a tabela e trazer apenas as lojas que não estão mais funcionando.\n    2. Agora imagine que essa coluna de Status não existe na sua tabela. Qual seria a outra forma que você teria de descobrir quais são as lojas que não estão mais funcionando?\n    - **Resposta Exercício 6**\n        \n        ```sql\n        SELECT \n        \t*\n        FROM\n        \tDimStore\n        --WHERE Status = 'Off'\n        WHERE CloseReason IS NOT NULL\n        \n        -- SELECT DISTINCT\tCloseReason FROM DimStore\n        -- NULL, Realocation, Store\n        \n        /*Caso não existisse a coluna status, para consultar as lojas inativas poderímos usar o parâmetro não nulo,\n        pois se a razão de fechamento estiver preenchida, significa que a loja foi fechada*/\n        ```\n        \n7. De acordo com a quantidade de funcionários, cada loja receberá uma determinada quantidade de máquinas de café. As lojas serão divididas em 3 categorias: \n    1. CATEGORIA 1: De 1 a 20 funcionários -\u003e 1 máquina de café\n    2. CATEGORIA 2: De 21 a 50 funcionários -\u003e 2 máquinas de café\n    3. CATEGORIA 3: Acima de 51 funcionários -\u003e 3 máquinas de café\n        1. (Identifique, para cada caso, quais são as lojas de cada uma das 3 categorias acima (basta fazer uma verificação).)\n    - **Resposta Exercício 7**\n        \n        ```sql\n        SELECT * FROM DimStore\n        ORDER BY EmployeeCount\n        \n        -- quantas máquinas de café cada loja receberá?\n        -- categoria A: de 01-20 funcionários\n        SELECT\n        \tStoreName,\n        \tEmployeeCount\n        FROM\n        \tDimStore\n        WHERE \n        \t-- CATEGORIA A\n        \tEmployeeCount BETWEEN 1 AND 20\n        \t\n        \t-- CATEGORIA B\n        \t--EmployeeCount BETWEEN 21 AND 50\n        \n        \t--CATEGORIA C\n        \t--EmployeeCount \u003e= 51\n        ORDER BY EmployeeCount ASC\n        \n        /*\n        Total de Lojas: 306\n        \n        Lojas por categorias\n        Categoria A: 75  lojas\n        Categoria B: 187 lojas\n        Categoria C: 43  lojas\n        */\n        ```\n        \n8. A empresa decidiu que todas as televisões de LCD receberão um super desconto no próximo mês. O seu trabalho é fazer uma consulta à tabela DimProduct e retornar os ID’s, Nomes e Preços de todos os produtos LCD existentes.\n    - **Resposta Exercício 8**\n        \n        ```sql\n        -- Exiba todos os produtos LCD (ID, nome e preços)\n        SELECT \n        \tProductKey\t\t\tAS 'ID',\n        \tProductDescription\tAS 'Produto',\n        \tUnitPrice\t\t\tAS 'Preço'\n        FROM\n        \tDimProduct\n        WHERE\n        \tProductDescription LIKE '%LCD%'\n        ORDER BY\n        \tUnitPrice DESC\n        ```\n        \n        ![Untitled](img/Untitled%209.png)\n        \n9. Faça uma lista com todos os produtos das cores: Green, Orange, Black, Silver e Pink. Estes produtos devem ser exclusivamente das marcas: Contoso, Litware e Fabrikam.\n    - **Resposta Exercício 9**\n        \n        ```sql\n        -- Liste os produtos Green, Orange, Black, Silver e Pink das Marcas Contoso, Litware e Fabrikam\n        SELECT \n        \t*\n        FROM\n        \tDimProduct\t\n        WHERE \n        \tColorName IN ('Green', 'Orange', 'Black', 'Silver', 'Pink') AND\n        \tBrandName IN ('Contoso', 'Litware', 'Fabrikam')\n        ORDER BY\n        \tColorName\n        ```\n        \n10. A empresa possui 15 produtos da marca Contoso, da cor Silver e com um UnitPrice entre 10 e 30. Descubra quais são esses produtos e ordene o resultado em ordem decrescente de acordo com o preço (UnitPrice).\n    - **Resposta Exercício 10**\n        \n        ```sql\n        SELECT\n        \tProductName AS 'Produto',\n        \tUnitPrice\tAS 'Preço'\n        FROM\n        \tDimProduct\n        WHERE\n        \tBrandName = 'Contoso'\tAND\n        \tColorName = 'Silver'\tAND\n        \tUnitPrice BETWEEN 10 AND 30\n        ORDER BY\n        \tUnitPrice DESC\n        ```\n\n\u003c/details\u003e    \n\n---\n\n[🏠 Retornar ao índice](#table-of-contents)\n\n## Funções de Agregação\n\n### SUM\n\n\u003e Retorna o total de uma determinada coluna\n\n```sql\nSELECT\n\tSUM(SalesQuantity) AS 'Total Vendido',\n\tSUM(ReturnQuantity) AS 'Total Devolvido'\n\nFROM\n\tFactSales\n```\n\n### COUNT\n\n\u003e Retorna a contagem de valores ou dados de uma tabela\n\u003e \n\n```sql\nSELECT\n\tCOUNT(*) AS 'Total de produtos'\nFROM\n\tDimProduct\n\n--observe sempre qual coluna está contando\n```\n\n### COUNT DISTINCT\n\n\u003e Retorna a contagem de valores únicos\n\u003e \n\n```sql\nSELECT\n\tCOUNT(DISTINCT BrandName) AS 'Total Marcas Cadastradas'\nFROM\n\tDimProduct\n```\n\n### MIN E MAX\n\n\u003e Retorna menor e maior valor\n\u003e \n\n```sql\n--SELECT TOP(10) * FROM DimProduct\nSELECT\n\tMAX(UnitPrice) AS 'Maior valor',\n\tMIN(UnitPrice) AS 'Menor valor'\nFROM\n\tDimProduct\n```\n\n### AVG\n\n\u003e Retorna a média dos dados\n\u003e \n\n```sql\n--quanto é a renda média anual dos clientes cadastrados?\nSELECT\n\tAVG(YearlyIncome) 'Média da Renda Anual'\nFROM\n\tDimCustomer\n```\n\n### Exercícios\n\n\u003cdetails\u003e\n\u003csummary\u003e\u003cstrong\u003eExercícios e respostas\u003c/strong\u003e\u003c/summary\u003e\n\n1. O gerente comercial pediu a você uma análise da Quantidade Vendida e Quantidade Devolvida para o canal de venda mais importante da empresa: Store.\nUtilize uma função SQL para fazer essas consultas no seu banco de dados. Obs: Faça essa análise considerando a tabela FactSales.\n    - **Exercício 1**\n        \n        ```sql\n        SELECT \n        \tSUM(SalesQuantity)\tAS 'Quantidade de Produtos Vendidos',\n        \tSUM(ReturnQuantity)\tAS 'Qauntidade de Produtos Devolvidos'\n        FROM \n        \tFactSales\n        ```\n        \n2. Uma nova ação no setor de Marketing precisará avaliar a média salarial de todos os clientes da empresa, mas apenas de ocupação Professional. Utilize um comando SQL para atingir esse resultado.\n    - **Exercício 2**\n        \n        ```sql\n        SELECT \n        \tAVG(YearlyIncome) AS 'Média Salarial dos clientes que são profissionais'\n        FROM \n        \tDimCustomer\n        WHERE\n        \tOccupation = 'Professional'\n        ```\n        \n3. Você precisará fazer uma análise da quantidade de funcionários das lojas registradas na empresa. O seu gerente te pediu os seguintes números e informações:\n    1. Quantos funcionários tem a loja com mais funcionários?\n    2. Qual é o nome dessa loja?\n    3. Quantos funcionários tem a loja com menos funcionários?\n    4. Qual é o nome dessa loja?\n    - **Exercício 3**\n        \n        ```sql\n        --VISUALIZANDO COLUNAS DA TABELA...\n        select top(10) * from DimStore\n        \n        -- 1. Quantos funcionários tem a loja com mais funcionários?\n        -- 2. Qual é o nome dessa loja?\n        SELECT \n        \tMAX(EmployeeCount) AS \"Maior Quantidade de Funcionários\",\n        \tMIN(EmployeeCount) AS \"Menor Quantidade de Funcionários\"\n        FROM \n        \tDimStore\n        \n        -- 3. Quantos funcionários tem a loja com menos funcionários?\n        -- 4. Qual é o nome dessa loja?\n        SELECT TOP(1)\n        \tStoreName,\n        \tEmployeeCount\n        FROM \n        \tDimStore\n        WHERE \n        \tEmployeeCount IS NOT NULL\n        ORDER BY \n        \tEmployeeCount ASC\n        ```\n        \n4. A área de RH está com uma nova ação para a empresa, e para isso precisa saber a quantidade total de funcionários do sexo Masculino e do sexo Feminino.\n    1. Descubra essas duas informações utilizando o SQL.\n    2. O funcionário e a funcionária mais antigos receberão uma homenagem. Descubra as seguintes informações de cada um deles: Nome, E-mail, Data de Contratação.\n    - **Exercício 4**\n        \n        ```sql\n        --VISUALIZANDO COLUNAS DA TABELA...\n        select top(10) * from DimEmployee\n        \n        /*total de funcionários do sexo Masculino e do sexo Feminino.*/\n        \n        SELECT\n        \tCOUNT(Gender)\n        FROM \n        \tDimEmployee\n        --WHERE Gender = 'M'\n        WHERE Gender = 'F'\n        \n        --total: 293\n        -- masc: 206\n        -- fem.:  87\n        \n        -- Funcionária mais velho (tempo de casa)\n        -- FEM - Terry\tjolynn0@contoso.com\t1998-01-26\n        -- MASC - Kim\tguy1@contoso.com\t1996-07-31\n        \n        SELECT TOP(1)\n        \tFirstName AS \"Nome\",\n        \tEmailAddress AS \"Email\",\n        \tHireDate AS \"Contratado em\"\n        FROM\n        \tDimEmployee\n        --WHERE Gender = 'F'\n        WHERE \n        \tGender = 'M'\n        ORDER BY\n        \tHireDate ASC\n        ```\n        \n5. Agora você precisa fazer uma análise dos produtos. Será necessário descobrir as seguintes informações (fazer isso em uma mesma consulta):\n    1. Quantidade distinta de cores de produtos.\n    2. Quantidade distinta de marcas\n    3. Quantidade distinta de classes de produto\n    - **Exercício 5**\n        \n        ```sql\n        SELECT TOP(10) * FROM DimProduct\n        \n        SELECT\n        \tCOUNT(DISTINCT ColorID)\t\tAS CORES,\n        \tCOUNT(DISTINCT BrandName)\tAS MARCAS,\n        \tCOUNT(DISTINCT ClassName)\tAS CLASSES\n        FROM DimProduct\n        ```\n        \n        ![Untitled](img/Untitled%2010.png)\n\n\u003c/details\u003e        \n\n---\n\n[🏠 Retornar ao índice](#table-of-contents)\n\n## GROUP BY\n\n\u003e Dentro do SELECT, devemos declarar qual a coluna desejamos, e qual métrica será utilizada\n\u003e \n\nO GROUP BY é usado junto com funções de agregação (COUNT(), MAX(), MIN(), SUM(), AVG())\npara agrupar valores de acordo com uma ou mais colunas.\n\nAo invés de apenas contar quantas linhas a tabela possui, o group by permite que tenhamos um detalhamento dos dados.\n\n```sql\nSELECT\n\tBrandName AS \"Marca\",\n\tCOUNT(*)  AS \"Quant. Total\"\nFROM \n\tDimProduct\nGROUP BY BrandName\n```\n\n```sql\n-- quantos funcionários agrupados por tipo de loja existem?\nSELECT \n\tStoreType,\n\tSUM(EmployeeCount) AS \"total funcionários\"\nFROM \n\tDimStore\nGROUP BY\n\tStoreType\n```\n\n### GROUP BY + ORDER BY\n\n```sql\nselect \n\tStoreType, \n\tSUM(EmployeeCount) \nfrom \n\tDimStore \nGroup by StoreType\norder by SUM(EmployeeCount)\n```\n\n### GROUP BY + WHERE + ORDER BY\n\n```sql\nselect \n ColorName as 'cor',\n COUNT(*) AS 'total de produtos'\nfrom \n\tDimProduct\nwhere BrandName = 'Contoso'\ngroup by ColorName\norder by COUNT(*) desc\n```\n\n### HAVING\n\n\u003e Filtro após o agrupamento.\n\u003e \n\n```sql\nselect \n BrandName as 'Marca',\n COUNT(BrandName) AS 'total por marca'\nfrom \n\tDimProduct\ngroup by BrandName\nHAVING COUNT(BrandName) \u003e= 200\norder by COUNT(*) desc\n```\n\n![Untitled](img/Untitled%2011.png)\n\n- **Where:** Filtra a tabela original, **antes do agrupamento**\n- **Having:** Filtra a tabela **após o agrupamento**\n\n### Exercícios\n\n\u003cdetails\u003e\n\u003csummary\u003e\u003cstrong\u003eExercícios e respostas\u003c/strong\u003e\u003c/summary\u003e\n\n1. Realize as consultas tabela de FactSales:\n    1. Faça um resumo da quantidade vendida (SalesQuantity) de acordo com o canal de vendas (channelkey).\n    2. Faça um agrupamento mostrando a quantidade total vendida (SalesQuantity) e quantidade total devolvida (Return Quantity) de acordo com o ID das lojas (StoreKey).\n    3. Faça um resumo do valor total vendido (SalesAmount) para cada canal de venda, mas apenas para o ano de 2007.\n    - **Exercício 1**\n        \n        ```sql\n        -- verifica colunas da tabela...\n        select top(10) * from FactSales\n        \n        -- A\n        SELECT\n        \tchannelKey,\n        \tSUM(SalesQuantity) AS 'Quant Vendas'\n        FROM \n        \tFactSales\n        GROUP BY channelKey\n        \n        --B \n        SELECT\n        \tchannelKey,\n        \tSUM(SalesQuantity) AS 'Quant Vendas',\n        \tSUM(ReturnQuantity) AS 'Quant Devolvida'\n        \n        FROM \n        \tFactSales\n        GROUP BY channelKey\n        \n        -- C\n        SELECT\n        \tchannelKey,\n        \tSUM(SalesAmount) AS 'Total Vendas'\n        \t\n        FROM \n        \tFactSales\n        WHERE DateKey BETWEEN '01/01/2007' AND '31/12/2007'\n        GROUP BY channelKey\n        ```\n        \n2. Você precisa fazer uma análise de vendas por produtos. O objetivo final é descobrir o valor total vendido (SalesAmount) por produto (ProductKey).\n    1. A tabela final deverá estar ordenada de acordo com a quantidade vendida e, além disso, mostrar apenas os produtos que tiveram um resultado final de vendas maior do que $5.000.000.\n    2. Faça uma adaptação no exercício anterior e mostre os Top 10 produtos com mais vendas. Desconsidere o filtro de $5.000.000 aplicado.\n    - **Exercício 2**\n        \n        ```sql\n        -- verifica colunas da tabela...\n        select top(10) * from FactSales\n        \n        -- A\n        SELECT \n         ProductKey AS 'id_Produto',\n         SUM(SalesAmount) AS 'Total_vendido'\n        FROM\n        \tFactSales\n        GROUP BY ProductKey\n        HAVING SUM(SalesAmount) \u003e 5000000\n        ORDER BY SUM(SalesAmount) DESC\n        \n        -- B\n        SELECT TOP(10)\n         ProductKey AS 'id_Produto',\n         SUM(SalesAmount) AS 'Total_vendido'\n        FROM\n        \tFactSales\n        GROUP BY ProductKey\n        ORDER BY SUM(SalesAmount) DESC\n        ```\n        \n3. Realize as consultas tabela factionLineSales:\n    1. Você deve fazer uma consulta à tabela FactOnlineSales e descobrir qual é o ID (CustomerKey) do cliente que mais realizou compras online (de acordo com a coluna SalesQuantity).\n    2. Feito isso, faça um agrupamento de total vendido (SalesQuantity) por ID do produto e descubra quais foram os top 3 produtos mais comprados pelo cliente da letra a).\n    - **Exercício 3**\n        \n        ```sql\n        -- verifica colunas da tabela...\n        select top(10) * from FactOnlineSales\n        \n        -- A\n        SELECT TOP(1)\n        \tCustomerKey,\n        \tSUM(SalesQuantity) AS 'total comprado'\n        FROM\n        \tFactOnlineSales\n        GROUP BY CustomerKey\n        ORDER BY SUM(SalesQuantity) DESC\n        \n        -- B\n        SELECT TOP(3)\n        \tProductKey,\n        \tSUM(SalesQuantity) AS 'total comprado'\n        FROM\n        \tFactOnlineSales\n        GROUP BY ProductKey\n        ORDER BY SUM(SalesQuantity) DESC\n        ```\n        \n4. Realize as consultas tabela dimProduct:\n    1. Faça um agrupamento e descubra a quantidade total de produtos por marca.\n    2. Determine a média do preço unitário (UnitPrice) para cada ClassName.\n    3. Faça um agrupamento de cores e descubra o peso total que cada cor de produto possui.\n    - **Exercício 4**\n        \n        ```sql\n        -- verifica colunas da tabela...\n        select top(10) * from DimProduct\n        \n        -- A\n        SELECT\n        \tBrandName,\n        \tCOUNT(BrandName) AS 'total'\n        FROM\n        \tDimProduct\n        GROUP BY BrandName\n        ORDER BY BrandName\n        \n        --B\n        SELECT\n        \tClassName,\n        \tAVG(UnitPrice)\n        FROM\n        \tDimProduct\n        GROUP BY ClassName\n        \n        -- C\n        SELECT\n        \tColorName,\n        \tSUM(Weight) AS 'Peso total'\n        FROM\n        \tDimProduct\n        GROUP BY ColorName\n        ORDER BY SUM(Weight) DESC\n        ```\n        \n5. Você deverá descobrir o peso total para cada tipo de produto (StockTypeName). A tabela final deve considerar apenas a marca ‘Contoso’ e ter os seus valores classificados em ordem decrescente.\n    - **Exercício 5**\n        \n        ```sql\n        -- verifica colunas da tabela...\n        select top(10) * from DimProduct\n        \n        SELECT\n        \tStockTypeName,\n        \tSUM(Weight)\n        FROM \n        \tDimProduct\n        WHERE BrandName = 'Contoso'\n        GROUP BY StockTypeName\n        ```\n        \n        ![Untitled](img/Untitled%2012.png)\n        \n6. Você seria capaz de confirmar se todas as marcas dos produtos possuem à disposição todas as 16 opções de cores?\n    - **Exercício 6**\n        \n        ```sql\n        -- verificar dados da tabela --\n        SELECT top(10) *FROM DimProduct;\n        \n        --verifica se todas as marcar possuem 16 cores--\n        SELECT \n        \tBrandName AS 'marca', \n        \tCount(Distinct ColorID) AS 'quant_cores'\n        FROM DimProduct\n        GROUP BY BrandName\n        ORDER BY  quant_cores DESC \n        \n        --verifica quais cores determinada marca possui--\n        SELECT \n        \tdistinct(ColorName)\n        FROM DimProduct\n        WHERE BrandName = 'Tailspin Toys'\n        ORDER BY ColorName\n        ```\n        \n7. Faça um agrupamento para saber o total de clientes de acordo com o Sexo e também a média salarial de acordo com o Sexo. Corrija qualquer resultado “inesperado” com os seus conhecimentos em SQL. (tabela DimCustomer)\n    - **Exercício 7**\n        \n        ```sql\n        -- verificar dados da tabela --\n        SELECT top(10) * FROM DimCustomer;\n        \n        --tabela trás clientes PF e PJ--\n        --clientes pj possuem a informação null no campo sexo --\n        \n        SELECT \n        \tGender as 'sexo',\n        \tCOUNT(Gender) as 'quant_total_clientes',\n        \tAVG(YearlyIncome) as '´media_salarial_anual'\n        FROM DimCustomer\n        WHERE Gender is not null\n        GROUP BY Gender\n        ```\n        \n8. Faça um agrupamento para descobrir a quantidade total de clientes e a média salarial de acordo com o seu nível escolar. Utilize a coluna Education da tabela DimCustomer para fazer esse agrupamento.\n    - **Exercício 8**\n        \n        ```sql\n        -- verificar dados da tabela --\n        SELECT top(10) * FROM DimCustomer;\n        \n        --tabela trás clientes PF e PJ--\n        --clientes pj possuem a informação null no campo sexo --\n        \n        SELECT \n        \tEducation as 'nivel_escolarizacao',\n        \tCOUNT(Education) as 'quant_total_clientes',\n        \tAVG(YearlyIncome) as '´media_salarial_anual'\n        FROM DimCustomer\n        WHERE Gender is not null\n        GROUP BY Education\n        ```\n        \n9. Faça uma tabela resumo mostrando a quantidade total de funcionários de acordo com o Departamento (DepartmentName). Importante: Você deverá considerar apenas os funcionários ativos. (Tabela Dimemployee)\n    - **Exercício 9**\n        \n        ```sql\n        -- verificar dados da tabela --\n        SELECT top(10) * FROM DimEmployee;\n        \n        --tabela trás clientes PF e PJ--\n        --clientes pj possuem a informação null no campo sexo --\n        \n        SELECT \n        \tDepartmentName as 'departamento',\n        \tCOUNT(DepartmentName) as 'total'\n        FROM DimEmployee\n        WHERE EndDate IS NULL\n        GROUP BY DepartmentName\n        ORDER BY total\n        ```\n        \n10. Faça uma tabela resumo mostrando o total de VacationHours para cada cargo (Title). Você deve considerar apenas as mulheres, dos departamentos de Production, Marketing, Engineering e Finance, para os funcionários contratados entre os anos de 1999 e 2000.\n    - **Exercício 10**\n        \n        ```sql\n        -- verificar dados da tabela --\n        SELECT top(10) * FROM DimEmployee;\n        \n        --tabela trás clientes PF e PJ--\n        --clientes pj possuem a informação null no campo sexo --\n        \n        SELECT \n        \tTitle AS 'cargo',\n        \tSUM(VacationHours) as 'horas_férias_pendentes'\n        FROM DimEmployee\n        WHERE \n        \tGender = 'F' AND \n        \tDepartmentName IN ( 'Production', 'Marketing', 'Engineering', 'Finance') AND\n        \tHireDate BETWEEN '1999-01-01' AND '2000-12-31'\n        GROUP BY Title\n        ```\n \u003c/details\u003e       \n\n---\n\n[🏠 Retornar ao índice](#table-of-contents)\n\n## JOINS no SQL\n\n**Porque precisamos do join?**\n\n- para buscar informações em tabelas diversas e trazer em uma única visualização (relacionar diversas tabela por meio **de colunas em comum**)\n\n**Por que não se criam todas as tabelas juntas, com todas as informações?**\n\n- Porque quanto mais informações existem na tabela, mais processamento computacional é exigido, o que inviabiliza o uso e a consulta do banco de dados.\n\n### Chave Primária e Chave Estrangeira\n\n**Chave primária** é a coluna que identifica informações distindas em uma tabela\n\n**Chave Estrangeira** é a coluna que permite o relacionamento de uma segunda tabela com a chave primária de outra tabela\n\n![Untitled](img/Untitled%2013.png)\n\n### Tabela Fato e Tabela Dimensão\n\nTabela Dimensão é a tabela que contém características de um determinado elemento. Nessa tabela nenhum dos elementos principais irá se repetir, é onde encontramos as chaves primárias.\n\nTabela Fato é uma tabela que registra acontecimentos (fatos) de uma empresa/negócio ao longo do tempo. Geralmente é uma tabela com milhares de linhas, composta essencialmente por colunas de ID, usadas para buscar informações complementares de uma tabela dimensão, por meio de chaves estrangeiras.\n\n![Untitled](img/Untitled%2014.png)\n\nNão necessariamente é necessário fazer relação entres tabelas dimensão e tabelas fato.\n\n### Tipos de JOIN\n\nExistem 7 tipos, mas o que se usa mesmo são:\n\n- LEFT OUTER JOIN (verifica dados que existem em uma tabela e que não exista em outra)\n- INNER JOIN (verifica dados que existem nas duas tabela.\n\n![Untitled](img/Untitled%2015.png)\n\n- **Criar tabelas adicionais para testar os JOINs**\n    \n    ```sql\n    \n    CREATE DATABASE Joins\n    GO\n    \n    USE Joins\n    \n    CREATE TABLE produtos(\n    \tid_produto int,\n    \tnome_produto varchar(30),\n    \tid_subcategoria int);\n    \n    INSERT INTO produtos (id_produto, nome_produto, id_subcategoria)\n    VALUES\n    (1, 'Fone bluetooth', 5),\n    (2, 'PS6', 6),\n    (3, 'Notebook', 2),\n    (4, 'iPhone 11', 1),\n    (5, 'Moto G9', 1)\n    \n    /*********** Criando tabela de subcategorias   ***************/\n    \n    CREATE TABLE subcategoria(\n    \tid_subcategoria int,\n    \tnome_subcategoria varchar(30))\n    \n    INSERT INTO subcategoria (id_subcategoria, nome_subcategoria)\n    VALUES\n    (1, 'Celular'),\n    (2, 'Notebook'),\n    (3, 'Camera Digital'),\n    (4, 'Televisão'),\n    (5, 'Fone de ouvido')\n    ```\n    \n\n### **Exemplo dos JOINS**\n\n```sql\nSELECT \n\tProductKey,\n\tProductName,\n\tProductSubcategoryKey\nFROM DimProduct;\n\nSELECT\n\tProductSubcategoryKey,\n\tProductSubcategoryName\nFROM DimProductSubcategory;\n```\n\n![Untitled](img/Untitled%2016.png)\n\nINNER JOIN\n\n```sql\nSELECT \n\tProductKey,\n\tProductName,\n\tDimProduct.ProductSubcategoryKey,\n\tProductSubcategoryName\nFROM \n\tDimProduct\nINNER JOIN DimProductSubcategory\n\tON DimProduct.ProductSubcategoryKey = DimProductSubcategory.ProductSubcategoryKey\n```\n\n![Untitled](img/Untitled%2017.png)\n\nLEFT JOIN E RIGHT JOIN\n\n```sql\n/*\no LEFT JOIN trás o mesmo resultado do inner join, \no que signigica que todos os itens da tabela de produto\npossuem uma referência na tabela de subcategoria\n*/\n\n/*\nO RIGTH JOIN trás por sua vez resultados a mais do que o LEFT JOIN\no que significa que algumas subcategorias não possuem\nnenhum produto cadastrado.\n*/\n\nSELECT \n\tProductKey,\n\tProductName,\n\tDimProduct.ProductSubcategoryKey,\n\tProductSubcategoryName\nFROM \n\tDimProduct\nRIGHT JOIN DimProductSubcategory\nON DimProduct.ProductSubcategoryKey = DimProductSubcategory.ProductSubcategoryKey\n```\n\n![Untitled](img/Untitled%2018.png)\n\n**Múltiplos Joins**\n\n```sql\n-- verifica dados das tabelas para análise\n\n--produtos\nSELECT \n\tProductKey,\n\tProductName,\n\tProductSubcategoryKey\nFROM \n\tDimProduct;\n\n--subcategorias\nSELECT\n\tProductSubcategoryKey,\n\tProductSubcategoryName\nFROM \n\tDimProductSubcategory;\n\n--categorias\nSELECT\n\tProductCategoryKey, ProductCategoryName\nFROM\n\tDimProductCategory\n```\n\n![Untitled](img/Untitled%2019.png)\n\nA consulta para trazer o produto e o nome da subcategoria e categoria ficaria assim:\n\n```sql\nSELECT \n\tProductKey,\n\tProductName,\n\tDimProduct.ProductSubcategoryKey,\n\tProductSubcategoryName,\n\tProductCategoryName\nFROM \n\tDimProduct\nINNER JOIN DimProductSubcategory\n\tON DimProduct.ProductSubcategoryKey = DimProductSubcategory.ProductSubcategoryKey\n\t\tINNER JOIN DimProductCategory\n\t\t\tON DimProductSubCategory.ProductCategoryKey = DimProductCategory.ProductCategoryKey\n```\n\n![Untitled](img/Untitled%2020.png)\n\n### Exercícios\n\n\u003cdetails\u003e\n\u003csummary\u003e\u003cstrong\u003eExercícios e respostas\u003c/strong\u003e\u003c/summary\u003e\n\n*Os Joins têm como principal objetivo deixar as tabelas mais informativas, permitindo buscar dados de uma tabela para outra, de acordo com uma coluna em comum que permita essa relação. Dito isso, faça os seguintes exercícios:*\n\n1. Utilize o INNER JOIN para trazer os nomes das subcategorias dos produtos, da tabela DimProductSubcategory para a tabela DimProduct\n    - **Exercício 1**\n        \n        ```sql\n        --VERIFICA DADOS DAS TABELEAS\n        SELECT TOP(10) * FROM DimProductSubcategory;\n        SELECT TOP(10) * FROM DimProduct;\n        \n        SELECT \n        \tProductKey AS 'produto_id',\n        \tProductName AS 'produto_nome',\n        \tProductSubcategoryName AS 'subcategoria'\n        FROM\n        \tDimProduct\n        INNER JOIN DimProductSubcategory\n        \tON DimProduct.ProductSubcategoryKey = DimProductSubcategory.ProductSubcategoryKey\n        ```\n        \n2. Identifique uma coluna em comum entre as tabelas DimProductSubcategory e DimProductCategory. Utilize essa coluna para complementar informações na tabela DimProductSubcategory a partir da DimProductCategory. Utilize o LEFT JOIN.\n    - **Exercício 2**\n        \n        ```sql\n        --VERIFICA DADOS DAS TABELEAS\n        SELECT TOP(10) * FROM DimProductSubcategory;\n        SELECT TOP(10) * FROM DimProductCategory;\n        \n        SELECT\n        \tProductSubcategoryKey AS 'subcategoria_id',\n        \tProductSubcategoryName AS 'subcategoria',\n        \tProductCategoryName AS 'categoria'\n        FROM\n        \tDimProductSubcategory\n        LEFT JOIN\n        \tDimProductCategory\n        \t\tON DimProductSubcategory.ProductSubcategoryKey = DimProductCategory.ProductCategoryKey\n        ```\n        \n3. Para cada loja da tabela DimStore, descubra qual o Continente e o Nome do País associados (de acordo com DimGeography). Seu SELECT final deve conter apenas as seguintes colunas: StoreKey, StoreName, EmployeeCount, ContinentName e RegionCountryName. Utilize o LEFT JOIN neste exercício.\n    - **Exercício 3**\n        \n        ```sql\n        --VERIFICA DADOS DAS TABELEAS\n        SELECT TOP(10) * FROM DimStore;\n        SELECT TOP(10) * FROM DimGeography;\n        \n        SELECT\n        \tStoreKey AS 'loja_ID',\n        \tStoreName AS 'loja',\n        \tEmployeeCount AS 'quant_funcionarios',\n        \tContinentName AS 'continente',\n        \tRegionCountryName AS 'país'\n        FROM\n        \tDimStore\n        LEFT JOIN DimGeography\n        \tON DimStore.GeographyKey = DimGeography.GeographyKey\n        ```\n        \n4. Complementa a tabela DimProduct com a informação de ProductCategoryDescription. Utilize o LEFT JOIN e retorne em seu SELECT apenas as 5 colunas que considerar mais relevantes.\n    - **Exercício 4**\n        \n        ```sql\n        --VERIFICA DADOS DAS TABELEAS\n        SELECT TOP(10) * FROM DimProduct ;\n        SELECT TOP(10) * FROM DimProductCategory;\n        SELECT TOP(10) * from DimProductSubcategory;\n        \n        SELECT\n        \tProductKey\tAS 'produto_ID',\n        \tProductName AS 'produto',\n        \tDimProductCategory.ProductCategoryDescription AS 'descrição'\n        FROM\n        \tDimProduct\n        LEFT JOIN DimProductSubcategory\n        \tON DimProduct.ProductSubcategoryKey = DimProductSubcategory.ProductSubcategoryKey\n        \t\tLEFT JOIN DimProductCategory\n        \t\t\tON DimProductSubCategory.ProductCategoryKey = DimProductCategory.ProductCategoryKey\n        ```\n        \n5. A tabela FactStrategyPlan resume o planejamento estratégico da empresa. Cada linha representa um montante destinado a uma determinada AccountKey.\n    1. Faça um SELECT das 100 primeiras linhas de FactStrategyPlan para reconhecer a tabela.\n    2. Faça um INNER JOIN para criar uma tabela contendo o AccountName para cada AccountKey da tabela FactStrategyPlan. O seu SELECT final deve conter as colunas:\n        1. StrategyPlanKey\n        2. DateKey\n        3. AccountName\n        4. Amount\n    - **Exercício 5**\n        \n        ```sql\n        SELECT\n        \tStrategyPlanKey AS 'ID_conta',\n        \tDatekey\t\t\tAS 'data compra',\n        \tDimAccount.AccountName AS 'tipo conta',\n        \tAmount AS 'valor'\n        FROM\n        \tFactStrategyPlan\n        INNER JOIN DimAccount\n        \tON FactStrategyPlan.AccountKey = DimAccount.AccountKey\n        ```\n        \n6. Vamos continuar analisando a tabela FactStrategyPlan. Além da coluna AccountKey que identifica o tipo de conta, há também uma outra coluna chamada ScenarioKey. Essa coluna possui a numeração que identifica o tipo de cenário: Real, Orçado e Previsão. Faça um INNER JOIN para criar uma tabela contendo o ScenarioName para cada ScenarioKey da tabela  FactStrategyPlan. O seu SELECT final deve conter as colunas:\n    1. StrategyPlanKey\n    2. DateKey\n    3. ScenarioName\n    4. Amount\n    - **Exercício 6**\n        \n        ```sql\n        --VERIFICA DADOS DAS TABELEAS\n        SELECT TOP(100) * FROM FactStrategyPlan ;\n        SELECT TOP(10) * FROM DimScenario;\n        \n        SELECT\n        \tStrategyPlanKey\tAS 'ID_conta',\n        \tDatekey\t\t\tAS 'data compra',\n        \tScenarioName\tAS 'cenário',\n        \tAmount\t\t\tAS 'valor'\n        FROM\n        \tFactStrategyPlan\n        INNER JOIN DimScenario\n        \tON FactStrategyPlan.ScenarioKey = DimScenario.ScenarioKey\n        ```\n        \n7. Algumas subcategorias não possuem nenhum exemplar de produto. Identifique que subcategorias são essas\n    - **Exercício 7**\n        \n        ```sql\n        --VERIFICA DADOS DAS TABELEAS\n        SELECT TOP(10) * FROM DimProduct ;\t\t\t--\u003e ESQUERDA\n        SELECT TOP(10) * FROM DimProductSubcategory;--\u003e DIREITA\n        \n        SELECT\n        --DimProduct.ProductSubcategoryKey AS 'ID_subcategoria',\n        --ProductName AS 'produto',\n        ProductSubcategoryName AS 'categoria'\n        FROM\n        DimProduct\n        RIGHT JOIN DimProductSubcategory\n        ON DimProduct.ProductSubcategoryKey = DimProductSubcategory.ProductSubcategoryKey\n        WHERE ProductName IS NULL\n        \n        /*\n        Categorias que não possuem nenhum produto: Radio, Computer Setup \u0026 Service, \n        Speakers, Film Cameras, Audio Books, Headphones, Netbooks, Recorder,\n        Music CD, Games Accessories, TV \u0026 Video Accessories, Audio Accessories\n        */\n        ```\n        \n8. A tabela abaixo mostra a combinação entre Marca e Canal de Venda, para as marcas Contoso, Fabrikam e Litware. Crie um código SQL para chegar no mesmo resultado.\n    1. \n    \n    ![Untitled](img/Untitled%2021.png)\n    \n    - **Execício 8**\n        \n        ```sql\n        -- Visão geral dos dados\n        SELECT * FROM DimChannel;\n        \n        SELECT\n        \tDISTINCT\n        \tBrandName,\n        \tChannelName\n        FROM\n        \tDimProduct CROSS JOIN DimChannel\n        WHERE \n        \tBrandName IN ('Contoso', 'Fabrikam', 'Litware')\n        ```\n        \n9. Neste exercício, você deverá relacionar as tabelas FactOnlineSales com DimPromotion. Identifique a coluna que as duas tabelas têm em comum e utilize-a para criar esse relacionamento. Retorne uma tabela contendo as seguintes colunas:\n    1. OnlineSalesKey\n    2. DateKey\n    3. PromotionName\n    4. SalesAmount\n        1. A sua consulta deve considerar apenas as linhas de vendas referentes a produtos com desconto (PromotionName \u003c\u003e ‘No Discount’). Além disso, você deverá ordenar essa tabela de acordo com a coluna DateKey, em ordem crescente.\n    - **Exercício 9**\n        \n        ```sql\n        --Visão geral dos dados\n        SELECT TOP(10) * FROM FactOnlineSales;\n        SELECT TOP(10) * FROM DimPromotion;\n        \n        SELECT TOP (1000)\n        \tOnlineSalesKey,\n        \tDateKey,\n        \tPromotionName,\n        \tSalesAmount\n        FROM\n        \tFactOnlineSales\n        INNER JOIN DimPromotion\n        \tON FactOnlineSales.PromotionKey = DimPromotion.PromotionKey\n        WHERE\n        \tPromotionName \u003c\u003e 'No Discount'\n        ORDER BY\n        \tDateKey ASC\n        ```\n        \n10. A tabela abaixo é resultado de um Join entre a tabela FactSales e as tabelas: DimChannel, DimStore e DimProduct. Recrie esta consulta e classifique em ordem crescente de acordo com SalesAmount.\n    ![Untitled](img/Untitled%2022.png)\n    \n    - **Exercício 10**\n        \n        ```sql\n        SELECT TOP (100)\n        \tSalesKey,\n        \tChannelName,\n        \tStoreName,\n        \tProductName,\n        \tSalesAmount\n        FROM\n        \tFactSales\n        INNER JOIN DimChannel\n        \tON FactSales.channelKey = DimChannel.ChannelKey\n        INNER JOIN DimStore\n        \tON FactSales.StoreKey = DimStore.StoreKey\n        INNER JOIN DimProduct\n        \tON\tFactSales.ProductKey = DimProduct.ProductKey\n        ORDER BY SalesAmount\n        ```\n\u003c/details\u003e     \n  \n---\n\n[🏠 Retornar ao índice](#table-of-contents)\n\n## JOINS + Agrupamentos\n\n### Exercícios\n\n\u003cdetails\u003e\n\u003csummary\u003e\u003cstrong\u003eExercícios e respostas\u003c/strong\u003e\u003c/summary\u003e\n\n1. Faça um resumo da quantidade vendida (Sales Quantity) de acordo com o nome do canal de vendas (ChannelName). Você deve ordenar a tabela final de acordo com SalesQuantity, em ordem decrescente.\n    1. Faça um agrupamento mostrando a quantidade total vendida (Sales Quantity) e\n    quantidade total devolvida (Return Quantity) de acordo com o nome das lojas\n    (StoreName).\n    2. Faça um resumo do valor total vendido (Sales Amount) para cada mês\n    (CalendarMonthLabel) e ano (CalendarYear).\n    - **Exercício 01**\n        \n        ```sql\n        --A\n        SELECT TOP (50)\n            ChannelName AS 'canal de venda',\n            SUM(SalesQuantity) AS 'total quant. vendas'\n        FROM\n            FactSales\n        INNER JOIN DimChannel\n            ON FactSales.ChannelKey = DimChannel.channelKey\n        GROUP BY\n            ChannelName\n        ORDER BY \n            SUM(SalesQuantity) DESC\n        \n        --B\n        SELECT TOP (50)\n            StoreName AS 'Loja',\n            SUM(SalesQuantity) AS 'total  vendas',\n            SUM(ReturnQuantity) AS 'total devoluções'\n        FROM\n            FactSales\n        INNER JOIN DimStore\n            ON FactSales.StoreKey = DimStore.StoreKey\n        GROUP BY\n            StoreName\n        ORDER BY \n            StoreName\n        \n        --C\n        --visualisando os dados\n        SELECT TOP(50)* FROM DimDate\n        \n        SELECT TOP (50)\n            CalendarYear,\n            CalendarMonthLabel,\n            SUM(SalesAmount)\n        FROM\n            FactSales\n        INNER JOIN DimDate\n            ON FactSales.DateKey = DimDate.Datekey\n        GROUP BY\n            CalendarMonthLabel, CalendarYear, CalendarMonth\n        ORDER BY \n            CalendarYear, CalendarMonth\n        ```\n        \n2. Você precisa fazer uma análise de vendas por produtos. O objetivo final é descobrir o valor\ntotal vendido (SalesAmount) por produto.\n    1. Descubra qual é a cor de produto que mais é vendida (de acordo com SalesQuantity).\n    2. Quantas cores tiveram uma quantidade vendida acima de 3.000.000.\n    - **Exercício 02**\n        \n        ```sql\n        --A\n        SELECT TOP (100)\n            ColorName,\n            SUM(SalesQuantity)\n        FROM\n            FactSales\n        INNER JOIN DimProduct\n            ON\tFactSales.ProductKey = DimProduct.ProductKey\n        GROUP BY\n            ColorName\n        ORDER BY\n            SUM(SalesQuantity) DESC\n        -- A COR MAIS VENDIDA É PRETA\n        \n        --B\n        SELECT TOP (100)\n            ColorName,\n            SUM(SalesQuantity)\n        FROM\n            FactSales\n        INNER JOIN DimProduct\n            ON\tFactSales.ProductKey = DimProduct.ProductKey\n        GROUP BY\n            ColorName\n        HAVING\n            SUM(SalesQuantity) \u003e= 3000000\n        ORDER BY\n            SUM(SalesQuantity) DESC\n        ```\n        \n3. Crie um agrupamento de quantidade vendida (SalesQuantity) por categoria do produto\n(ProductCategoryName). Obs: Você precisará fazer mais de 1 INNER JOIN, dado que a relação entre FactSales e DimProductCategory não é direta.\n    - **Exercício 03**\n        \n        ```sql\n        --analisando os dados\n        \n        SELECT TOP (10) * FROM FactSales\n        SELECT TOP (10) * FROM DimProduct\n        SELECT TOP (10) * FROM DimProductSubCategory\n        SELECT TOP (10) * FROM DimProductCategory\n        \n        SELECT TOP(100)\n            ProductCategoryName,\n            SUM(SalesQuantity) AS\t'Total unidades vendidas'\n        FROM\n            FactSales\n        INNER JOIN DimProduct\n            ON FactSales.ProductKey = DimProduct.ProductKey\n                INNER JOIN DimProductSubCategory\n                    ON DimProduct.ProductSubcategoryKey = DimProduct.ProductSubcategoryKey\n                        INNER JOIN DimProductCategory\n                            ON DimProductSubcategory.ProductCategoryKey = DimProductCategory.ProductCategoryKey\n        GROUP BY \n            ProductCategoryName\n        ORDER BY \n            [Total unidades vendidas] DESC\n        ```\n        \n\n4. Você deve fazer uma consulta à tabela FactOnlineSales e descobrir qual é o nome completo do cliente que mais realizou compras online (de acordo com a coluna SalesQuantity).\n\nb) Feito isso, faça um agrupamento de produtos e descubra quais foram os top 10 produtos mais comprados pelo cliente da letra a, considerando o nome do produto.\n\n- **Exercício 04**\n    \n    ```sql\n    \n    --A\n    --analise geral das tabelas\n    \n    SELECT TOP(10) * FROM FactOnlineSales;\n    --CustomerKey, SalesQuantity\n    SELECT TOP(10) * FROM DimCustomer;\n    --FirstName, MidleName, LastName //CustomerType\n    \n    SELECT TOP(100)\n        FactOnlineSales.CustomerKey,\n        FirstName,\n        MiddleName,\n        LastName,\n        SUM(SalesQuantity) AS 'total compras'\n    FROM\n        FactOnlineSales\n    INNER JOIN DimCustomer\n        ON FactOnlineSales.CustomerKey = DimCustomer.CustomerKey\n    WHERE\n        CustomerType = 'Person'\n    GROUP BY\n        FirstName, MiddleName, LastName, FactOnlineSales.CustomerKey\n    ORDER BY\n        SUM(SalesQuantity) DESC\n    \n    /*\n    O cliente que mais comprou foi Robert C. Long (id 7665) comprando 376 produtos\n    */\n    \n    --B\n    --analise geral das tabelas\n    \n    SELECT TOP(10) * FROM FactOnlineSales;\n    --ProductKey\n    SELECT TOP(10) * FROM DimProduct;\n    --\n    \n    SELECT TOP(10)\n        FactOnlineSales.ProductKey,\n        ProductName,\n        SUM(SalesQuantity) as 'total itens comprado'\n    FROM\n    FactOnlineSales\n    INNER JOIN DimProduct\n        ON FactOnlineSales.ProductKey = DimProduct.ProductKey\n    WHERE \n        CustomerKey = 7665\n    GROUP BY\n        ProductName, FactOnlineSales.ProductKey\n    ORDER BY\n        [total itens comprado] DESC\n    \n    /*\n    O cliente que mais comprou foi Robert C. Long (id 7665) comprando 376 produtos\n    */\n    ```\n    \n1. Faça um resumo mostrando o total de produtos comprados (Sales Quantity) de acordo com o sexo dos clientes\n    - **Exercício 05**\n        \n        ```sql\n        --analise geral das tabelas\n        \n        SELECT TOP(10) * FROM FactOnlineSales;\n        --ProductKey\n        SELECT TOP(10) * FROM DimCustomer;\n        --Gender, CustomerType\n        SELECT TOP(10) * FROM DimProduct;\n        --ProductKey, ProductName\n        \n        SELECT\n            Gender,\n            SUM(SalesAmount) AS 'total vendas realizadas',\n            ProductName,\n            DimProduct.ProductKey\n        FROM\n            FactOnlineSales\n        INNER JOIN DimCustomer\n            ON FactOnlineSales.CustomerKey = DimCustomer.CustomerKey\n        INNER JOIN DimProduct\n            ON FactOnlineSales.ProductKey = DimProduct.ProductKey\n        -- para remover valorre null, que identificam clientes PJ\n        WHERE\n            CustomerType = 'Person'\n        GROUP BY\n            Gender, ProductName, DimProduct.ProductKey\n        ```\n        \n2. Faça uma tabela resumo mostrando a taxa de câmbio média de acordo com cada CurrencyDescription. A tabela final deve conter apenas taxas entre 10 e 100.\n    - **Exercício 06**\n        \n        ```sql\n        --ANALISE GERAL DAS TABELAS\n        SELECT TOP(10) * FROM FactExchangeRate;\n        --AverageRate\n        SELECT TOP(10) * FROM DimCurrency;\n        --CurrencyDescription\n        \n        SELECT\n            --ExchangeRateKey,\n            CurrencyDescription AS 'moeda',\n            AVG(AverageRate)\tAS 'taxa câmbio média'\n        FROM\n            FactExchangeRate\n        INNER JOIN DimCurrency\n            ON FactExchangeRate.CurrencyKey = DimCurrency.CurrencyKey\n        GROUP BY\n            CurrencyDescription\n        HAVING\n            AVG(AverageRate) BETWEEN 10 AND 100\n        ```\n        \n3. Descubra o valor total na tabela FactStrategyPlan destinado aos cenários: Actual e Budge\n    - **Exercício 07**\n        \n        ```sql\n        --ANALISE GERAL DAS TABELAS\n        SELECT TOP(10) * FROM FactStrategyPlan\n        --ScenarioKey, Amount\n        SELECT TOP(10) * FROM DimScenario\n        --ScenarioKey, ScenarioName\n        \n        SELECT\n            ScenarioName,\n            SUM(Amount) AS 'total budget'\n        FROM\n            FactStrategyPlan\n        INNER JOIN DimScenario\n            ON FactStrategyPlan.ScenarioKey = DimScenario.ScenarioKey\n        WHERE\n            ScenarioName \u003c\u003e 'Forecast'\n        GROUP BY \n            ScenarioName, DimScenario.ScenarioKey\n        ORDER BY\n            [total budget] DESC\n        ```\n        \n4. Faça uma tabela resumo mostrando o resultado do planejamento estratégico por ano.\n    - **Exercício 08**\n        \n        ```sql\n        --ANALISE GERAL DAS TABELAS\n        SELECT TOP(10) * FROM FactStrategyPlan\n        --DateKey, Amount\n        SELECT TOP(10) * FROM DimDate\n        --DateKey, CalendarYear\n        \n        SELECT\n            CalendarYear\tAS 'ano',\n            SUM(Amount)\t\tAS 'total_ano'\n        FROM\n            FactStrategyPlan\n        INNER JOIN DimDate\n            ON FactStrategyPlan.Datekey = DimDate.Datekey\n        GROUP BY\n            CalendarYear\n        ```\n        \n5. Faça um agrupamento de quantidade de produtos por ProductSubcategoryName. Leve em consideração em sua análise apenas a marca Contoso e a cor Silver\n    - **Exercício 09**\n        \n        ```sql\n        --ANALISE GERAL DAS TABELAS\n        SELECT TOP(10) * FROM DimProductSubcategory\n        --ProductSubcategoryName\n        SELECT TOP(10) * FROM DimProduct\n        --ProductName\n        \n        SELECT\n            ProductSubcategoryName\tAS 'subcategoria',\n            COUNT(*)\t\t\t\tAS 'quantidade_produtos'\n        FROM\n            DimProductSubcategory\n        INNER JOIN DimProduct\n            ON DimProductSubcategory.ProductSubcategoryKey = DimProduct.ProductSubcategoryKey\n        WHERE\n            BrandName IN ('Contoso') AND ColorName = 'Silver'\n        GROUP BY\n            ProductSubcategoryName\n        ORDER BY\n            quantidade_produtos\n        ```\n        \n6. Faça um agrupamento duplo de quantidade de produtos por BrandName e ProductSubcategoryName. A tabela final deverá ser ordenada de acordo com a coluna BrandName.\n    - **Exercício 10**\n        \n        ```sql\n        --ANALISE GERAL DAS TABELAS\n        SELECT TOP(10) * FROM DimProductSubcategory\n        SELECT TOP(10) * FROM DimProduct\n        \n        SELECT\n            ProductSubcategoryName\tAS 'subcategoria',\n            BrandName\t\t\t\tAS 'marca',\n            COUNT(*)\t\t\t\tAS 'quantidade_produtos'\n        FROM\n            DimProductSubcategory\n        INNER JOIN DimProduct\n            ON DimProductSubcategory.ProductSubcategoryKey = DimProduct.ProductSubcategoryKey\n        GROUP BY\n            ProductSubcategoryName, BrandName\n        ORDER BY\n            marca\n        ```\n\u003c/details\u003e\n\n---\n\n[🏠 Retornar ao índice](#table-of-contents)\n\n### Variáveis\n\nEm breve... \n\n\n\n\n---\n\u003c!-- CONTACT --\u003e\n## Contato\n\n\u003cp align='center'\u003e\n  \u003ca href='https://github.com/jonasaacampos'\u003e\n    \u003cimg src='https://img.shields.io/badge/GitHub-100000?style=for-the-badge\u0026logo=github\u0026logoColor=white'/\u003e\n  \u003c/a\u003e\n  \u003ca href='https://www.linkedin.com/in/jonasaacampos/'\u003e\n    \u003cimg src='https://img.shields.io/badge/LinkedIn-0077B5?style=for-the-badge\u0026logo=linkedin\u0026logoColor=white'/\u003e\n  \u003c/a\u003e\n\u003c/p\u003e\n\n**Author:** Jonas Araujo de Avila Campos\n\n**Confira mais projetos: [AQUI](https://github.com/jonasaacampos)**\n\n## Crédito das imagens\n- Os ícones usados aqui são do FlatIcon.\n- As capturas de tela são de minha autoria.\n","funding_links":[],"categories":[],"sub_categories":[],"project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fjonasaacampos%2Fguia-sql","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fjonasaacampos%2Fguia-sql","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fjonasaacampos%2Fguia-sql/lists"}