Você está na página 1de 206

prof.

José Picovsky
jpicovsky@gmailcom.br
INSTALAR OS SOFWARES NA SEGUINTE ORDEM

1) JDK 11 (obrigatório)
https://www.oracle.com/br/java/technologies/javase/jdk11-archive-
downloads.html

2) ORACLE (instale no c:\oracle)


https://www.oracle.com/br/database/technologies/xe-downloads.html

3) SQLDEVELOPER (instalar dentro da pasta Oracle)


https://www.oracle.com/tools/downloads/sqldev-downloads.html

Ou utilizar o Oracle On line pelo link


https://livesql.oracle.com/apex/f?p=590:1000
Crie uma conta na oracle e use esse recurso do Oracle Live
INSTALAR OS SOFWARES NA SEGUINTE ORDEM

DESCOMPACTE O ORACLE (PKZIP) NA PASTA ORACLE

DEPOIS INSTALE O ORACLE PELO ARQUIVO SETUP (DENTRO DA PARA


ORACLE)

QUANDO CONCLUIR , REINICIE O COMPUTADOR

SE NÃO HOUVER A CONTINUIDADE NA INSTALAÇÃO, EXECUTE O SETUP


NOVAMENTE

ELE VAI PEDIR UMA SENHA PARA O USUÁRIO SYSTEM (COLOQUE A


SENHA, POR EXEMPLO abc)

AO CONCLUIR COLOQUE O SQLDEVELOPER, NA PASTA ORACLE

NO TERMINO EXECUTE O SQLDEVELOPER QUE ESTA DENTRO DESTA


PASTA
Clique no sinal de + ou CTRL N para criar uma conexão

Digite em
Nome: DBA
Nome do Usuário: System
Senha: Coloque aqui a mesma senha que foi solicitada na instalação do Oracle
Clique em Salvar Senha, Testar , Salvar, Conectar
Agora crie um usuário qualquer , que não seja o usuário system (DBA).

Na tela do query builder digite uma linha de cada vez, selecionando a mesma e
clicando ctrl enter em cada uma das linhas.

alter session set "_ORACLE_SCRIPT"=true;


(as vezes será necessário digitar essa linha)

Aqui você digita um nome para o usuário e a senha para criar o usuário

CREATE USER nome IDENTIFIED BY senha

CREATE USER pico IDENTIFIED BY abc;

Depois você dá os direitos para esse usuário

GRANT create session, create table, create view , dba to nome usuário

GRANT create session, create table, create view, dba TO pico;


Depois clique em nova conexão

Na tela de conexão digite um nome para a mesma

O nome do usuário e a senha deverão ser os mesmo utilizados


em create user pico - abc

Clique em salvar senha, depois em testar , se der a mensagem


de criado com sucesso, clique em salvar e depois em conectar
E POR FIM A CONEXÃO PICO
VAI SER CRIADA
Verifique se você está na aba do usuário (pico) e se esta mostrando no canto
superior direito o nome deste usuário (pico)

Agora é só começar criando tabelas e executar o comando do sql oracle


Tipos de Comandos SQL
Categorias de Instruções SQL
Tipos de dados Oracle
Tipos de dados Oracle

•VARCHAR2 – Sequencia de caracteres alfanuméricos de tamanho variável com


limite de 4000 Bytes.

•VARCHAR – Sinônimo para VARCHAR2, por recomendação da própria Oracle,


este tipo de dados não deve ser usado, pois existe a possibilidade do tipo
VARCHAR integrar versões futuras do banco de dados Oracle com
características diferentes do VARCHAR2. O comprimento para este tipo de
dados é variável, assim somente o espaço que realmente for preenchido será
armazenado na memória. O VAR significa Variable.
Tipos de dados Oracle
Tipos de dados Oracle

A diferença entre os tipos VARCHAR2/VARCHAR e CHAR está na capacidade total


de armazenamento, onde pode-se armazenar mais caracteres quando o tipo de
dados VARCHAR2 e no aproveitamento de memória, o tamanho de um campo
VARCHAR2 varia de acordo com seu conteúdo, o valor declarado é apenas um
limitador, já quando usa-se o tipo CHAR o valor declarado é fixo independente do
seu conteúdo.
Exemplo 1:
Para uma coluna hipotética chamada NOME do tipo VARCHAR2 com tamanho
(máximo) 20 caracteres, ao armazenarmos o nome Paulo, serão usadas apenas 5
posições.
Caso o tipo de dados para esta mesma coluna for definido com CHAR tamanho
20, ao armazenarmos o nome Paulo, serão usadas 20 posições de memória,
sendo 5 para a palavra Paulo e o restante será preenchido com espaços em
branco.
Pode-se concluir que o uso do tipo VARCHAR2 é mais adequado quando o valor a
ser armazenado tem seu tamanho variável.
Tipos de dados Oracle
Tipos de dados Oracle

•NUMBER [(precisão),(escala)] - Representa um número que podem variar entre 1 e 38


posições e a escala entre –84 e 127 posições. Para valores inteiros a escala deve ser 0.
A “Precisão” corresponde ao tamanho do número que se deseja armazenar, já a escala
representa o tamanho da parte decimal (Quantidade de casas decimais). Exemplo: Se o
Valor que se deseja armazenar possuir quatro casas decimais e duas casas inteiras
(22,1245) a declaração do tipo será 6 para a primeira posição, pois representa o total de
numeros e a segunda será 4: NUMBER(6,4) indica que o tamanho total é 6 sendo que 4
são decimais.
•Para trabalhar com o tipo de dados NUMBER armazenando apenas números inteiros
declara-se NUMBER(38). Exemplo de uma tabela que contem dois campos do tipo
NUMBER, sendo que o primeiro está declarado para armazenar dados com casas
decimais e no segundo apenas dados inteiros.

•INTEGER – Tipo de dados para números inteiros. Equivalente ao NUMBER, com escala
zero.
Nota: Qual tipo usar para armazenar dados Inteiros: Number ou Integer?
Quando declara-se um campo com o tipo Integer ou Number ambos são armazenados no
dicionário como tipo numérico.
•SMALLINT – Equivalente ao NUMBER, porém ocupa a metade do espaço em memória.
Tipos de dados Oracle
Tipos de dados Oracle
Constraint

CONSTRAINTS, que nada mais são restrições que você estabelece para uma coluna no
banco de dados, que nada mais é de um método para validar a integridade de todos os
dados que entram em sua base.

As restrições mantém os dados do usuário restritos, e assim evitam dados inválidos


inseridos no banco. A mera definição do tipo de dado para uma coluna é apenas
uma restrição . Por exemplo, uma coluna de tipo DATE restringe o conteúdo da mesma
para dados válidos.

Constraints bom podemos ter os seguintes tipos:

•Primary Key (PK) = Está restrição cria um índice único para um conjunto de colunas ou
uma coluna para Chave Primaria.
•Unique = Está Contraint determina que uma coluna não poderá ter 2 linhas com o
mesmo valor.
•Foreign Key (FK ou Chave Estrangeira) = Determina uma coluna ou um conjunto de
colunas que possuem valores em outras tabelas, referente a uma referência ou um
relacionamento.
•Check = Especifica a condição que a coluna precisa para salvar o registro.
•Not Null = Determina que a coluna tem preenchimento obrigatório.
Chave Primária (Primary key – PK)

A chave primária, ou Primary key (PK) é o identificador único de um registro na tabela.

Pode ser constituída de um campo (chave simples) ou pela combinação de dois ou mais
campos (chave composta), de tal maneira que não existam repetição de dados no campo
de valor de chave primária.

A constraint Primary Key (chave primaria), não permite valores nulos

Portanto,

•Para ser uma chave primária a coluna que definem a chave primária são exclusiva, ou
seja a coluna não pode conter valores duplicados;
•Nenhum valor nas colunas de chave primária é NULL ou valores “em branco”.
Chave Estrangeira (Foreign – FK)
Uma chave estrangeira é um conjunto de uma ou mais colunas em uma tabela que se
refere à chave primária em outra tabela.

Chave estrangeira é o campo que estabelece o relacionamento entre duas tabelas. Assim,
uma coluna corresponde à mesma coluna que é a chave primária de outra tabela. Dessa
forma, deve-se especificar na tabela que contém uma chave estrangeira são essas
colunas à qual tabela são relacionadas.

Não há nenhuma obrigatoriedade especial, que seja necessário colocar uma chave
estrangeira.

O uso de chaves estrangeiras garante que não existirão dados nos campos das tabelas-
filhas que não tenham correspondência na tabela mãe.
Exemplo de Chave Primária e Chave Estrangeira

Tabela Produtos Tabela Itens do Pedido


- Codigo_produto (chave primária) - Numero_pedido
- Produto - Codigo_produto (chave estrangeira)
- Categoria - Quantidade
- Preço Data
- Quantidade
- Descricao

Nas tabelas acima temos um caso de chaves primária e estrangeira.

Observe que o codigo_produto consta nas duas tabelas. Em Produtos ele é o campo
identificador, ou seja, cada produto deverá ser exclusivo, portanto, uma chave
primária. Já em Itens do Pedido o campo codigo_produto poderá constar várias vezes
e como ele já é chave primária em Produtos, aqui ele será uma chave estrangeira.

Nesse exemplo a tabela mãe é a tabela Produtos e a tabela filha é a de Itens do


Pedido, pois a mesma depende da tabela Produtos(mãe) para que um código de
produto possa ser preenchido na tabela filha.
Exemplo de Chave Primária e Chave Estrangeira

Tabela Produtos Tabela Itens do Pedido


- Codigo_produto (chave primária) - Numero_pedido
- Produto - Codigo_produto (chave estrangeira)
- Categoria - Quantidade
- Preço Data
- Quantidade
- Descricao

Um campo de chave estrangeira depende dos dados do mesmo campo em outra tabela,
onde ele é chave primária.

Ele vai ser preenchido com os códigos que existem em outra tabela , chamada de tabela
mãe.

No exemplo acima a tabela Itens_pedidos só poderá ter códigos que existem na tabela
Produtos

De forma sucinta, a chave estrangeira é uma referência em uma tabela a uma chave primária
de outra tabela.
Exemplo de Chave Primária e Chave Estrangeira

Tabela Produtos Tabela Itens do Pedido


- Codigo_produto (chave primária) - Numero_pedido
- Produto - Codigo_produto (chave estrangeira)
- Categoria - Quantidade
- Preço Data
- Quantidade
- Descricao

Um campo de chave estrangeira depende dos dados do mesmo campo em outra tabela,
onde ele é chave primária.

Ele vai ser preenchido com os códigos que existem em outra tabela , chamada de tabela
mãe.

No exemplo acima a tabela Itens_pedidos só poderá ter códigos que existem na tabela
Produtos

De forma sucinta, a chave estrangeira é uma referência em uma tabela a uma chave primária
de outra tabela.
Exemplo de Chave Primária e Chave Estrangeira

Note que Codigo_Mecanico, na tabela Mecanico é chave primária, pois não podemos ter
outros mecânicos utilizando o mesmo código. É nessa tabela que temos todos os dados do
mecânico, por isso ela é considerada uma tabela mãe.

Já na tabela Serviços, só podemos ter códigos que existam na tabela Mecanico. A tabela
Serviços é uma tabela dependente da tabela Mecanico, por isso a tabela serviços, é uma
tabela filha e nesta tabela o Codigo_mecânico é uma chave estrangeira, pois todos os dados
de mecânicos estão na tabela mãe, Mecanicos.
Exemplo de Chave Primária e Chave Estrangeira

Nesse exemplo acima tabela Clientes é a tabela mãe de pedidos, pois é necessário preencher
primeiro a tabela Clientes para poder usar um código de clientes , da mesma, para utilizá-lo em
Pedidos.
A tabela itens de pedido , depende das tabelas Pedidos e Produtos, sendo que estas duas ultimas
tabelas tem que ser preenchidas antes de itens do pedido.

Asssim sendo a tabela mãe terá sempre uma chave primária. A tabela filha terá uma chave
estrangeira para poder se relacionar com a tabela mãe. Essa tabela filha, no caso Pedidos, poderá
ter a sua chave primária também, pois ela tem como filha a tabela itens pedidos. A tabela
produtos, também é mãe de itens do pedido. Esta tabela produtos terá a sua chave primária.
Exemplo de Chave Primária e Chave Estrangeira
Veja abaixo um diagrama de banco de dados com várias tabelas relacionadas. Perceba a presença de
chaves primárias, identificadas por PK (primary key) e as chaves estrangeiras, identificadas por FK
(foreign key).
Comando create table (para criar uma tabela)
Sem constraints (regras)

Entre na sua conexão, conforme indica a seta em vermelho e digite o comando


Comando create table (para criar uma tabela)
Com constraints (regras)
Comando create table (para criar uma tabela com constraints)

A restrição pode ser colocada direto no campo ou no final das descrições de


campos, colocando a palavra constraint. Embora seja a mesma coisa, com a
descrição da regra em constraint é a melhor forma em termos de documentação das
mesmas, é mais profissional !

Na constraints colocamos o comando na seguinte sequencia:

Constraints nome da tabela_nome do campo_pk primary key(nome do campo de


chave primária)
Comando create table (para criar uma tabela)
Com constraints (regras)
Comando create table (para criar uma tabela)
Com constraints (regras)

Observe o campo é chave estrangeira pelo comando FOREIGN KEY (codeditora) que faz parte
da tabela livro3. A declaração REFERENCES indica qual tabela
será consultada para validar a chave estrangeira, no exemplo EDITORA3
Comando create table (para criar uma tabela com PK e FK)

Observe que o atributo id_pais é chave primária na TB_PAIS

Constraint tb_piloto_id_pais_fk é o nome da restrição , formado pelo nome da tabela, nome


do campo de chave estrangeira e a identificação fk. Se for primary key a identificação fica pk,
se for not null fica nn (veja acima em nomes de restrições na tabela TB_PAIS)

A declaração de qual campo é chave estrangeira é dada pelo comando FOREIGN KEY
(id_pais).

A declaração REFERENCES indica qual tabela será consultada para validar a chave
estrangeira, no exemplo TB_PAIS , e dentro dos parênteses indicamos qual a coluna será
consultada, no caso o campo id_pais

Constraints nome da restrição foreign key (campo da tabela que depende de outra tabela)
references nome da tabela a ser consultada e entre parênteses o campo comum nas duas
tabelas
Exemplos de constraints (regras)
CREATE TABLE TB_PILOTO (
id_piloto NUMBER(5) CONSTRAINT tb_piloto_id_piloto_
pk PRIMARY KEY,
nm_piloto VARCHAR2(50),
dt_nascimento DATE,
id_pais NUMBER(5)
);

ou

CREATE TABLE TB_PILOTO (


id_piloto NUMBER(5),
nm_piloto VARCHAR2(50),
dt_nascimento DATE,
id_pais NUMBER(5),
CONSTRAINT tb_piloto_id_piloto_pk PRIMARY KEY (id_piloto)
)
Exemplos de constraints (regras)

CREATE TABLE ITENS (


ID_PRODUTOS NUMBER(4),
ID_PEDIDO NUMBER(4),
QT_ITENS NUMBER(4) NOT NULL,
PRIMARY KEY(ID_PRODUTOS,ID_PEDIDO),
CONSTRAINT ITENS_ID_PRODUTOS_FK FOREIGN KEY (ID_PRODUTOS) REFERENCES PRODUTO
(ID_PRODUTO),
CONSTRAINT ITENS_ID_PEDIDO_FK FOREIGN KEY (ID_PEDIDO) REFERENCES PEDIDO (ID_PEDIDO)
)
Exemplos de constraints (regras)

CREATE TABLE TB_PAIS (


id_pais NUMBER(5),
nm_pais VARCHAR2(50) UNIQUE,
nr_populacao VARCHAR2(10),
CONSTRAINT tb_pais_id_pais_pk PRIMARY KEY (id_pais),
CONSTRAINT tb_pais_nm_pais_nn CHECK (nm_pais IS NOT
NULL)
);

Unique – não permite repetir um dados no campo


Primary Key (Chave Primária)
Is not null - campo obrigatório
Exemplos de constraints (regras)

CREATE TABLE TB_PAIS (


id_pais NUMBER(5),
nm_pais VARCHAR2(50),
nr_populacao VARCHAR2(10),
CONSTRAINT tb_pais_id_pais_pk PRIMARY KEY (id_pais),
CONSTRAINT tb_pais_nm_pais_nn CHECK (nm_pais IS NOT
NULL),
CONSTRAINT tb_pais_nm_pais_un UNIQUE (nm_pais)
);

Unique – não permite repetir um dados no campo


Primary Key (Chave Primária)
Is not null - campo obrigatório
Exemplos de constraints (regras)
CREATE TABLE TB_PILOTO (
id_piloto NUMBER(5),
nm_piloto VARCHAR2(50),
dt_nascimento DATE DEFAULT SYSDATE,
id_pais NUMBER(5),
ie_sexo CHAR(1),
CONSTRAINT tb_piloto_ie_sexo_ck CHECK (ie_sexo IN (‘M’,’F’)),
CONSTRAINT tb_piloto_id_piloto_pk PRIMARY KEY (id_piloto),
CONSTRAINT tb_piloto_id_pais_fk FOREIGN KEY (id_pais) REFERENCES TB_PAIS
(id_pais),
CONSTRAINT tb_piloto_nm_piloto_ck CHECK (nm_piloto = UPPER(nm_piloto))
);

CHECK (ie_sexo IN (‘M’,’F’)) para aceitar somente a digitação do M ou F

CHECK (nm_piloto = UPPER(nm_piloto)) para aceitar a digitação do nome do piloto


escrito com letras maiusculas
Alterar a estrutura de uma tabela
ALTER TABLE Modifica a definição de uma tabela

Alterar o nome de uma tabela


RENAME nome_antido_tabela TO nome_novo_tabela;
Para exemplificar
RENAME TB_TEMP TO TB_PAIS_BK;
=======================================================
Alterar o nome de uma coluna de uma tabela
ALTER TABLE table_name RENAME COLUMN old_column_name TO
new_column_name;

ALTER TABLE EMPREGADOS RENAME COLUMN email TO email_id;


=======================================================
Adicionar um novo campo em uma tabela
alter table func add dtcadastro date;
=======================================================
Colocar um not null em uma coluna de uma tabela
ALTER TABLE func MODIFY nome NOT NULL;
Alterar a estrutura de uma tabela
Aumentar o tamanho do campo de uma tabela
ALTER TABLE FUNC MODIFY SALARIO NUMERIC(13,2);
ALTER TABLE FUNC MODIFY NOME VARCHAR2(50);
=======================================================
Alterar o tipo de dados de uma tabela
ALTER TABLE FUNC MODIFY DTCADASTRO TIMESTAMP;
=======================================================
Colocar uma chave primária em um campo
ALTER TABLE TB_EQUIPE ADD CONSTRAINT tb_equipe_id_equipe_pk
PRIMARY KEY (id_equipe);
=======================================================
Colocar uma chave estrangeira
ALTER TABLE TB_EQUIPE ADD CONSTRAINT tb_equipe_id_pais_fk
FOREIGN KEY (id_pais) REFERENCES TB_PAIS (id_pais);
=======================================================
Excluir um campo de uma tabela
ALTER TABLE TB_EQUIPE DROP COLUMN DTCADASTRO;
=======================================================
Colocar uma regra em um campo de uma tabela
ALTER TABLE FUNC ADD CONSTRAINT func_cargo CHECK (cargo IS NOT NULL);
Excluir uma tabela

DROP TABLE

Remove totalmente a tabela e todos os seus dados do banco de dados

Todas as linhas da tabela são eliminadas.

Exemplo:

drop table tb_pilotos


Padronização nomes tabelas e campos

Não existe um consenso sobre como se deve criar o projeto físico do SGBD nem sobre quais
regras de nomenclatura devem ser adotadas para tabelas e colunas.

A padronização de nomes, campos, tabelas é importante pois facilita o entendimento e a


velocidade de desenvolvimento de analistas e programadores.

Quando você está modelando e trabalhando com um banco de dados pequeno, pode parecer
perda de tempo discutir e definir uma política de padronização, mas quando o número de
tabelas é grande as coisas mudam e pode se tornar muito difícil extrair informações de um
banco não padronizado.

Existem dois padrões que inspiram muitos DBA a criar suas regras que são variações
para cada SGBD o da trigramação e o qualificador nome descritivo.
Padronização nomes tabelas e campos

TRIGRAMAÇÃO.

A trigramação é uma cadeia de caracteres, normalmente constituída por três letras da


entidade ou pela escolha das três letras mais significativas de uma entidade. Essas
três letras são utilizadas como parte da definição do atributo da mesma entidade.
Para exemplificar a figura a seguir apresenta a entidade Cliente e ela convertida para
trigramação.
Padronização nomes tabelas e campos

TRIGRAMAÇÃO.

Como regra geral da trigramação, nunca utilize artigo como ‘de’, ‘das’ ou ‘com’ ou
pronomes em uma entidade ou atributo. Não utilize caracteres especiais, acentos ou
cedilha. Todas as palavras compostas devem ser separadas por ‘_’ underscore como
pessoa_jurídica ou pessoa_fisica.

O nome da entidade deve ser sempre no singular e deve expressar de forma clara a
finalidade da entidade. Na trigramação, ao se criarem abreviaturas, pode ocorrer de ao
escolher as três primeiras letras de uma entidade, encontrar outra entidade que
apresente as três letras iniciais idênticas. Neste caso, você deve manter duas letras
idênticas e escolher uma terceira que permita diferenciar as entidades. Se o modelo
for complexo e tiver a necessidade de se criar módulos, o nome do módulo será
abreviado e atribuído a todas as tabelas que lhe pertence.

Toda a chave primária terá a trigramação seguido da palavra id.


Padronização nomes tabelas e campos

QUALIFICADOR NOME DESCRITIVO.

O qualificador nome descritivo tem como base o padrão ISO/IEC 11179-5. A regra
utiliza basicamente algumas tabelas com símbolos e todas as entidades e atributos
do DER devem, de alguma forma, ser representados por um destes símbolos. Por
exemplo, imagine que queremos converter a entidade Cliente do DER para o padrão
qualificador nome descritivo. Você deverá procurar para cada atributo da entidade
na tabela a seguir o símbolo mais adequado. A figura abaixo apresenta como
fica a representação da entidade no modelo.
Padronização nomes tabelas e campos
QUALIFICADOR NOME DESCRITIVO.
Padronização nomes tabelas e campos
SEM QUALIFICADOR NOME DESCRITIVO.
Padronização nomes tabelas e campos
COM QUALIFICADOR NOME DESCRITIVO.

Para o nome da constraints existe uma limitação de 30 caracteres


Inserindo dados nas tabelas

A instrução INSERT é usada para adicionar linha em uma ou mais tabelas.

Os dados serão adicionados com valores especificados

insert into <TABELA> (<lista-de-colunas>) values (<lista-de-valores>)

insert into <TABELA> values (<lista-de-valores>)


A lista de colunas é opcional, porém só funciona se na lista-de-valores forem
inseridas todas as colunas da tabela na ordem de sua criação.
Inserindo dados nas tabelas

Para inserir uma linha em uma tabela SQL, é necessário a utilização do


comando INSERT.

Os dados serão adicionados com valores especificados em values

insert into <TABELA> (<lista-de-colunas>) values (<lista-de-valores>)

insert into <TABELA> values (<lista-de-valores>)


A lista de colunas é opcional, porém só funciona se na lista-de-valores forem
inseridas todas as colunas da tabela na ordem de sua criação.

Exemplos:
insert into PROFESSOR (CPF,NOME,SALARIO,TITULACAO)
values (11111111111, 'RICARDO TERRA', 1.99, 'ESPECIALISTA’);

insert into PROFESSOR


values (11111111111, 'RICARDO TERRA', 1.99, 'ESPECIALISTA');
Inserindo dados nas tabelas
create table funcionarios(
matricula number(8),
nome varchar2(70),
endereco varchar2(80),
cidade varchar2(35),
uf char(2),
cep char(9),
salario number(10,2)
);

insert into funcionários (matricula, nome, endereco, cidade, uf, cep, salario)
values (111,'Jose Lima','Rua México,200','São Paulo','SP','01417-020',2000)

ou

insert into funcionários values (111,'Jose Lima','Rua México,200','São Paulo’, 'SP’,


'01417-020’, 2000)
Inserindo dados nas tabelas
create table funcionarios(
matricula numeric(8) not null primary key,
nome varchar2(70) not null,
fone varchar2(25),
uf char(2) not null,
salario numeric(8,2) check (salario>=1200),
dtnasc date
);

Para datas usar o to_date que converte uma data no formato texto para data.

insert into funcionarios (matricula,nome,fone,uf,salario,dtnasc)


values (123,'Jose Lima','(11) 9-1234-12-11','SP',1200.34, to_date('30/04/2000','dd/mm/yyyy’));

insert into agenda(


codcli numeric not null primary key,
data date values (313, TO_DATE(‘03/12/2021 16:02:44', ‘dd/mm/yyyy hh24:mi:ss'));
Inserindo dados nas tabelas
Para inserir múltiplas linhas, utilize o comando
INSERT ALL.

INSERT ALL
INTO TB_PAIS (id_pais, nm_pais) VALUES (7,'Espanha')
INTO TB_PAIS (id_pais, nm_pais) VALUES (8,'Reino Unido')
INTO TB_PAIS (id_pais, nm_pais) VALUES (9,'Austrália’)

Outra forma de utilizar o INSERT ALL é utilizar a ordem padrão da tabela.

INSERT ALL
INTO TB_PAIS VALUES (10,'Países Baixos',NULL)
INTO TB_PAIS VALUES (11,'Suécia',NULL)
INTO TB_PAIS VALUES (12,'Canadá',NULL)
INTO TB_PAIS VALUES (13,'Itália',NULL)
INTO TB_PAIS VALUES (14,'Rússia',NULL)
Trabalhando com Sequence

Com a sequence é possível criar um campo de incremento automático


com valores inteiros que pode ser atribuído nas chaves primárias.

Se dois usuários incrementarem simultaneamente a mesma


sequência, os números de sequência que cada usuário adquire podem
ter lacunas, porque os números de sequência estão sendo gerados
pelo outro usuário.

Um usuário nunca pode adquirir o número de sequência gerado por


outro usuário.

Depois que um valor de sequência é gerado por um usuário, esse


usuário pode continuar acessando esse valor, independentemente de a
sequência ser incrementada por outro usuário.
Trabalhando com Sequence
CREATE SEQUENCE sequence
[INCREMENT BY n]
[START WITH n]
[MAXVALUE n]
[MINVALUE n | ]
[{CACHE n | NOCACHE}];

sequence:é o nome da sequence (gerador de sequência).


INCREMENT BY n:especifica o intervalo entre os geradores de sequência.
START WITH n:especifica o primeiro número da sequência.
MAXVALUE n:especifica o valor máximo que a sequência pode gerar.
MINVALUE n:especifica o valor mínimo da sequência.
CACHE especifica quantos valores da sequencia que o servidor oracle mantém em memória Se
four usado um cache 5, vão ser gerados cinco números e depois mais cinco números e assim por
diante.
Trabalhando com Sequence - Exemplos
create table CARGOS(
codcargo numeric(5) not null,
cargo varchar2(30) not null,
CONSTRAINT CARGOS_codcargo_pk primary key(codcargo)
);

Se formos inserir dados sem usar a sequence, deveremos informar um valor para codcargo
insert into tb_cargos(codcargo,cargo) values(1,’Diretor’);
insert into tb_cargos(codcargo,cargo) values(2,’Secretária');
insert into tb_cargos(codcargo,cargo) values(3,’Gerente de Informática’);

Se formos criar a sequence usamos o comando abaixo e não será necessário informar um número de
Código de cargo, o mesmo será gerado automaticamente ao inserir dados na tabela Cargos.

CREATE SEQUENCE sqCargos INCREMENT BY 1 START WITH 1 CACHE 5;

insert into CARGOS(codcargo,cargo) values (sqCargos.nextval,'Diretor');


insert into CARGOS(codcargo,cargo) values (sqCargos.nextval,'Secretária');
insert into CARGOS(codcargo,cargo) values (sqCargos.nextval,'Gerente de Informática');

O sqCargos.nextval insere o próximo número da sequencia

Para excluir uma sequence usamos DROP SEQUENCE nome_da_sequence


UTILIZANDO IDENTITY AO INVÉS DE SEQUENCE

CREATE TABLE teste(


codigo NUMBER GENERATED BY DEFAULT AS IDENTITY,
nome varchar2(255) NOT NULL,
PRIMARY KEY(codigo)
);

CREATE TABLE teste(


codigo GENERATED BY DEFAULT AS IDENTITY START WITH 10 INCREMENT BY 10,
nome varchar2(255) NOT NULL ,
PRIMARY KEY(codigo)
);

insert into teste (nome) values ('Jose');


insert into teste (nome) values('Ana');
insert into teste (nome) values('Maria’);

Aqui vão ser inseridos os códigos automáticamente

Codigo nome
1 José
2 Ana
3 Maria
UTILIZANDO IDENTITY AO INVÉS DE SEQUENCE

CREATE TABLE teste(


codigo NUMBER GENERATED BY DEFAULT AS IDENTITY,
nome varchar2(255) NOT NULL,
PRIMARY KEY(codigo)
);

insert into teste (nome) values ('Jose');


insert into teste (nome) values('Ana');
insert into teste (nome) values('Maria’);

Aqui vão ser inseridos os códigos automáticamente

Codigo nome
10 José
20 Ana
30 Maria
Alterando dados de uma tabela
A instrução UPDATE é usada para modificar linhas existentes em
uma tabela.

UPDATE nome_da_tabela
SET nome_da_coluna = novo_valor [, nome_de outa_coluna =
novo_valor] [WHERE lista_de_condição];

update PROFESSOR set SALARIO = 1.1*SALARIO;

update PROFESSOR set SALARIO = 1.1*SALARIO where coddepto=400;

update PROFESSOR set SALARIO = 1.1*SALARIO, NOME=‘JOSE SILVA’


WHERE MATRICULA=222 ; // aqui altera o salario e o nome de um professor
coma a matrícula 222
Alterando dados de uma tabela

Alterando o ano em uma tabela

Atualiza o ano de diversas datas somando 2 ao ano =➔ 2022

UPDATE servicos set data=data+INTERVAL '2' YEAR where extract(year from


data)>2020

Corrige o ano de diversas datas , alterando apenas o ano de datas erradas


ano =➔ 2022

update servicos set data = to_date(to_char(data,'dd-mon')||'-'||'2022','dd-mon-yyyy')


where extract(year from data)>2032
Excluindo linhas de uma tabela

A instrução DELETE é usada para remover linhas de uma tabela.

delete [from] <TABELA> [where <condições>]

delete from PROFESSOR ➔ exclui todos os professores (CUIDADO !)

delete from PROFESSOR where SALARIO <1000


exclui os professores cujo salário seja inferior a 1000

delete from PROFESSOR where SALARIO <1000 and uf=‘BA’


exclui os professores cujo salário seja inferior a 1000 do estado da sigla BA
ANOMALIAS DE BANCO DE DADOS

As anomalias são definidas como "anomalias de inserção, exclusão e modificação"

Anomalias são mudanças em dados que podem gerar uma inconsistência no banco
de dados relacional.

Uma inconsistência é geralmente representada por situações em que dados que


deveriam ser iguais, apresentam valores diferentes em várias tabelas do banco de
dados, quando não é utilizada a chave estrangeira.

Outro exemplo seria exclusão de uma tabela que fornece informações para uma
tabela dependente e poder excluir um dados da mesma, também quando não
usamos chave estrangeira.

Uma anomalia de inserção ao inserir um dado , este pode gerar uma inconsistência
no banco de dados, como a repetição de um RA , numa tabela que não tem chave
primária.
ANOMALIAS DE BANCO DE DADOS
Supondo que sejam criadas as tabelas

create table CARGOS(


codcargo numeric(5) not null,
cargo varchar2(30) not null,
CONSTRAINT CARGOS_codcargo_pk primary key(codcargo)
);

create table FUNCIONARIOS (


matricula numeric(10) not null,
nome varchar2(50) not null,
codcargo numeric(5),
salario numeric(10,2) check (salario>=1200),
sexo char(1) check (sexo IN ('M','F','O')),
email varchar(100) unique,
CONSTRAINT funcionarios_matricula_pk primary key(matricula),
constraint funcionarios_codcargo_fk FOREIGN KEY (codcargo) references CARGOS
(codcargo)
);

CREATE SEQUENCE sqCargos INCREMENT BY 1 START WITH 1 CACHE 5;

CREATE SEQUENCE sqFunc INCREMENT BY 1000 START WITH 1000 CACHE 5;


ANOMALIAS DE BANCO DE DADOS

Supondo que sejam inseridos os seguintes dados na tabela cargos

insert into CARGOS(codcargo,cargo) values (sqCargos.nextval,'Diretor');


insert into CARGOS(codcargo,cargo) values (sqCargos.nextval,'Secretária');
insert into CARGOS(codcargo,cargo) values (sqCargos.nextval,'Gerente Informática');
insert into CARGOS(codcargo,cargo) values (sqCargos.nextval,'Analista de Sistemas');
insert into CARGOS(codcargo,cargo) values (sqCargos.nextval,'Analista Financeiro');
insert into CARGOS(codcargo,cargo) values (sqCargos.nextval,'Analista de RH');
insert into CARGOS(codcargo,cargo) values (sqCargos.nextval,'Vendedor’);
ANOMALIAS DE BANCO DE DADOS

Supondo que sejam inseridos os seguintes dados na tabela Funcionarios

insert into funcionarios(matricula,nome,codcargo,salario,sexo,email)


values(sqFunc.nextval,'Rita Reis',2, 1300,'F', 'rr@abc.com.br');

insert into funcionarios(matricula,nome,codcargo,salario,sexo,email)


values(sqFunc.nextval,'Ana Lemos',1,10000,'F', 'al@abc.com.br');

insert into funcionarios(matricula,nome,codcargo,salario,sexo,email)


values(sqFunc.nextval,'Luis Almeida Marinho',4,3000,'M', 'lam@abc.com.br');
ANOMALIAS DE BANCO DE DADOS - CHAVE PRIMÁRIA

Ao tentar inserir a linha abaixo em Funcionarios vai ocorrer um erro

insert into funcionarios(matricula,nome,codcargo,salario,sexo,email)


values(1000,'Roberto Silva',2, 1200,'M', 'rs@abc.com.br');

Esse erro ocorre pois estamos tentando inserir a matricula de número 1000 que já
existe na tabela funcionários e no campo matrícula o mesmo é chave primária.

CONSTRAINT funcionarios_matricula_pk primary key(matricula)


ANOMALIAS DE BANCO DE DADOS – CHAVE PRIMÁRIA

Ao tentar inserir a linha abaixo em Funcionarios vai ocorrer um erro

insert into funcionarios(nome,codcargo,salario,sexo,email)


values('Roberto Silva',2, 1200,'M', 'rs@abc.com.br');

Esse erro ocorre pois não informamos a matricula que é chave primária que não
permite nulos no campo e nem repetição no mesmo e além disto colocamos na tabela
Funcionarios uma restrição

matricula numeric(10) not null


ANOMALIAS DE BANCO DE DADOS – REGRA DE UM CAMPO

Ao tentar inserir a linha abaixo em Funcionarios vai ocorrer um erro

insert into funcionarios(matricula,nome,codcargo,salario,sexo,email)


values(sqFunc.nextval,'Roberto Silva',2, 1000,'F', 'rs@abc.com.br’);

Esse erro ocorre pois estamos tentando inserir o salario de 1000 quando

Tínhamos restringido o mesmo na linha

salario numeric(10,2) check (salario>=1200)


ANOMALIAS DE BANCO DE DADOS – REGRA DE UM CAMPO

Ao tentar inserir a linha abaixo em Funcionarios vai ocorrer um erro

insert into funcionarios(matricula,nome,codcargo,salario,sexo,email)


values(sqFunc.nextval,'Roberto Silva',2, 1200,'N', 'rs@abc.com.br');

Esse erro ocorre pois estamos tentando inserir o SEXO N , quando

tínhamos restringido o mesmo na linha

sexo char(1) check (sexo IN ('M','F','O’))

Para sexo serão aceitos apenas M , F , O


ANOMALIAS DE BANCO DE DADOS - UNIQUE

Ao tentar inserir a linha abaixo em Funcionarios vai ocorrer um erro

insert into funcionarios(matricula,nome,codcargo,salario,sexo,email)


values(sqFunc.nextval,'Roberto Silva',2, 1200,’M', ‘rr@abc.com.br');

Esse erro ocorre pois estamos tentando inserir o email rr@abc.com.br

tínhamos restringido o mesmo na linha

email varchar(100) unique,

Sendo que esse email já estava sendo utilizado para Rita Reis
ANOMALIAS DE BANCO DE DADOS – CHAVE ESTRANGEIRA

Ao tentar inserir a linha abaixo em Funcionarios vai ocorrer um erro

insert into funcionarios(matricula,nome,codcargo,salario,sexo,email)


values(sqFunc.nextval,'Roberto Silva',20, 1200,'M', 'rs@abc.com.br');

Esse erro ocorre pois estamos tentando inserir o ´código de cargo 20


Sendo que esse código não existe na tabela cargos e fizemos a seguinte restrição,
utilizando chave estrangeira.

constraint funcionarios_codcargo_fk FOREIGN KEY (codcargo) references CARGOS

Tendo uma chave estrangeira , a mesma impede que possamos inserir um Código na
tabela funcionarios que não existe na tabela cargos. No caso a tabela mãe é a tabela
cargos e a tabela fuincionarios depende dos códigos da mesma.
ANOMALIAS DE BANCO DE DADOS – CHAVE ESTRANGEIRA
Ao tentar excluir o codcargo 1 , vai ocorrer um erro delete from cargos where codcargo=1

Esse erro ocorre pois estamos excluir um cargo da tabela cargos que esta sendo utilizado na tabela
funcionários. Se algum código de cargo não estiver sendo utilizado em uma tabela que faz uma
chave estrangeira, a exclusão será permitida.

Não podemos esquecer que temos uma chave estrangeira em Funcionarios que serve para manter
a integridade referencial entre as tabelas.

constraint funcionarios_codcargo_fk FOREIGN KEY (codcargo) references CARGOS (codcargo)

Se fossemos excluir a Ana Lemos de funcionarios que usa o codcargo 1, não ocorreria o erro, pois
a tabela funcionarios é filha de cargos.
ANOMALIAS DE BANCO DE DADOS – CHAVE ESTRANGEIRA
Ao tentar alterar um código da tabela cargos que esta sendo usado na tabela funcionários , ocorre um erro,
por conta da chave estrangeira, e na tabela funcionários acabaria ficando um código de cargo que não
existiria mais na tabela cargos

update cargos set codigo=13 where codigo=1

Aqui estamos tentando alterar o código 1 da tabela cargos pelo 13


ANOMALIAS DE BANCO DE DADOS – CHAVE ESTRANGEIRA
Se tentarmos alterar um codcargo da tabela funcionários por outro que não exista em cargos, vai dar um
erro, por conta da chave estrangeira

update funcionarios set codcargo=13 where codcargo=1


Aquí estaríamos tentando alterar o codcargo 1 de funcionarios pelo 13 que ainda não existe em cargos

Caso fossemos alterar o codcargo 1 de cargos pelo codcargo 5, a acção seria perfeitamente possível, pois
o mesmo existe na tabela cargos

update funcionarios set codcargo=5 where codcargo=1


COMANDO SELECT – CONSULTAS TABELAS
Comando para seleção (recuperação) de dados em uma tabela.

Na lista de colunas, deverá ser citada cada uma das colunas separadas por vírgula
(,) .

SELECT NOME, SALARIO FROM FUNCIONARIOS


COMANDO SELECT – CONSULTAS TABELAS
A lista de colunas pode ser substituída por asterisco (*), que indica a
exibição de todas as colunas na sequencia que foram criados os campos nas tabelas

SELECT * FROM FUNCIONARIOS


COMANDO SELECT – CONSULTAS TABELAS
Em algumas situações o nome do cabeçalho de uma coluna pode apresentar pouco significado. Nestas
situações pode ser utilizado um ‘apelido’ para a coluna.

O ‘apelido’ é definido logo em seguida ao nome da coluna com um espaço ou utilizando a palavra AS. É
recomendável inserir o nome do ‘apelido’ entre aspas duplas ("). Caso o apelido tenha espaço, é obrigatório o
uso de aspas duplas (").

SELECT nome “Nome do Funcionario”, Salario, codcargo “Cod Cargos” from funcionários
OU
select nome AS "NOME DO FUNCIONARIO", Salario, codcargo AS "COD. CARGO" from funcionarios
COMANDO SELECT DISTINCT – CONSULTAS TABELAS
Utilizado quando desejamos buscar dados de uma tabela sem repetição num determinado campo. Para ele
funcionar corretamente, ele tem que ser aplicado a um unico campo de uma tabela

select distinct(UF) from funcionários

Se o distinct for aplicado a mais de um campo da tabela, ele trará todas as linhas da tabela

select distinct(UF) , nome from funcionarios


SELECT COM ORDER BY – CONSULTAS ORDENADAS TABELAS

A expressão ORDER BY é utilizada quando se pretende exibir os registros em uma determinada ordem, seja
esta crescente (ASC - default) ou decrescente (DESC). Caso a expressão não esteja presente,
os registros serão exibidos na ordem em que foram inseridos na tabela.

Os campos que constam na expressão ORDER BY não devem obrigatoriamente estarem presentes na
expressão SELECT. Caso estejam presentes, pode-se utilizar números indicando que a ordenação
será feira por determinado campo de acordo com a ordem do select.

Select nome, uf, salario from funcinarios order by nome

Equivale a

Select nome, uf, salario from funcinarios order by nome asc


SELECT COM ORDER BY – CONSULTAS ORDENADAS TABELAS

Em ordem decrescente de qualquer campo, basta usar a palavra desc

Select nome, uf, salario from funcinarios order by nome desc


SELECT COM ORDER BY – CONSULTAS ORDENADAS TABELAS

É possível ordenar pela posição do campo no select , usando um número

select nome, uf, salario from funcionarios order by 3 desc

Equivale a select nome, uf, salario from funcionarios order by salario desc
SELECT COM ORDER BY – CONSULTAS ORDENADAS TABELAS

Pode utilizar mais colunas para compor uma ordenação iniciando pela primeira , dentro desta vai ser ordenado
pela próxima coluna e assim sucessivamente.

Ordenado agora pela UF em ordem crescente e nome em ordem crescente

select uf,nome, salario from funcionarios order by uf asc , nome asc


SELECT COM ORDER BY – CONSULTAS ORDENADAS TABELAS

Pode utilizar mais colunas para compor uma ordenação iniciando pela primeira , dentro desta vai ser ordenado
pela próxima coluna e assim sucessivamente.

Ordenado agora pela UF em ordem crescente e salario em ordem decrescente

select uf, salario, nome from funcionarios order by uf asc , salario desc
SELECT COM ORDER BY – CONSULTAS ORDENADAS TABELAS

Pode utilizar mais colunas para compor uma ordenação iniciando pela primeira , dentro desta vai ser ordenado
pela próxima coluna e assim sucessivamente.

Ordenado agora pelo nome em ordem crescente e salario em ordem decrescente

select nome, uf, salario from funcionarios order by nome asc, salario desc
SELECT SELECIONANDO A QUANTIDADE DE LINHAS

As vezes você não está interessado em ver o resultado como um todo, mas sim, alguma parte do resultado.
Para isto, o Oracle utiliza de uma pseudo-coluna conhecida como ROWNUM a partir do resultado.

select * from (select dtnasc, nome from funcionarios order by dtnasc) WHERE ROWNUM <= 4;

Equivale a

select dtnasc , nome from funcionarios order by dtnasc fetch first 4 rows Only

Sé serão exibidos quatro linhas da tabela


SELECT UTILIZANDO CONDIÇÕES

Existem vários operadores de comparação que pode ser usados para a restrição do número
de resultados, ou seja, podem ser utilizadas uma ou mais condições para que sejam exibidas
apenas as linhas que atendas a essas condições.
SELECT UTILIZANDO CONDIÇÕES

Um exemplo de uso da equalidade é a busca dos funcionarios de um determinado


departamento, por exemplo , buscar todos os funcionários de código de departamento 400:

select nome, salario , codcargo from funcionarios where coddepto=400

Podemos ordenar essa consulta (query)

select nome, salario , codcargo from funcionarios where coddepto=400 order by nome
SELECT UTILIZANDO CONDIÇÕES

Um exemplo de uso da equalidade é a busca dos funcionarios com um determinado nome.


Esse nome tem que ser exatamente igual ao que esta na base de dados

select nome, salario , codcargo from funcionarios where nome= 'Flavio Gama Santana’

select nome, salario , codcargo from funcionarios where uf='SP' order by nome
SELECT UTILIZANDO CONDIÇÕES

Podemos procurar, também pelos diferentes de algo

select uf ,nome, salario , codcargo from funcionarios where uf<>'SP' order by uf


SELECT UTILIZANDO CONDIÇÕES

O operador LIKE é usado quando se deseja obter colunas de um registro que sigam um
determinado padrão pré-especificado. Quando se quer saber o nome de todos os funcionários
cujo nome começa com ‘João’ ou termina com ‘Silva’, utiliza-se o operador LIKE.

% indica quaisquer caracteres


O _ indica que naquela posição pode qualquer caractere

select uf ,nome, salario , codcargo from funcionarios where nome like 'Ana%’
Seleciona todos os nomes que se iniciam com Ana

select uf ,nome, salario , codcargo from funcionarios where nome like '_a%’
Seleciona todos os nomes que tenham a letra a na segunda posição
SELECT UTILIZANDO CONDIÇÕES

O operador LIKE é usado quando se deseja obter colunas de um registro que sigam um
determinado padrão pré-especificado. Podemos usar o % oque se se deseja pesquisar% ou
ainda
%o que se deseja pesquisar

select uf ,nome, salario , codcargo from funcionarios where nome like '%ana%’
Seleciona todos os nomes que contem a palavra ana em qualquer posição

select uf ,nome, salario , codcargo from funcionarios where nome like '%ana’
Seleciona todos os nomes que terminem com a palavra ana
SELECT UTILIZANDO CONDIÇÕES

Um exemplo de uso da relação de maior, maior ou igual, menor ou menor ou igual é o busca de
um funcionario que possui um salário maior que um certo valor e menor do que outro.

select * from funcionarios where SALARIO > 2000


Busca os que possuem salário maior que 2000

select * from funcionarios where SALARIO >= 2000


Busca os que possuem salário maior ou igual a 2000

select * from funcionarios where SALARIO < 2000


Busca os que possuem salário menor que 2000

select * from funcionarios where SALARIO <= 2000


Busca os que possuem salário menor ou igual a 2000
SELECT UTILIZANDO CONDIÇÕES
select * from funcionarios where SALARIO >= 3000 order by nome
Busca os que possuem salário maior ou igual a 3000

select nome,codcargo,salario from funcionarios where codcargo=4 order by salario desc


Busca os funcionários de cargo igual 4 em ordem decrescente de salario

select nome,salario from funcionarios where codcargo=4 order by salario desc


Busca os funcionários de cargo igual 4 em ordem decrescente de salario não sendo necessário ter
o codcargo no select
SELECT UTILIZANDO CONDIÇÕES
select * from funcionarios where not coddepto = 500
Equivalente a select * from funcionarios where coddepto <> 500

Busca os que possuem os funcionários com código de departamento coddepto diferente de 500

select * from funcionários where uf is NULL


Busca os funcionários onde a uf não foi preenchida
No caso abaixo, todas as UF estão preenchidas
SELECT UTILIZANDO CONDIÇÕES COM DATAS
No Oracle, ‘07-06-1994’ não é uma data, mas sim, uma string (UM TEXTO). Portanto, como representar uma
data para utilizar os operadores aprendidos?
Basta utilizar a função to_date

select nome, dtnasc from funcionarios where dtnasc >= to_date('03/10/2000', 'dd/mm/yyyy’) order by dtnasc
SELECT UTILIZANDO CONDIÇÕES COM DATAS
No Oracle o sysdate é a data de hoje obtida do servidor
select nome, dtnasc from funcionarios where dtnasc <= sysdate order by dtnasc
No caso abaixo, o select vai trazer todas as linhas da tabela funcionarios
COMANDO SELECT COM FUNÇÕES DE CONVERSÕES DE DADOS
UTILIZANDO FORMATAÇÕES NOS CAMPOS DE NÚMEROS E DATAS
UTILIZANDO FORMATAÇÕES NOS CAMPOS DE NÚMEROS E DATAS
SELECT UTILIZANDO FORMATAÇÕES NOS CAMPOS DE DATAS

A função TO_CHAR tem por objetivo converter um número ou uma data para o formato string de
caractere. Além desse fim, ela acaba sendo muito utilizada para formatação visual de dados.

select NOME, TO_CHAR(DTNASC,'DD/MM/YYYY') from FUNCIONARIOS where DTNASC >=


to_date('03/10/2005', 'dd/mm/yyyy')

select NOME, TO_CHAR(DTNASC,'DD/MM/YYYY’) “DATA” from FUNCIONARIOS where


DTNASC >= to_date('03/10/2005', 'dd/mm/yyyy')
SELECT UTILIZANDO FORMATAÇÕES NOS CAMPOS DE DATAS

SELECT NOME ,TO_CHAR(DTNASC,'YYYY') AS ANO FROM FUNCIONARIOS ORDER BY ANO DESC


SELECT UTILIZANDO FORMATAÇÕES NOS CAMPOS DE DATAS

SELECT NOME ,TO_CHAR(DTNASC,'DD/MM/YYYY') AS DATA_NASC , TO_CHAR(DTNASC,'DAY') AS


DIASEMANA FROM FUNCIONARIOS ORDER BY DTNASC
SELECT UTILIZANDO FORMATAÇÕES NOS CAMPOS DE DATAS

SELECT NOME ,TO_CHAR(DTNASC,'MONTH') AS MES , TO_CHAR(DTNASC,'DY') AS DIASEMANA FROM


FUNCIONARIOS ORDER BY DTNASC
SELECT UTILIZANDO FORMATAÇÕES NOS CAMPOS DE DATAS

SELECT NOME,TO_CHAR(DTNASC,'DD/MM/YYYY') FROM funcionarios where to_char(DTNASC,'yyyy')=2000

Ou usando a função extract

SELECT * FROM funcionarios WHERE extract(year from dtnasc) = 2000

Usando o Extract para mostrar as datas com mês 7 e ano 2000

SELECT * FROM funcionarios WHERE extract(month from dtnasc) = 7 and extract (year
from dtnasc) = 2000;
SELECT UTILIZANDO FORMATAÇÕES NOS CAMPOS DE VALORES

select nome,dtnasc, to_char(salario,'l999g999d00') as "Salario" from funcionários order by salario


SELECT UTILIZANDO FORMATAÇÕES E CALCULOS

Estamos calculando o salario de férias com um aumento de 1,3

select nome,TO_CHAR(salario, 'FML09G999D00') "salario", to_char(salario *1.3 , 'FML09G999D00') "Salário de Férias"


FROM funcionarios;
SELECT UTILIZANDO FORMATAÇÕES E CALCULOS

Estamos aqui um INSS hipotético com 11% sobre o valor do salario para pessoas que ganham acima de 2000

select nome,TO_CHAR(salario, '9g999g999d00') "salario", to_char(salario *0.11 , '99g999d00') "INSS"


from funcionarios where salario>=2000 order by nome;
SELECT UTILIZANDO FORMATAÇÕES E CALCULOS
Se tivermos números com casas decimais podemos arrendá-los

O Dual aqui só mostra na tela sem pegar dados de tabelas

select round(46.53) from dual; 47


select round(46,33) from dual; 46
select round(46.537823,2) from dual; 46,54

select nome,salario, round(salario*0.001,1) "Comissao" from


SELECT UTILIZANDO FORMATAÇÕES E CALCULOS
Aqui será calculada a idade dos funcionários pegando a data do sistema, que varia dia a dia

SELECT nome, to_char(dtnasc,'dd/mm/yyyy') "Nascimento" , round((sysdate-dtnasc)/365.25) "Idade"


FROM funcionarios order by dtnasc desc
SELECT UTILIZANDO MAIS DE UM CAMPO COMO FILTRO
Operadores lógicos

AND

Às vezes, no português falado dizemos, por exemplo, que queremos todos os funcionários que estão no
departamento 200 e que ganham mais de 3.000.

A consulta abaixo faz exatamente isto:

select nome, salario from funcionarios where coddepto=200 and salario>2000

OR

Existem outros casos que queremos todos os funcionários que estão no departamento 200 ou que
ganham mais de 2000

A consulta abaixo faz exatamente isto:

select nome, salario from funcionarios where coddepto=200 or salario>2000


SELECT UTILIZANDO MAIS DE UM CAMPO COMO FILTRO

Podemos buscar os funcionários que tenham salario entre 3000 e 10000 , incluído os
mesmos

select nome, salario from funcionarios where salario>=3000 and salario<=10000 order
by nome
SELECT UTILIZANDO MAIS DE UM CAMPO COMO FILTRO

O operador BETWEEN permite testar se um determinado campo assume o valor dentro


de um intervalo especificado. É utilizado por ser mais prático que o teste de >= e <=.

Ou seja escrever , os comando abaixo se equivalem

select nome, salario from funcionarios where salario>=3000 and salario<=10000 order by
nome
Ou
select nome, salario from funcionarios where salario between 3000 and 10000 order by
nome
SELECT UTILIZANDO MAIS DE UM CAMPO COMO FILTRO

Caso queiramos os funcionários que não se enquadram num intervalo de valores


ou datas, basta acrescentar o operador lógico NOT:

select * from RH.EMPREGADO where not SALARIO between 5000 and 10000

select nome, salario from funcionarios where not salario between 3000 and 10000 order
by nome
SELECT UTILIZANDO MAIS DE UM CAMPO COMO FILTRO

IN e NOT IN
O operador IN e NOT IN são utilizados para testar uma condição de um
grupo de valores.

IN é equivalente ao operador =ANY, pois ambos retornam verdadeiro se um valor


existe em uma lista ou em uma subquery.

NOT IN é equivalente ao operador !=ALL, pois ambos retornam verdadeiro se o


valor não existe em uma lista ou em uma subquery
SELECT UTILIZANDO MAIS DE UM CAMPO COMO FILTRO

Para retornar os usuário que estão nos estados de SP e RJ , poderíamos escrever

select uf, nome, salario from funcionarios where UF='SP' OR UF=‘RJ’ order by uf

Ou

select uf, nome, salario from funcionarios where uf in ('SP','RJ’) order by uf


SELECT UTILIZANDO MAIS DE UM CAMPO COMO FILTRO

Para retornar os usuário que estão em uma determinada lista de departamentos


utilizamos o IN ou any

select coddepto, nome, salario from funcionarios where coddepto in(200,400) order by
coddepto

Ou

select coddepto, nome, salario from funcionarios where coddepto= any(200,400) order
by coddepto
SELECT UTILIZANDO MAIS DE UM CAMPO COMO FILTRO

Para retornar os usuário que não estão em uma determinada lista de departamentos
utilizamos o NOT IN ou !ALL

select coddepto, nome, salario from funcionarios where coddepto not in (200,400)
order by coddepto

Ou

select coddepto, nome, salario from funcionarios where coddepto != all (200,400) order
by coddepto
SELECT UTILIZANDO VÁRIAS TABELAS

Um banco de dados possui várias tabelas que armazenam dados.

A capacidade de junção de duas ou mais tabelas e o acesso às informações é a


principal força dos banco de dados relacionais.

Usando a instrução SELECT podemos escrever consultas avançadas que satisfazem


os requisitos dos usuários.
SELECT UTILIZANDO VÁRIAS TABELAS

A instrução SELECT possui as seguintes cláusulas obrigatórias:

SELECT
uma lista de colunas, expressões, funções e afins.
FROM
diz em qual(is) tabela(s) irá buscar as informações desejadas.

Na cláusula WHERE, você define a relação entre as tabelas listadas na cláusula


FROM usando operadores de comparação ou seja colocamos as colunas comuns
entre as tabelas

Ao invés de utilizarmos o WHERE, podemos indicar a correspondência entre duas


tabelas utilizando a cláusula JOIN

- o campo comum que liga uma tabela com outra tem quer do mesmo tipo (numeric,
texto,..), não podemos um com numeric e o outro com varchar

- para fazer o relacionamento entre as tabelas não é obrigatório que os campos


sejam chaves primaria ou estrangeira
SELECT UTILIZANDO VÁRIAS TABELAS

Na consulta abaixo vamos pegar nome e salario da tabela funcionários e cargo da


tabela cargos, tendo em comum o campo codcargo de ambas as tabelas

select nome, cargo, salario from funcionarios,cargos where


funcionarios.codcargo=cargos.codcargo;
SELECT UTILIZANDO VÁRIAS TABELAS

Na consulta abaixo vamos pegar nome e salario da tabela funcionários e cargo da


tabela cargos, tendo em comum o campo codcargo de ambas as tabelas e uma
condição de trazer de funcionários somente cargo = ‘Vendedor’

select nome, cargo, salario from funcionarios,cargos


where funcionarios.codcargo=cargos.codcargo and cargo= 'Vendedor'
SELECT UTILIZANDO VÁRIAS TABELAS

Na consulta abaixo vamos pegar nome e salario da tabela funcionários e cargo da


tabela cargos, tendo em comum o campo codcargo de ambas as tabelas e uma
condição de trazer de funcionários com salario maior que 2000 ordenados por nome

select nome, cargo, salario from funcionarios,cargos


where funcionarios.codcargo=cargos.codcargo and salario>2000 order by nome
SELECT UTILIZANDO VÁRIAS TABELAS

Na consulta abaixo vamos pegar nome e salario da tabela funcionários e cargo da


tabela cargos, tendo em comum o campo codcargo de ambas as tabelas e uma
condição de trazer de funcionários com salario maior que 2000 e menor que 6000
ordenados por nome

select nome, cargo, salario from funcionarios,cargos


where funcionarios.codcargo=cargos.codcargo and salario>2000 and salario<6000
order by nome
SELECT UTILIZANDO VÁRIAS TABELAS
Na consulta abaixo vamos pegar nome e salario da tabela funcionários e
departamento da tabela departamentos, tendo em comum o campo coddepto de
ambas as tabelas .

select depto,nome,salario from departamentos,funcionarios


where departamentos.coddepto=funcionarios.coddepto;
SELECT UTILIZANDO VÁRIAS TABELAS
Na consulta abaixo vamos pegar nome e salario da tabela funcionários e departamento da
tabela departamentos, tendo em comum o campo coddepto de ambas as tabelas , utilizando
um apelido para os nomes das tabelas.

select depto,nome,salario from departamentos d,funcionarios f


where d.coddepto=f.coddepto;

Ou select d.depto,f.nome,f.salario from departamentos d,funcionarios f


where d.coddepto=f.coddepto;
SELECT UTILIZANDO VÁRIAS TABELAS
Na consulta abaixo vamos pegar campos de três tabelas diferente , pegando os campos
nome e salario da tabela funcionários, cargo da tabela cargos e departamento da tabela
departamentos, tendo em comum o campo coddepto de ambas as tabelas , e codcargos
utilizando um apelido para os nomes das tabelas.

select nome , depto , cargo, salario from funcionarios f, departamentos d,cargos c


where f.codcargo=c.codcargo and f.coddepto=d.coddepto
SELECT UTILIZANDO VÁRIAS TABELAS USANDO INNER JOIN
Na consulta abaixo vamos pegar nome e salario da tabela funcionários e cargo da tabela
cargos, tendo em comum o campo codcargo de ambas as tabelas e uma condição de trazer
de funcionários com salario maior que 1000 e menor que 4000

select nome, cargo, salario from funcionarios


INNER JOIN cargos on funcionarios.codcargo=cargos.codcargo
where salario>1000 and salario<4000
SELECT UTILIZANDO VÁRIAS TABELAS USANDO INNER JOIN
Na consulta abaixo vamos pegar campos de três tabelas diferente , pegando os campos
nome e salario da tabela funcionários, cargo da tabela cargos e departamento da tabela
departamentos, tendo em comum o campo coddepto de ambas as tabelas , e codcargos

select nome, depto, cargo, salario from funcionarios


INNER JOIN cargos on funcionarios.codcargo=cargos.codcargo
inner join departamentos on funcionarios.coddepto=departamentos.coddepto
where salario>1000 and salario<4000
SELECT UTILIZANDO VÁRIAS TABELAS USANDO NATURAL JOIN

A NATURAL JOIN é uma operação JOIN que cria uma cláusula de associação com base
nas colunas comuns nas duas tabelas diferentes que estão sendo combinadas, e que tem
um campo em comum entre elas. O NATURAL JOIN funciona muito bem quando uma
coluna é chave estrangeira da outra tabela.

Não é possível especificar TABELA.CAMPO dentro de um NATURAL JOIN (erro ORA-


00942 – A tabela ou view não existe);

select depto ,nome from funcionarios natural join departamentos order by depto,nome
SELECT UTILIZANDO VÁRIAS TABELAS USANDO NATURAL JOIN

Usando duas tabelas, localizar os funcionários nascidos entre 01/03/2006 a 31/03/2006


listando cargo, nome, dtnasc

select cargo, nome , dtnasc from


funcionarios natural join cargos
where dtnasc between to_date('01/03/2006','dd/mm/yyyy') and
to_date('31/03/2006','dd/mm/yyyy')
order by cargo, nome;
SELECT UTILIZANDO VÁRIAS TABELAS USANDO NATURAL JOIN

Segue um Natural Join com três tabelas

select depto ,cargo, nome from funcionarios natural join departamentos natural join cargos
order by depto,cargo, nome
SELECT UTILIZANDO VÁRIAS TABELAS USANDO USING

A clausula USING deve ser utilizada, quando você tem várias colunas com o mesmo nome
e precisa escolher o campo de junção. Ainda é um facilitador automático, mas permite que
você informe o campo comum das tabelas que servirá para unificar os registros.

Em alguns bancos de dados mais antigos as vezes o modelo não apresenta todas as
colunas com nomes bem definidos. Pode ocorrer de algumas tabelas terem mais colunas
com o mesmo nome e o mesmo tipo de dados sem serem as chaves primárias e
estrangeiras, ou a coluna comum entre as tabelas não serem do mesmo tipo de dados, ou
ainda as tabelas podem conter colunas com o mesmo nome e o mesmo tipo de dados que
você não queira como sendo pontos da relação entre as tabelas, então nesses casos
devemos usar o using e escolher o campo de junção entre as tabelas

select depto ,cargo, nome from funcionarios natural join departamentos natural join cargos
order by depto,cargo, nome
SELECT UTILIZANDO VÁRIAS TABELAS USANDO USING

Aqui o campo coddepto será utilizado para ligar as tabelas funcionários,departamentos

select depto , nome from funcionarios join departamentos using (coddepto) order by depto,
nome
SELECT UTILIZANDO VÁRIAS TABELAS USANDO USING

Aqui o campo coddepto será utilizado para ligar as tabelas funcionários/departamentos e o


campo codcargo será utilizado para ligar as tabelas funcionários / cargos

select depto , cargo, nome from funcionarios


join departamentos using (coddepto)
join cargos using (codcargo)
order by depto, cargo, nome
SELECT UTILIZANDO VÁRIAS TABELAS USANDO INNER JOIN

INNER JOIN seleciona todas as linhas de ambas as tabelas participantes, desde que ocorra uma
correspondência entre as colunas. Um INNER JOIN é o mesmo que JOIN, combinando linhas de
duas ou mais tabelas. Após ANSI SQL de 1992, a clausula INNER é opcional .

O INNER JOIN junta as tabelas de acordo com a correspondência determinada como critério no
operador ON.

No INNER JOIN é feito o produto cartesiano dos dados e os dados que não correspondem à
condição ON são excluídos do conjunto de resultados. A maioria dos DBAs gostam da forma que
o INNER JOIN separa as ligações entre as tabelas usando a cláusula ON e permitindo que o
WHERE fique apenas como filtro dos elementos individuais da consulta.

select cargo, nome , salario from


funcionarios join cargos
on funcionarios.codcargo= cargos.codcargo
where uf='SP' order by cargo, nome

Ou

select c.cargo, f.nome , f.salario from


funcionarios f join cargos c
on f.codcargo= c.codcargo
where uf='SP' order by cargo, nome
SELECT UTILIZANDO VÁRIAS TABELAS USANDO INNER JOIN

Dessa forma o join poder ser escrito explicitamente ou implicitamente.

select cargo, nome , salario from


funcionarios ,cargos
where funcionarios.codcargo= cargos.codcargo
and uf='SP' order by cargo, nome

ou

select cargo, nome , salario from


funcionarios join cargos
on funcionarios.codcargo= cargos.codcargo
where uf='SP' order by cargo, nome
SELECT UTILIZANDO VÁRIAS TABELAS USANDO INNER JOIN

Localizar os funcionários listando nome, cargo, dtnasc que nasceram no mês de março de 2006

select cargo, nome , dtnasc from


funcionarios ,cargos
where funcionarios.codcargo= cargos.codcargo
and dtnasc between to_date('01/03/200','dd/mm/yyyy') and to_date('31/03/2006','dd/mm/yyyy')
order by cargo, nome;

ou

select cargo, nome , salario from


funcionarios join cargos
on funcionarios.codcargo= cargos.codcargo
where dtnasc between to_date('01/03/2006','dd/mm/yyyy') and to_date('31/03/2006','dd/mm/yyyy')
order by cargo, nome
SELECT UTILIZANDO VÁRIAS TABELAS USANDO INNER JOIN

INNER JOIN com três tabelas Funcionarios , Departamentos, Cargos

select depto, cargo, nome , salario from funcionarios


join departamentos
on funcionarios.coddepto=departamentos.coddepto
join cargos
on funcionarios.codcargo=cargos.codcargo
where uf='SP' order by depto, cargo, nome

Ou

select d.depto, c.cargo, f.nome , f.salario


from funcionarios f join departamentos d
on f.coddepto=d.coddepto
join cargos c
on f.codcargo=c.codcargo
where uf='SP' order by depto,cargo, nome;
SELECT UTILIZANDO VÁRIAS TABELAS USANDO NO-EQUIJOIN

Tem como base o relacionamento entre duas tabelas através de um grupo ou limites
máximo e mínimos. Na maioria das vezes, não se trata de um relacionamento entre
chave primária e chave estrangeira. Todo o relacionamento que não é construído
utilizando o operador de igualdade é denominado de NO-EQUIJOIN.
Para exemplificar você deve criar a tabela GRADES e inserir alguns registros.

create table grades(


nivel char,
limite_menor number(8),
limite_maior number(8),
CONSTRAINT grades_nivel_pk PRIMARY KEY (nivel)
);

INSERT INTO grades (nivel,limite_menor,limite_maior) VALUES ('A',1000,2999);


INSERT INTO grades (nivel,limite_menor,limite_maior) VALUES ('B',3000,5999);
INSERT INTO grades (nivel,limite_menor,limite_maior) VALUES ('C',6000,9999);
INSERT INTO grades (nivel,limite_menor,limite_maior) VALUES ('D',10000,14999);
INSERT INTO grades (nivel,limite_menor,limite_maior) VALUES ('E',15000,24999);
INSERT INTO grades (nivel,limite_menor,limite_maior) VALUES ('F',25000,40000);
SELECT UTILIZANDO VÁRIAS TABELAS USANDO NO-EQUIJOIN
Agora você está pronto para testar NO-EQUIJOIN. O objetivo é relacionar o salário do empregado
com a faixa uma faixa salarial e retornar à classificação do empregado. O funcionário que estiver
com grade_level 'A' está na menor faixa salarial da empresa, enquanto os funcionários que
estiverem na faixa 'F' são os que estão na maior faixa salarial.

SELECT f.nome AS “Nome do Funcionário", TO_CHAR(f.salario,'fml09G999D00') AS "Salário",


g.nivel AS "Faixa Salarial" FROM funcionarios f, grades g
WHERE f.salario BETWEEN g.limite_menor AND g.limite_maior ORDER BY NOME;
SELECT UTILIZANDO VÁRIAS TABELAS USANDO NO-EQUIJOIN
A NO-EQUIJOIN também pode ser construída tendo como base uma JOIN, como no exemplo:

SELECT f.nome AS "nome do Funcionário",


TO_CHAR(f.salario,'fml09G999D00') AS "Salário",
g.nivel AS "Faixa Salarial"
FROM funcionarios f JOIN grades g
ON f.salario
BETWEEN g.limite_menor AND g.limite_maior
ORDER BY nome;
SELECT UTILIZANDO VÁRIAS TABELAS USANDO LEFT JOIN
A LEFT OUTER JOIN ou apenas LEFT JOIN é o argumento que permite unir duas tabelas
solicitando que todos os dados de uma tabela participem do resultado independente de existir um
relacionamento com a outra tabela.

Nesse caso a query traz todos os registros de funcionários com os respectivos departamentos,
pois na tabela funcionários so existem os coddepto que existem na tabela departamentos, devido
a chave estrangeira. Caso não existisse a chave e fosse colocado em funcionários um código de
departamento que não existisse em Departamentos , a query listaria essa linha também, o que
não ocorre num inner join

select nome, depto from funcionarios left join departamentos


on funcionarios.coddepto=departamentos.coddepto order by
depto,nome

Ou

select nome, depto from funcionarios , departamentos


where funcionarios.coddepto(+) = departamentos.coddepto
coddepto order by depto,nome
SELECT UTILIZANDO VÁRIAS TABELAS USANDO LEFT JOIN
Se na tabela Funcionarios não existisse a chave estrangeira, poderíamos cadastrar diversos
coddepto que não existem na tabela departamentos e ao utilizar o left join , na coluna depto iria
aparecer null, pois não seria encontrado correspondência. Se fosse utilizado o inner join ao invés
de left join são seriam exibidas as linhas de funcionários que tem correspondente em
Departamentos

Tabela Funcionarios
Tabela Departamentos

Não encontrou um coddepto


correspondente na tabela
Departamentos

select nome, depto from funcionarios left join departamentos


on funcionarios.coddepto=departamentos.coddepto order by
depto,nome

22 Zito Costa Null


SELECT UTILIZANDO VÁRIAS TABELAS USANDO RIGHT JOIN
A RIGHT OUTER JOIN ou apenas RIGHT JOIN é o argumento que permite unir duas tabelas
solicitando que todos os dados de uma tabela participem do resultado independente de existir um
relacionamento com a outra tabela.

Nesse caso a query traz todos os registros de funcionários com os respectivos departamentos, e
traz , também, na linha 11 o novo departamento com null na coluna nome, pois ainda não foi
utilizado esse departamento ainda por nenhum funcionario

select * from user_sequences

insert into departamentos values


(sqdepartamentos.nextval, ‘SEGURANÇA’)

select nome, depto from funcionarios right join departamentos


on funcionarios.coddepto=departamentos.coddepto order by
depto,nome

Ou

select nome, depto from funcionarios , departamentos


where funcionarios.coddepto = departamentos.coddepto(+)
order by depto,nome
SELECT UTILIZANDO FUNÇÕES DE GRUPOS

As funções de grupo operam sobre um conjunto de linhas para dar um único resultado por grupo

▪ Funções de agregação NÃO PODEM aparecer na cláusula WHERE de uma instrução SELECT.
Exemplo select nome, salario where salario=max(salario);

▪ O atributo DISTINCT pode fazer parte de uma função de grupo para solicitar que se considere valores
não duplicados.

▪ Todas as funções de grupo exceto o COUNT(*) ignoram os valores nulos.

▪ Quando utilizada em um SELECT, geralmente requer uma cláusula GROUP BY, porém quando a
mesma não é especificada, o agrupamento padrão é por todo o resultado.
SELECT UTILIZANDO FUNÇÕES DE GRUPOS

AVG (média aritmética):

Retorna a média dos valores de uma determinada coluna.

Ex.: select avg(SALARIO) from funcionarios where coddepto=500;

select avg(SALARIO)from funcionarios where coddepto=500;

select avg(SALARIO)"Média Salarial" from funcionarios where coddepto=500;


SELECT UTILIZANDO FUNÇÕES DE GRUPOS

SUM (soma de valores):

Retorna a soma dos valores de uma determinada coluna.

Ex.: select sum(SALARIO) “Total Salários” from funcionários

Seleciona a soma dos salários de todos os empregados

Seleciona a soma dos salários, formatado de todos os empregados

select to_char(sum(SALARIO),'9g999g999d99') as "Total de Salários" from funcionarios ;


SELECT UTILIZANDO FUNÇÕES DE GRUPOS

MAX (maior valor):

Retorna o maior valor de uma determinada coluna.

Exemplo: select max(SALARIO) “Maior Salario” from funcionarios

Seleciona o maior salário de todos os empregados

Seleciona o maior dos salários, formatado

select to_char(max(SALARIO),'9g999g999d99') as "Maior Salário" from funcionarios ;


SELECT UTILIZANDO FUNÇÕES DE GRUPOS

MIN (menor valor):

Retorna o menor valor de uma determinada coluna.

Exemplo: select min (SALARIO) “Menor Salário” from funcionários

Seleciona o menor salário de todos os empregados

Seleciona o menor dos salários, formatado

select to_char(mix(SALARIO),'9g999g999d99') as "Menor Salário" from funcionarios ;


SELECT UTILIZANDO FUNÇÕES DE GRUPOS

COUNT (contagem)

Retorna o número de linhas ou de colunas do resultado.

Pode vir a ser distinta com a utilização do operador DISTINCT.

count(*) Retorna o número de linhas do resultado.

count() ou count(ALL ) Retorna o número de colunas do resultado.

count(DISTINCT ) Retorna o número de colunas distintas do resultado.


SELECT UTILIZANDO FUNÇÕES DE GRUPOS

COUNT (contagem)

Exemplos:

Seleciona o número de funcionarios.


select count(*) from funcionários

Seleciona o número de funcionários do estado de SP


select count(uf) from funcionários where uf=‘SP’
Ou
select count(uf)"Tot Func SP" from funcionarios where uf='SP’

Seleciona o número de UF distintos de funcionários


select count(distinct(uf)) "Núm de UF" from funcionarios

select distinct(uf) "UF" from funcionarios


SELECT AGRUPANDO DADOS COM GROUP BY

As funções de agregação são úteis, porém seu uso comum é vinculá-las a uma
cláusula GROUP BY.

A cláusula GROUP BY como o próprio nome diz trabalha nos dados que estão
agrupados.

Por exemplo, seria interessante buscar


▪ o menor e o maior salário por cada departamento
▪ a média salarial por cargo
▪ o número de funcionários por cada departamento, entre outros.

Para isto, devemos aplicar um função de agregação e agrupá-la por algum campo.
SELECT AGRUPANDO DADOS COM GROUP BY

Desejamos saber quantos funcionários temos em cada departamento.

Se não fossemos usar um group by teríamos que listar a tabela


funcionários, mostrando nome de cada departamento.

E depois teríamos que contar na mão a quantidade de funcionários


de cada departamento

select matricula ,depto "Departamento" from funcionarios,


departamentos
where funcionarios.coddepto=departamentos.coddepto order by depto
SELECT AGRUPANDO DADOS COM GROUP BY

Para sabermos quanto funcionários temos em cada departamento podemos usar um


group by

select depto "Departamento" , count(matricula) "Total de funcionarios" from


funcionarios, departamentos
where funcionarios.coddepto=departamentos.coddepto
group by depto order by depto
SELECT AGRUPANDO DADOS COM GROUP BY
Vamos pesquisar o maior e o menor salário, total de salários e média salarial por cada
departamento

select coddepto "Cod Departamento", MIN(SALARIO) "Menor Salário", MAX(SALARIO) "Maior


Salário" , sum(salario) "Total Salarios" , avg(salario) "Média de Salários" from funcionarios group
by coddepto

Aqui foi utilizado o distinct para média sem repetição de dados


select coddepto "Cod Departamento", MIN(SALARIO) "Menor Salário", MAX(SALARIO) "Maior
Salário" , sum(salario) "Total Salarios" , avg(distinct(salario)) "Média de Salários" from
funcionarios group by coddepto
SELECT AGRUPANDO DADOS COM GROUP BY

Vamos pesquisar o maior e o menor salário por cada departamento, o total de


salários e a quantidade de funcionários de cada departamento, usando o nome do
departamento

select depto "Departamento", MIN(SALARIO) "Menor Salário", MAX(SALARIO)


"Maior Salário" , sum(salario) "Total Salarios" , count(matricula) "Num Funcionarios"
from funcionarios , departamentos where
funcionarios.coddepto=departamentos.coddepto group by depto order by depto
SELECT AGRUPANDO DADOS COM GROUP BY

Vamos pesquisar a média salarial por cargo

select cargo "Cargo" , avg(salario) "Média Salarios" , count(matricula) "Num


Funcionarios" from funcionarios ,
cargos where funcionarios.codcargo=cargos.codcargo group by cargo order by cargo
SELECT AGRUPANDO DADOS COM GROUP BY E HAVING

Limitando dados agrupados com HAVING

Funções de agregação (max,min, sum,count,avg) não podem ser usadas na cláusula


WHERE, porém em alguns casos você deseja agrupar os dados e aplicar um certo
filtro no agrupamento dos dados.

Este filtro não pode ser feito na cláusula WHERE, pois ele é um filtro sobre as linhas
agrupadas.

Por exemplo, exibir a média salarial dos empregados de cada departamento cuja
média salarial seja superior a 8.000,00.

O filtro não é sobre a tabela de FUNCIONARIO, mas sim, sobre o agrupamento feito
sobre esta tabela.
SELECT AGRUPANDO DADOS COM GROUP BY E HAVING

Se fosse só mostrar os totais de salários dos funcionários por UF utilizaríamos a


seguinte query

SELECT UF, MAX(salario) FROM funcionarios


GROUP BY UF

Para buscar o total de salários dos funcionarios de cada UF cuja total salarial seja
superior ou igual a 3.000,00, complementamos a query acima com o Having

SELECT UF, MAX(salario) FROM funcionarios


GROUP BY UF having max(salario)>=3000
SELECT AGRUPANDO DADOS COM GROUP BY E HAVING

Buscar a média salarial dos funcionarios de cada departamento cuja média salarial
seja superior ou igual a 3.000,00. Aqui mostra pelo código do departamento.

select coddepto "Cod. departamento" , avg(salario) "Média Salarios" from


funcionarios group by coddepto having avg(salario)>=3000 order by avg(salario)
SELECT AGRUPANDO DADOS COM GROUP BY E HAVING

Buscar a média salarial dos funcionarios de cada departamento cuja média salarial
seja superior ou igual a 3.000,00, Aqui mostra pelo nome do departamento, então
temos que fazer um join com a tabela departamentos

select depto “Departamento" , avg(salario) "Média Salarios" from funcionarios ,departamentos


where funcionarios.coddepto=departamentos.coddepto group by depto having
avg(salario)>=3000 order by avg(salario)
SELECT AGRUPANDO DADOS COM GROUP BY E HAVING

Buscar a média salarial dos funcionarios de cada departamento, da UF de SP, cuja


média salarial seja superior ou igual a 3.000,00. Aqui mostra a seleção de dados
utilizando um having e um Where para fazer o link entre as tabelas funcionários e
departamentos com mais um filtro por UF

select depto "Departamento" , avg(salario) "Média Salarios" from funcionarios ,departamentos


where funcionarios.coddepto=departamentos.coddepto and UF='SP' group by depto having
avg(salario)>=3000 order by avg(salario);
SELECT USANDO SUBQUERY

Uma subquery é um consulta dentro de uma consulta.

Quando você tem várias subqueries, a subquery mais interna é avaliada primeiramente.

Podem ser usadas com todas as instruções DML.


SELECT USANDO SUBQUERY

Buscar o nome do departamento e o código do departamento cujo nome do funcionário


comece com a Ana.

select depto,coddepto from departamentos


where coddepto IN (select coddepto from funcionarios
where nome like 'Ana%’)

Ou
select depto,coddepto from departamentos d
where EXISTS (select coddepto from funcionarios where coddepto=d.coddepto and
nome like 'Ana%');

Ou sem a subquery
select f.nome, f.coddepto, d.depto
from funcionarios f, departamentos d
where f.coddepto=d.coddepto and nome like ‘Ana%'
SELECT USANDO SUBQUERY

Buscar o nome do funcionário e o código do departamento cujo nome do departamento


comece com a letra ‘R’.

select nome,coddepto from funcionarios


where coddepto IN
(select coddepto from departamentos
where depto like ‘V%’)

Ou sem a subquery

select f.nome, f.coddepto, d.depto from funcionarios f, departamentos d


where f.coddepto=d.coddepto and depto like 'V%'
SELECT USANDO SUBQUERY

Para sabermos quanto funcionários temos no departamento de vendas podemos


podemos usar a seguinte query

select depto "Departamento" , count(matricula) "Total de funcionarios" from


funcionarios, departamentos
where funcionarios.coddepto=departamentos.coddepto and depto=‘VENDAS’
group by depto order by depto

Ou utilizando uma subquery

SELECT COUNT(matricula) "Número de Empregados"


FROM funcionarios WHERE coddepto= (SELECT coddepto FROM departamentos
WHERE depto= ‘VENDAS');
SELECT USANDO SUBQUERY

Para sabermos qual o maior salario de funcionário podemos usar a seguinte query

Se o objetivo fosse sómente o valor sem saber o nome podemos usar a query
select max(SALARIO) "Maior Salario" from funcionários

selec nome, max(salario) from funcionarios ;


dá erro porque quando se utiliza uma função de agrupamento com um campo,
obrigatoriamente, devemos usar um group by

select matricula ,max(salario) from funcionarios group by matricula;


é inviável por aqui vai ser listada a base de dados inteira e não somente o maior salário

SELECT nome,salario from funcionarios WHERE salario = MAX(salario);


vai dar erro, pois não podemos usar as funções de agregação diretamente no WHERE

Esta subquery vai realizar a pesquisa com sucesso


SELECT nome, salario FROM funcionarios
WHERE salario = ( SELECT MAX(salario) FROM funcionarios);
Aqui vão aparecer todos os funcionários com o maior salário
SELECT USANDO SUBQUERY

O operador EXISTS é sempre seguido por uma subquery em parênteses.

Este operador retorna verdadeiro se o resultado da subquery retorna pelo


menos um registro.

O exemplo abaixo retorna os departamentos que ainda


não foram utilizados em funcionarios.

vamos inserir o departamento de SEGURANÇA

SELECT coddepto, depto


FROM departamentos d WHERE NOT EXISTS
(SELECT 1 FROM funcionarios f WHERE f.coddepto = d.coddepto)

Ou
select coddepto,depto from departamentos
where coddepto not in (select coddepto from funcionarios)
SELECT EXPRESSÃO CASE

A expressão CASE pode ser usada como uma derivação da lógica if.. then.. else
Sintaxe:
CASE <expressao>
WHEN <valor de comparação> THEN <valor de retorno>
ELSE <valor de retorno>
END

A cláusula WHEN pode se repetir.


A cláusula ELSE é opcional.

select uf,upper(nome) ,sexo,


CASE sexo
WHEN 'M' THEN 'Masculino'
WHEN 'F' THEN 'Feminino'
ELSE 'Outro'
END as "Sexo"
from funcionarios order by uf,sexo
SELECT EXPRESSÃO DECODE
Case e o Decode tem a mesma função, que é permitir de forma dinâmica e pratica
como obter um retorno de uma coluna com base em uma condição, ou seja, ter a
possibilidade de usar condições semelhantes ao IF-THEN-ELSE em consultas.

Como na coluna sexo, da tabela funcionários, foi craido o camo com char(2) , temos
que colocar no decode ‘M_’ e ‘F_’ com espaços.

select nome, decode(sexo,'M ', 'Masculino','F ', 'Feminino','Indefinido') "SEXO" from


FUNCIONARIOS;
Ou
select nome, decode(trim(sexo),'M', 'Masculino','F', 'Feminino','Indefinido') "SEXO"
from FUNCIONARIOS;

A função trim, limpa os espaços


em branco de uma String
FUNÇÕES DO ORACLE

Existem as funções internas do Oracle que você pode usar para manipular dados.

•Existe as função NVL


NVL (x1, x2)
Possui dois argumentos nos quais ambos são expressões.
A função NVL retorna x2 se x1 é nulo.
Se x1 não é nulo, então x1 é retornado.

Supondo que foi criada a coluna INSS e para alguns funcionários o mesmo não foi
preenchido, então se fosse efetuado um cálculo qualquer nesta coluna com null, iria
dar um erro , então podemos usar a função NVL que em caso da coluna INN não ser
preenchida podemos informar um outro valor para a mesma.

SELECT nome,salario + NVL(inss,1)*1.2 “INSS ATUALIZADO“ FROM funcionarios;


FUNÇÕES DE TEXTO DO ORACLE
FUNÇÕES DE TEXTO DO ORACLE
FUNÇÕES DE TEXTO DO ORACLE

Seguem alguns exemplos:

Mostra um nome em minúsculo


SELECT LOWER(depto) AS "nome do Departamento" FROM departamentos;

Mostra um nome em maiúsculo


SELECT UPPER(nome) AS "nome" FROM funcionarios;

Altera todos os nomes da tabela Funcionarios para maiúsculo


update funcionarios set nome=upper(nome);

Mostra os nomes da tabela funcionários com a primeira letra em maisculo


SELECT INITCAP(nome), salario FROM funcionarios ORDER BY nome;

Altera todos os nomes da tabela Funcionarios para primeira letra do nome em


maiusculo
update funcionarios set nome=initcap(nome);
FUNÇÕES DE TEXTO DO ORACLE

A função RPAD completa a direita de uma coluna com caracteres


especificados.

SELECT RPAD(depto,30,'_') AS "nome do Departamento"


FROM departamentos;

SELECT nome,TO_CHAR(salario,'fml9G999G999D00') AS salario,


RPAD(' ',salario/100,'*') AS GRAFICO FROM funcionários order by grafico desc
FUNÇÕES DE TEXTO DO ORACLE

LPAD
A função LPAD completa a esquerda de uma coluna com caracteres
especificados. No caso, o a tecla | | faz a junção de campos / textos

SELECT RPAD(depto,30,'_’) || LPAD(coddepto,5,'_') AS "nome do Departamento e


Código" FROM departamentos;
FUNÇÕES DO ORACLE

SELECT nome,SUBSTR(nome,3,4) || TO_CHAR(dtcadastro, 'MMDD')


AS APELIDO FROM funcionarios;

O SUBSTR pega um pedaço de um dado de um campo , a partir da posição ate uma


outra
FUNÇÕES DE TEXTO DO ORACLE

O SUBSTR pega um pedaço de um dado de um campo , a partir da posição ate uma


outra

select substr('jpicovsky@gmail.com',11,5)from dual; gmail

select substr('maria@gmail.com',11,5) from dual; l.com

select substr('01417-020',1,5) from dual; 01417


FUNÇÕES DE TEXTO DO ORACLE

A função INSTR retorna a posição de ocorrência de um caractere


ou substring. A função retorna um número inteiro que indica onde foi
encontrado o caractere dentro da string.

SELECT INSTR('jpicovsky@gmail.com','@') AS "Posição" FROM DUAL;

10

select substr('maria@gmail.com',instr('maria@gmail.com','@')+1) from dual;

gmail.com
FUNÇÕES DE TEXTO DO ORACLE

SELECT depto AS "nome do Departamento", LENGTH(depto) AS "Tamanho do


nome” FROM departamentos;
Retorna a quantidade de caracteres digitado no campo
FUNÇÕES DE TEXTO DO ORACLE

TRANSLATE
A função TRANSLATE substitui um caractere em uma string. A sintaxe
é:

TRANSLATE (expressão,de_valor,para_valor)

SELECT nome, TRANSLATE(UPPER(nome),'L','X’)


AS "Usuário“ FROM funcionarios;
FUNÇÕES DE TEXTO DO ORACLE

A função REPLACE é muito parecida com a função TRANSLATE, a diferença é que


a função TRANSLATE substitui um caractere por outro enquanto a função REPLACE
substitui uma expressão por outra expressão.
A sintaxe é apresentada a seguir:

REPLACE (uma expressão, por outra])

SELECT cargo,REPLACE(cargo,'Vendedor','Analista Vendas') AS


"Cargo" FROM cargos
mostra como ficara trocando uma palavra por outra
FUNÇÕES NUMÉRICAS DO ORACLE
FUNÇÕES NUMÉRICAS DO ORACLE
FUNÇÕES NUMÉRICAS DO ORACLE

SELECT ROUND(45.193,1) "Round" FROM DUAL;


SELECT ROUND(45.86,1) "Round" FROM DUAL;
SELECT ROUND(45.86) "Round" FROM DUAL;

TRUNC A função corta o número de acordo com o solicitado.


TRUNC (n1 [, n2])
Onde:
n1 é o valor que será cortado ou truncado.
n2 é o número de casas decimais. Se n2 for omitido, então n1 é
truncado para 0 lugares. N2 pode ser negativo para fazer zeros dígitos
antes do ponto decimal.

SELECT TRUNC(45.193,1) "Trunc" FROM DUAL;


A QUERY retorna 45.1

SELECT TRUNC(45.193,0) "Trunc" FROM DUAL; 45


FUNÇÕES NUMÉRICAS DO ORACLE

SELECT TRUNC(45.86,1) "Trunc" FROM DUAL;


A QUERY retorna 45.8 . Isso ocorre
porque não há arredondamento e sim um corte no número, mantendo
apenas um número após o ponto decimal

SELECT TRUNC(45.84) "Trunc" FROM DUAL;


A QUERY retorna 45 visto que você não passou o argumento n2

POWER
A função POWER retorna à potência de uma base elevada a um expoente.
A função apresenta a seguinte sintaxe:
POWER (n2, n1)

Onde:
n2 é a base n2.
n1 é o expoente se n2 for negativo, então n1 deve ser um número
inteiro.
FUNÇÕES NUMÉRICAS DO ORACLE

SELECT POWER(3,2) "Potência" FROM DUAL;


A consulta retorna 9

SELECT POWER(3,12) "Potência" FROM DUAL; retorna 531441

Para ilustrar, imagine que a empresa queira criar um bônus com


base no salário do empregado. Foi determinado que o bônus será dado
pela formula: (salário/100)2. A QUERY ficaria assim:

SELECT nome,TO_CHAR(salario, '999G999D00') "salario",


TO_CHAR(POWER((salario/1000),2), '99G999D00') "Bônus" FROM funcionarios
WHERE UF='SP'
FUNÇÕES NUMÉRICAS DO ORACLE

SQRT
A função SQRT retorna a raiz quadrada do campo ou valor informado.

SELECT SQRT(81) "Raiz" FROM DUAL;

SELECT nome,TO_CHAR(salario, 'FML09G999D00') "Salario",


TO_CHAR(SQRT(salario)*8, '99g999D00') "Bônus Produtividade"
FROM funcionarios WHERE UF='RJ'
FUNÇÕES NUMÉRICAS DO ORACLE

Gerar número randômico (aleatório)


select dbms_random.value(1,60) num from dual;
41,04924017810997222966155203247133285263

select trunc(dbms_random.value(1,60)) as "Num" from dual;


13

A função MOD retorna o resto da divisão. A sintaxe da função é:


MOD (n2, n1)
Onde:
n2 é o número dividendo que sofrerá a divisão.
n1 é o número divisor.

SELECT MOD(3,2) "Resto" FROM DUAL; resto 1

O comando MOD é muito utilizado para retornar se determinado


número é par ou ímpar. Todo número par retorna resto 0,
enquanto um número ímpar retorna resto 1.
FUNÇÕES DATAS DO ORACLE
FUNÇÕES DATAS DO ORACLE
FUNÇÕES DATAS DO ORACLE

A função MONTHS_BETWEEN retorna o número de meses entre


duas datas.
A sintaxe da função é: MONTHS_BETWEEN(data1, data2)

SELECT MONTHS_BETWEEN( TO_DATE('310717','DDMMYY’),


TO_DATE('310617','DDMMYY')
) AS "Meses"
FROM DUAL;

O resultado da consulta é 1 mês. A QUERY calcula quantos meses se passaram entre


as duas datas.
FUNÇÕES DATAS DO ORACLE

SELECT NOME, ROUND(MONTHS_BETWEEN(SYSDATE,DTNASC)) AS "Meses"


FROM FUNCIONARIOS ORDER BY "Meses" DESC
FUNÇÕES DATAS DO ORACLE

SELECT NEXT_DAY( TO_DATE('25122021','DDMMYYYY') ,'Sáb')


FROM DUAL;
A QUERY está solicitando qual o próximo sábado após o dia 25/12/2021.
01/01/22

Ultimo dia do mês


SELECT SYSDATE AS "Hoje", LAST_DAY(SYSDATE) AS "Último dia do Mês",
LAST_DAY(SYSDATE) - SYSDATE AS "Faltam“ FROM DUAL;
FUNÇÕES DATAS DO ORACLE

Adiciona uma quantidade de dias a uma data


SELECT nome,dtcadastro as "Data da Contratação",
ADD_MONTHS(dtcadastro, 3) AS "Fim da Experiencia"
FROM funcionários

SELECT SESSIONTIMEZONE AS "nome da Região do Fuso"


FROM DUAL;

Data obtida da estação de trabalho, não é a data do servidor


SELECT TO_CHAR(CURRENT_DATE,'DD/MM/YYYY HH:MI:SS') AS
"Data" FROM DUAL;
FUNÇÕES DATAS DO ORACLE

Adiciona uma quantidade de dias a uma data


SELECT nome,dtcadastro as "Data da Contratação",
ADD_MONTHS(dtcadastro, 3) AS "Fim da Experiencia"
FROM funcionários

SELECT SESSIONTIMEZONE AS "nome da Região do Fuso"


FROM DUAL;

Data obtida da estação de trabalho, não é a data do servidor


SELECT TO_CHAR(CURRENT_DATE,'DD/MM/YYYY HH:MI:SS') AS
"Data" FROM DUAL;
COMMIT – ROLLBACK - SAVEPOINT

Quando você cria uma sessão, todas as suas alterações só estão visíveis para você
enquanto estiver utilizando a interface. Se você quiser tornar perene suas alterações,
ou visíveis para outros usuários, você deve utilizar o comando COMMIT.

É interessante notar que quando você sai de uma sessão e a mesma é encerrada sem
problemas, ocorre um COMMIT implícito.

Se sua sessão finaliza por qualquer outro problema, ocorre um ROLLBACK implícito.

O comando ROLLBACK desfaz quaisquer alterações desde o último COMMIT e retorna


os dados aos valores existentes antes das alterações.

A sintaxe para o comando ROLLBACK é bem simples:


ROLLBACK;
COMMIT – ROLLBACK – SAVEPOINT

Vamos inserir o cargo Supervisor na tabela Cargos


INSERT INTO CARGOS VALUES(8,'Supervisor’)
Em seguida, vamos executar o commit para graver efetivamente os dados.

COMMIT; --inicia um ponto de salvamento

Depois vamos deletar esse cargo


delete from cargos where codcargo=8

Se utilizarmos o comando rollback, este registro voltará a fazer parte da tabela


cargos, pois já ocorreu um commit
COMMIT – ROLLBACK – SAVEPOINT

Supondo que voce já tenha efetuado um commit


COMMIT; --inicia um ponto de salvamento

Depois vamos deletar todos os registros da tabela cargos


delete from cargos

Se utilizarmos o comando rollback, os registros voltarão a fazer parte da tabela


cargos, pois já ocorreu um commit

Se caso nenhum commit tenha sido efetuado, os registros não voltarão para a tabela
cargos
COMMIT – ROLLBACK - SAVEPOINT

A declaração SAVEPOINT faz parte dos comandos COMMIT e ROLLBACK.

Este comando estabelece demarcações ou pontos dentro de uma transação.

Seu objetivo é permitir que os comandos COMMIT ou ROLLBACK possam se subdividir e que
alguns pontos possam ser salvos ou ter a transação desfeita

SAVEPOINT nome_ponto;
Para exemplificar, experimente:

SAVEPOINT ponto1
Insira um novo registro na tabela cargos
Depois apague esse registro usando o comando delete

Execute, novamente um savepoint


SAVEPOINT ponto2
Insira um registro diferente do que fez no ponto 1
Depois apague esse registro usando o comando delete
Execute um ROLLBACK TO ponto2;
Voce vai perceber que o registro inserido em ponto 1 não voltou para a tabela
cargos, somente o registro do ponto 2 foi que voltou
VIEW - VISÃO

Uma visão é como uma janela através da qual os dados das tabelas podem ser vistos e
alterados.

Uma visão é derivada de uma tabela ou de outra visão, a qual é chamada de tabela ou visão
base. - uma tabela real com os dados fisicamente armazenados.

Uma visão é armazenada na forma de um comando SELECT apenas. É uma tabela virtual, ou
seja, uma tabela que não existe fisicamente no banco de dados, mas parece existir.

Uma visão não tem dados próprios. Os dados são manipulados a partir das tabelas base.

Uma visão pode ser considerada uma consulta armazenada ou mesmo uma tabela virtual (não
existe fisicamente).

Somente a consulta é armazenada no dicionário de dados, os dados atuais não são copiados de
forma alguma. Isto indica que visão convencional não ocupa qualquer espaço de
armazenamento, somente um espaço no dicionário de dados.
VIEW - VISÃO

Visões são úteis pelas seguintes razões:

▪ Restringir o acesso ao banco de dados. Permite enxergar apenas parte das tabelas.

▪ Permite aos usuários executar consultas simples para obter resultados de consultas
complexas. Podem ser recuperados dados de várias tabelas como se fosse uma única tabela.

▪ Provê independência de dados, permitindo alterar as tabelas base sem afetar as aplicações
dos usuários.

▪ Representar um subconjunto de dados

▪ Ocultar junções complexas

▪ Prover nomes mais entendíveis para colunas

▪ Criação de uma camada entre a aplicação e a fonte de dados


VIEW - VISÃO

•Visões simples
•• dados derivados de uma única tabela
•• não contém funções ou dados grupados.

•Visões complexas
•• dados derivados de múltiplas tabelas
•• contém funções ou dados grupados.

Sintaxe:
CREATE OR REPLACE VIEW nome_da_view [(coluna1, coluna2,...)]
AS
SELECT cláusula_select

select VIEW_NAME from USER_VIEWS para ver os nomes das Views


VIEW - VISÃO

create view V90


as
select nome, email, uf
from funcionarios
where coddepto=500;

select * from v90

select * from v90 where uf='RJ’

Para dropar a view


Drop view v90;
VIEW - VISÃO

create view V90A


as
select nome "IDENTIFICA" , email, uf "ESTADO"
from funcionarios
where coddepto=500;

select * from v90a where uf=‘RJ’ da erro

select * from v90A where ESTADO='RJ’


Aqui a view permite se mascarar o nom dos
campos para que não fiquem visíveis para
outros usuários que não devem ter acesso
completo aos campos da view
VIEW - VISÃO

create view func as


select depto "Departamento" , count(matricula) "Total de funcionarios" from
funcionarios, departamentos
where funcionarios.coddepto=departamentos.coddepto
group by depto order by depto

select * from func

Você também pode gostar