Fala pessoal!

neste vídeo mostro bem rapidamente como utilizar as Window Function com as funções de classificação do T-SQL. Vamos aprofundar um pouco no módulo seguinte!

Aqui está o código (retirei do Simple Talk e da apresentação do Fabiano no SQLSAT 100, as fontes estão logo em cima!)

--cria a base de dados
/*fonte:  https://www.simple-talk.com/sql/t-sql-programming/sql-server-2012-window-function-basics/ 
outras fontes: http://blogfabiano.com/?s=sql+saturday+100 */
USE TSQL2012;
GO
 
IF OBJECT_ID('RegionalSales', 'U') IS NOT NULL
DROP TABLE RegionalSales;
GO
 
CREATE TABLE RegionalSales
(
  SalesID INT NOT NULL IDENTITY PRIMARY KEY,
  SalesGroup NVARCHAR(30) NOT NULL,
  Country NVARCHAR(30) NOT NULL,
  AnnualSales INT NOT NULL
);
GO
 
INSERT INTO RegionalSales
  (SalesGroup, Country, AnnualSales)
VALUES
  ('North America', 'United States', 22000),
  ('North America', 'Canada', 32000),
  ('North America', 'Mexico', 28000),
  ('Europe', 'France', 19000),
  ('Europe', 'Germany', 22000),
  ('Europe', 'Italy', 18000),
  ('Europe', 'Greece', 16000),
  ('Europe', 'Spain', 16000),
  ('Europe', 'United Kingdom', 32000),
  ('Pacific', 'Australia', 18000),
  ('Pacific', 'China', 28000),
  ('Pacific', 'Singapore', 21000),
  ('Pacific', 'New Zealand', 18000),
  ('Pacific', 'Thailand', 17000),
  ('Pacific', 'Malaysia', 19000),
  ('Pacific', 'Japan', 22000);
GO
-----------------------------------------------------------------------------------------------------------------------------------
--sintaxe b�sica:

<window function> OVER
  (
    [ PARTITION BY <expression> [, ... n] ] --define a janela
    [ ORDER BY <expression> [ASC|DESC] [, ... n] ] --define a ordem dos dados dentro da janela
    [ ROWS|RANGE <window frame> ] --frame, ou moldura, define em quais linhas a fun��o � calculada
  )
go


---------------------------------------------------------------------------------------------------------------
--fun��es de RANKING:
--ranking functions:
--a janela � a tabela toda:
--ORDER BY OBRIGAT�RIO:
SELECT
  SalesGroup,
  Country,
  AnnualSales,
  ROW_NUMBER() OVER(ORDER BY AnnualSales DESC) AS RowNumber,
  RANK() OVER(ORDER BY AnnualSales DESC) AS BasicRank,
  DENSE_RANK() OVER(ORDER BY AnnualSales DESC) AS DenseRank,
  NTILE(3) OVER(ORDER BY AnnualSales DESC) AS NTileRank
FROM
  RegionalSales;
 go
 --------------------------------------------------------------
 --ordena��o diferente
 SELECT
  SalesGroup,
  Country,
  AnnualSales,
  ROW_NUMBER() OVER(ORDER BY AnnualSales DESC) AS RowNumber,
  RANK() OVER(ORDER BY AnnualSales DESC) AS BasicRank,
  DENSE_RANK() OVER(ORDER BY AnnualSales DESC) AS DenseRank,
  NTILE(3) OVER(ORDER BY AnnualSales DESC) AS NTileRank
FROM
  RegionalSales
ORDER BY
  SalesGroup, Country;

 -------------------------------------------------------------
 --defini��o de janela: SALESGROUP
 SELECT
  SalesGroup,
  Country,
  AnnualSales,
  ROW_NUMBER() OVER(PARTITION BY SalesGroup
    ORDER BY AnnualSales DESC) AS RowNumber,
  RANK() OVER(PARTITION BY SalesGroup
    ORDER BY AnnualSales DESC) AS BasicRank,
  DENSE_RANK() OVER(PARTITION BY SalesGroup
    ORDER BY AnnualSales DESC) AS DenseRank,
  NTILE(3) OVER(PARTITION BY SalesGroup
    ORDER BY AnnualSales DESC) AS NTileRank
FROM
  RegionalSales;
------------------------------------------------------------
--utilizando fun��es de agrupamento em janelas:
--grouping functions:

SELECT
  SalesGroup,
  Country,
  AnnualSales,
  COUNT(AnnualSales) OVER(PARTITION BY SalesGroup) AS CountryCount,--janela � SALESGROUP, contar quantos existem
  SUM(AnnualSales) OVER(PARTITION BY SalesGroup) AS TotalSales, --soma total de vendas  por SALESGROUP
  AVG(AnnualSales) OVER(PARTITION BY SalesGroup) AS AverageSales --m�dia por SALESGROUP
FROM
  RegionalSales
ORDER BY
  SalesGroup, AnnualSales DESC;

-----------------------------------------
--igual, menos colunas
SELECT DISTINCT
  SalesGroup,
  COUNT(AnnualSales) OVER(PARTITION BY SalesGroup) AS CountryCount,
  SUM(AnnualSales) OVER(PARTITION BY SalesGroup) AS TotalSales,
  AVG(AnnualSales) OVER(PARTITION BY SalesGroup) AS AverageSales
FROM
  RegionalSales
ORDER BY
  TotalSales DESC;
 --------------------------------------------
 --AGRUPANDO E ORDENANDO
 --grouping with ordering: each grouping column is different!
 --duplicate are aggregated together
 /*
 The default setting for the ROWS/RANGE subclause is RANGE BETWEEN UNBOUNDED PRECEDING AND CURRENT ROW. 
 This means that, for each row in the partition, the window function is applied to the current row and the preceding rows only. 
 So aggregations don�t operate on the entire set of values within the partition, but only on the value in the current row and the previous rows, 
 as we saw in the example below.
 */

 --contagem a partir de dentro da janela, ordenando do maior valor de venda at� o menor, agregando da primeira linha at� a atual.
 SELECT
  SalesGroup,
  Country,
  AnnualSales,
  COUNT(AnnualSales) OVER(PARTITION BY SalesGroup
    ORDER BY AnnualSales DESC) AS CountryCount,
  SUM(AnnualSales) OVER(PARTITION BY SalesGroup
    ORDER BY AnnualSales DESC) AS TotalSales,
  AVG(AnnualSales) OVER(PARTITION BY SalesGroup
    ORDER BY AnnualSales DESC) AS AverageSales
FROM
  RegionalSales  ;
------------------------------------------------------------------------------------------------
--PALAVRAS-CHAVE: PRECEDING -> anteriores, FOLLOWING -> seguintes
--CURRENT ROW -> linha atual
--UNBOUNDED -> sem limite, a partir da primeira ou at� a �ltima

--IGUAL com a defini��o de frame padr�o:
--RANGE considera valores iguais como o mesmo, GREECE e SPAIN, agregando apenas um deles:

 SELECT
  SalesGroup,
  Country,
  AnnualSales,
  COUNT(AnnualSales) OVER(PARTITION BY SalesGroup
    ORDER BY AnnualSales DESC 
  range between unbounded preceding and current row) AS CountryCount,
  SUM(AnnualSales) OVER(PARTITION BY SalesGroup
    ORDER BY AnnualSales DESC 
  range between unbounded preceding and current row) AS TotalSales,
  AVG(AnnualSales) OVER(PARTITION BY SalesGroup
    ORDER BY AnnualSales DESC 
  range between unbounded preceding and current row) AS AverageSales
FROM
  RegionalSales  ;
---------------------------------------------------------------------------
--ROWS considera cada linha como um valor a ser agregado, normalmente � o mais utilizado
 SELECT
  SalesGroup,
  Country,
  AnnualSales,
  COUNT(AnnualSales) OVER(PARTITION BY SalesGroup
    ORDER BY AnnualSales DESC 
  rows between unbounded preceding and current row) AS CountryCount,
  SUM(AnnualSales) OVER(PARTITION BY SalesGroup
    ORDER BY AnnualSales DESC 
  rows between unbounded preceding and current row) AS TotalSales,
  AVG(AnnualSales) OVER(PARTITION BY SalesGroup
    ORDER BY AnnualSales DESC 
  rows between unbounded preceding and current row) AS AverageSales
FROM
  RegionalSales  ;
-------------------------------------------------------------------------------------
--fa�a a agrega��o apenas com as 2 linhas anteriores:
--only the 2 preceding rows and current
SELECT
  SalesGroup,
  Country,
  AnnualSales,
  COUNT(AnnualSales) OVER(PARTITION BY SalesGroup
    ORDER BY AnnualSales DESC
      ROWS 2 PRECEDING) AS CountryCount,
  SUM(AnnualSales) OVER(PARTITION BY SalesGroup
    ORDER BY AnnualSales DESC
      ROWS 2 PRECEDING) AS TotalSales,
  AVG(AnnualSales) OVER(PARTITION BY SalesGroup
    ORDER BY AnnualSales DESC
      ROWS 2 PRECEDING) AS AverageSales
FROM
  RegionalSales;
  ------------------------------------------
 --fa�a a agrga��o considerando a janela toda: 
SELECT
  SalesGroup,
  Country,
  AnnualSales,
  COUNT(AnnualSales) OVER(PARTITION BY SalesGroup
    ORDER BY AnnualSales DESC
       ROWS BETWEEN UNBOUNDED PRECEDING AND UNBOUNDED FOLLOWING) AS CountryCount,
  SUM(AnnualSales) OVER(PARTITION BY SalesGroup
    ORDER BY AnnualSales DESC
       ROWS BETWEEN UNBOUNDED PRECEDING AND UNBOUNDED FOLLOWING) AS TotalSales,
  AVG(AnnualSales) OVER(PARTITION BY SalesGroup
    ORDER BY AnnualSales DESC
      ROWS BETWEEN UNBOUNDED PRECEDING AND UNBOUNDED FOLLOWING) AS AverageSales
FROM
  RegionalSales;




 ------------------------------------------
 --FUN��ES ANAL�ICAS:
  --First/Last values - analytic functions
 --veja horizontalmente
 SELECT
  SalesGroup,
  Country,
  AnnualSales,
  FIRST_VALUE(AnnualSales) OVER(PARTITION BY SalesGroup
    ORDER BY AnnualSales DESC) AS HighestSales, -- ordene o valor do maior pro menor, ous seja, o primeiro � o maior, o �ltimo � o menor
  LAST_VALUE(AnnualSales) OVER(PARTITION BY SalesGroup
    ORDER BY AnnualSales DESC) AS LowestSales
FROM
  RegionalSales;

------------------------------
--todas as linhas da parti��o!
SELECT
  SalesGroup,
  Country,
  AnnualSales,
  FIRST_VALUE(AnnualSales) OVER(PARTITION BY SalesGroup
    ORDER BY AnnualSales DESC) AS HighestSales,
  LAST_VALUE(AnnualSales) OVER(PARTITION BY SalesGroup
    ORDER BY AnnualSales DESC
      ROWS BETWEEN UNBOUNDED PRECEDING AND UNBOUNDED FOLLOWING)
      AS LowestSales
FROM
  RegionalSales;
 ----------------------------

 --LAG: valor de n linhas antes da atual
 --LEAD: valor de n linhas depois da atual
 SELECT
  SalesGroup,
  Country,
  AnnualSales,
  LAG(AnnualSales, 1) OVER(PARTITION BY SalesGroup
    ORDER BY AnnualSales DESC) AS PreviousSale,
  LEAD(AnnualSales, 1) OVER(PARTITION BY SalesGroup
    ORDER BY AnnualSales DESC) AS NextSale
FROM
  RegionalSales;
  ----------------------------
  --tratando nulls:
   SELECT
  SalesGroup,
  Country,
  AnnualSales,
  LAG(AnnualSales, 1,0) OVER(PARTITION BY SalesGroup
    ORDER BY AnnualSales DESC) AS PreviousSale,
  LEAD(AnnualSales, 1,0) OVER(PARTITION BY SalesGroup
    ORDER BY AnnualSales DESC) AS NextSale
FROM
  RegionalSales;



Abraços e Happy SQL Serving!

É isso ae galera!

No dia 24 de Junho tivemos mais um SQL SATURDAY em terras brazucas. Desta vez foi em Caxias do Sul.
O pessoal da organização está de parabéns! O evento foi muito bem organizado, cheio de palestras sensacionais e é claro, ótimos coffees!

O pessoal que participou também está de parabéns! O evento não ficou vazio depois do almoço. Conseguimos perceber que o pessoal está bastante interessado e está comprometido. Isso é muito gratificante para todos!

Neste SQLSAT conversei sobre Opções de Alta Disponibilidade entre SQL SERVER e ORACLE. Os slides da minha palestra podem ser encontrados aqui.

 

Nos encontramos por aí.

Happy SQL Serving!

Fala galera,

Segue link do hangout fiz pelo site codificando – se você não conhece, acesse JÁ: http://codificando.net/.

Falei a respeito dos processos de T.I. na nossa vida de DBA: http://live.codificando.net/2015/05/edicao-48-dba-vs-itil-como-os-processos-podem-ajudar-e-atrapalhar-a-vida-do-dba/

A apresentação está neste link: sql-itil

O hangout:

Espero que gostem e aguardo feedbacks!

Abraços a todos!

 

 

 

Fala pessoal, boa noite.

Subi mais um video no canal do youtube. Este é um video não tecnico que trata dos problemas que podem ocorrer quando não seguimos processos (biblioteca ITIL, por exemplo) e deixamos a proatividade (para não falar outra coisa) falar mais alto do que a vontade de… escrever… documentar…

Sim, ITIL pode ser chato, mas pode salvar um emprego!

Com certeza este video terá mais do que uma parte e haverão palestras a respeito do tema.

Espero que gostem…

Até a próxima!

 

Fala pessoal, tudo bem?

Neste post vou apresentar uma série de videos que criei para ajudar vocês a criar do zero um cluster virtualizado.

O que utilizei:

  • Freenas 9.2;
  • VMware Workstation (9 ou 10);
  • Iso do Windows server 2008 R2 (sem piratear heim! ;-));
  • Iso do SQL SERVER 2008 R2 (mesma dica de cima!);

Estou testando o cluster em uma máquina física de 16 Gb de RAM e estou utilizando em torno de 150 Gb de espaço em disco. No caso estou usando um processador i7.

 

Espero que gostem e seja útil.

Parte 1 – Criação do storage:

Parte 2 – Criando o AD:

Parte 3.1: Instalando o Sistema Operacional dos servidores do cluster e gerando templates.

ps: Sim, eu dividi a parte 3 em duas, caso contrário os videos ficariam muito extensos.

Parte 3.2: Configurando o cluster no Windows:

Parte 4, final – instalando o SQL SERVER no Cluster:

É isso pessoal, espero que gostem e seja útil de alguma forma. Pelo menos para brincar!

Abraços!

Marcelo

 

Fala galera,

Há algum tempo o Adam Machanic e o Jonathan Kehayias postaram scripts que ajudam a “inchar” as bases de dados AdventureWorks do SQL SERVER, para conseguirmos fazer testes mais reais em cima de um WORKLOAD mais “plausível”.

Para os SQLGeeks de plantão:

https://www.sqlskills.com/blogs/jonathan/enlarging-the-adventureworks-sample-databases/

http://sqlblog.com/blogs/adam_machanic/archive/2011/10/17/thinking-big-adventure.aspx

 

Para baixar as bases de exemplo iniciais:

http://msftdbprodsamples.codeplex.com/

Enjoy! 😉

Fala pessoal,

Neste post vou falar sobre os limites e melhores práticas a respeito de configurações de memória no SQL SERVER.

O funcionamento

O SQL SERVER possui dois limites configuráveis de alocação de memória: inferior e superior.
Quando o serviço do mesmo é iniciado apenas uma pequena quantidade de memória é alocada (o suficiente para alocar as estruturas de funcionamento de buffers), não necessariamente o limite inferior configurado.
Quando o SQL SERVER alcançar o limite mínimo ele manterá o Buffer Cache no mínimo neste valor. O limite máximo indica para o SGBD não ultrapassar determinado valor de alocação de memória.
Vale lembrar que este limite configurável determina apenas o valor do Buffer Cache, o SQL SERVER normalmente necessita de mais 20% de memória para funcionamento adequado.

memoria SQL SERVER - mantenha configurada!

A boa prática

O ideal assim que terminamos de instalar a instância do SQL SERVER é reservar um valor específico como limite mínimo e um valor superior como limite máximo. Respeitando os seguintes fatores:

  • O SQL SERVER vai consumir em média mais 20% de memória acima do limite máximo e;
  • O Sistema Operacional também precisa trabalhar! Deixe em torno de 20% da memória total do servidor para ele.

A péssima prática

Consideramos péssimas práticas:

  1. Deixar de configurar os limites de memória do SQL SERVER;
  2. Configurar os limites de memória com valores iguais.

São péssimas práticas porque:

  1. Caso o S.O. sinalize pressão de memória o SQL não vai liberar nada;
  2. Mesma situação, não será possível dar uma “folga” para o S.O. caso haja pressão externa de memória.

Abaixo o vídeo com a nossa experiência: