Oracle Tipos de objetos PL/SQL: CREATE TYPE com exemplos
โก Resumo Inteligente
Os tipos de objeto em PL/SQL trazem a programaรงรฃo orientada a objetos para... Oracle, permitindo que vocรช modele entidades do mundo real com atributos e mรฉtodos. Elas suportam construtores, heranรงa e comparaรงรฃo de igualdade, de modo que um รบnico tipo em nรญvel de esquema possa armazenar e processar dados estruturados.

O que รฉ tipo de objeto em PL/SQL?
A Programaรงรฃo Orientada a Objetos รฉ especialmente adequada para a construรงรฃo de componentes reutilizรกveis โโe aplicaรงรตes complexas. Os programas sรฃo organizados em torno de "objetos" em vez de "aรงรตes"; ou seja, sรฃo projetados para trabalhar e interagir com um objeto inteiro, em vez de uma รบnica aรงรฃo. Essa abordagem permite ao programador preencher e manipular detalhes no nรญvel da entidade do objeto.
A imagem abaixo ilustra um exemplo de um tipo de objeto no qual uma conta bancรกria รฉ tratada como uma entidade objeto. Os atributos do objeto armazenam valores โ para uma conta bancรกria, esses valores sรฃo o nรบmero da conta, o saldo bancรกrio e assim por diante โ enquanto os mรฉtodos do objeto descrevem aรงรตes como calcular a taxa de juros ou gerar um extrato bancรกrio, cada uma das quais requer um processo para ser concluรญda.
In PL/SQLA programaรงรฃo orientada a objetos baseia-se em tipos de objetos. Um tipo de objeto pode representar qualquer entidade do mundo real. As seรงรตes a seguir exploram os tipos de objetos, seus componentes e como criรก-los e usรก-los.
Componentes de tipos de objetos
Um tipo de objeto PL/SQL contรฉm principalmente dois componentes.
- Atributos
- Membros/Mรฉtodos
Atributos
Atributos sรฃo as colunas ou campos nos quais os dados sรฃo armazenados. Cada atributo รฉ mapeado para o tipo de dados que define o processamento e o tipo de armazenamento desse atributo. Um atributo pode ser de qualquer tipo vรกlido. Tipo de dados PL/SQLou pode ser de outro tipo de objeto.
Membros/Mรฉtodos
Membros, ou mรฉtodos, sรฃo subprogramas Definidos dentro do tipo de objeto. Nรฃo sรฃo usados โโpara armazenar dados; em vez disso, definem o processamento realizado dentro do tipo de objeto โ por exemplo, validar dados antes de preencher o objeto. Sรฃo declarados na especificaรงรฃo do tipo de objeto e definidos no corpo do tipo de objeto. O corpo รฉ opcional: se nรฃo houver membros presentes, um tipo de objeto nรฃo terรก corpo.
Criar objeto em Oracle
Um tipo de objeto nรฃo pode ser criado no nรญvel do subprograma; ele sรณ pode ser criado no nรญvel do esquema. Uma vez definido no esquema, o tipo de objeto pode ser usado em subprogramas. O tipo de objeto รฉ criado usando a instruรงรฃo โCREATE TYPEโ, e o corpo do tipo sรณ pode ser criado depois que o tipo de objeto existir.
As capturas de tela abaixo mostram a sintaxe CREATE TYPE para a especificaรงรฃo do objeto e a sintaxe CREATE TYPE BODY que define seus mรฉtodos.
CREATE TYPE<object_type_name> AS OBJECT ( <attribute_l><datatype>, . . ); / CREATE TYPE BODY<object_type_name> AS OBJECT ( MEMBER[PROCEDURE|FUNCTION]<member_name> IS <declarative section> BEGIN <execution part> END; . . ); /
Explicaรงรฃo da sintaxe:
- A sintaxe acima mostra a criaรงรฃo de um OBJETO com atributos e um CORPO DE OBJETO com mรฉtodos.
- Os mรฉtodos tambรฉm podem estar sobrecarregados no corpo do objeto.
Inicializaรงรฃo de declaraรงรฃo do tipo de objeto
Assim como outros componentes em PL/SQL, os tipos de objeto devem ser declarados antes de serem usados โโem um programa. Uma vez criado, o tipo de objeto pode ser usado na seรงรฃo declarativa de um subprograma para declarar uma variรกvel desse tipo de objeto.
Sempre que uma variรกvel รฉ declarada como um tipo de objeto, em tempo de execuรงรฃo, uma nova instรขncia desse tipo de objeto รฉ criada, e essa instรขncia recรฉm-criada รฉ referenciada pelo nome da variรกvel. Dessa forma, um รบnico tipo de objeto pode armazenar mรบltiplos valores em instรขncias diferentes.
A captura de tela abaixo mostra uma variรกvel sendo declarada como um tipo de objeto dentro de um Bloco PL/SQL.
DECLARE <variable_name> <object_type_name>; BEGIN . . END; /
Explicaรงรฃo da sintaxe:
- A sintaxe acima mostra a declaraรงรฃo de um variรกvel como um tipo de objeto na seรงรฃo declarativa.
Uma vez que a variรกvel รฉ declarada como um tipo de objeto em um subprograma, ela รฉ atomicamente nula โ o objeto inteiro em si รฉ nulo. Ela deve ser inicializada com valores antes de poder ser usada no programa. Os objetos sรฃo inicializados usando construtores.
Construtores sรฃo mรฉtodos implรญcitos de um objeto que podem ser referenciados com o mesmo nome do tipo do objeto. A captura de tela abaixo mostra a inicializaรงรฃo de uma instรขncia de um tipo de objeto.
DECLARE <variable_name> <object_type_name>; BEGIN <variable_name>:=<object_type_name>(); END; /
Explicaรงรฃo da sintaxe:
- A sintaxe acima mostra a inicializaรงรฃo da instรขncia do tipo de objeto com um valor nulo.
- O objeto em si deixa de ser nulo apรณs ser inicializado, mas os atributos dentro do objeto permanecem nulos atรฉ que valores sejam atribuรญdos a eles.
Construtores
Construtores sรฃo mรฉtodos implรญcitos de um objeto que podem ser referenciados com o mesmo nome do tipo do objeto. Sempre que o objeto รฉ referenciado pela primeira vez, esse construtor รฉ chamado implicitamente.
Vocรช tambรฉm pode inicializar objetos usando esses construtores. Um construtor pode ser definido explicitamente definindo um membro no corpo do tipo de objeto com o mesmo nome do tipo de objeto.
1 exemplo: No exemplo a seguir, usamos o membro do tipo objeto para inserir registros na tabela `emp` com os valores ('RRR', 1005, 20000, 1000) e ('PPP', 1006, 20000, 1001). Apรณs a inserรงรฃo dos dados, os exibimos usando o membro do tipo objeto. Tambรฉm usamos um construtor explรญcito para preencher o `manager id` com o valor padrรฃo 1001 para o segundo registro.
Executamos isso seguindo os passos abaixo.
- Passo 1: Crie o tipo de objeto e o corpo do tipo de objeto.
- Passo 2: Crie um bloco anรดnimo para chamar o tipo de objeto atravรฉs do construtor implรญcito para emp_no 1005.
- Etapa 3: Crie um bloco anรดnimo para chamar o tipo de objeto atravรฉs do construtor explรญcito para emp_no 1006.
Passo 1) Crie o tipo de objeto e o corpo do tipo de objeto.
A captura de tela abaixo mostra a especificaรงรฃo do tipo de objeto emp_object sendo criada com seus atributos e membros.
CREATE TYPE emp_object AS OBJECT( emp_no NUMBER, emp_name VARCHAR2(50), salary NUMBER, manager NUMBER, CONSTRUCTOR FUNCTION emp_object(p_emp_no NUMBER, p_emp_name VARCHAR2, p_salary NUMBER) RETURN SELF AS RESULT), MEMBER PROCEDURE insert_records, MEMBER PROCEDURE display_records); /
A captura de tela abaixo mostra o corpo do tipo emp_object sendo criado com o construtor explรญcito e os procedimentos membro.
CREATE OR REPLACE TYPE BODY emp_object AS CONSTRUCTOR FUNCTION emp_object(p_emp_no NUMBER,p_emp_name VARCHAR2, p_salary NUMBER) RETURN SELF AS RESULT IS BEGIN Dbms_output.put_line('Constructor fired..'); SELF.emp_no:=p_emp_no; SELF.emp_name:=p_emp_name; SELF.salary:=p_salary; SELF.manager:=1001; RETURN; END; MEMBER PROCEDURE insert_records IS BEGIN INSERT INTO emp VALUES(emp_no,emp_name,salary,manager); END; MEMBER PROCEDURE display_records IS BEGIN Dbms_output.put_line('Employee Name:'||emp_name); Dbms_output.put_line('Employee Number:'||emp_no); Dbms_output.put_line('Salary:'||salary); Dbms_output.put_line('Manager:'||manager); END; END; /
Code Explicaรงรฃo
- Code linhas 1-9: Criando o tipo de objeto 'emp_object' com 4 atributos e 3 membros. Ele contรฉm a definiรงรฃo de um construtor com apenas 3 parรขmetros. (O construtor implรญcito real contรฉm um nรบmero de parรขmetros igual ao nรบmero de atributos presentes no tipo de objeto.)
- Code linha 10: Criando o corpo do texto.
- Code linhas 11-21: Definindo o construtor explรญcito. Atribuindo os valores dos parรขmetros aos atributos e atribuindo ao atributo 'manager' o valor padrรฃo '1001'.
- Code linhas 22-26: Definindo o membro 'insert_records', no qual os valores dos atributos sรฃo inseridos na tabela 'emp'.
- Code linhas 27-34: Definindo o membro 'display_records', que exibe os valores dos atributos do tipo objeto.
Saรญda:
Tipo criado
Digite corpo criado
Passo 2) Criando um bloco anรดnimo para chamar o tipo de objeto criado atravรฉs do construtor implรญcito para emp_no 1005.
A captura de tela abaixo mostra o bloco anรดnimo que chama emp_object atravรฉs do construtor implรญcito.
DECLARE guru_emp_det emp_object; BEGIN guru_emp_det:=emp_object(1005,'RRR',20000,1000); guru_emp_det.display_records; guru_emp_det.insert_records; COMMIT; END;
Code Explicaรงรฃo
- Code linhas 37-45: Inserindo os registros usando o construtor implรญcito. A chamada ao construtor contรฉm o nรบmero real de valores de atributo.
- Code linha 38: Declara 'guru_emp_det' como um objeto do tipo 'emp_object'.
- Code linha 41: A instruรงรฃo 'guru_emp_det.display_records' chama o membro 'display_records' e os valores dos atributos sรฃo exibidos.
- Code linha 42: A instruรงรฃo 'guru_emp_det.insert_records' chama o membro 'insert_records' e os valores dos atributos sรฃo inseridos na tabela. O bloco entรฃo confirma a operaรงรฃo. transaรงรฃo.
Saรญda:
Nome do funcionรกrio: RRR
Nรบmero do funcionรกrio: 1005
Salรกrio: 20000
Gerente: 1000
Passo 3) Criando um bloco anรดnimo para chamar o tipo de objeto criado atravรฉs do construtor explรญcito para emp_no 1006.
A captura de tela abaixo mostra o bloco anรดnimo que chama emp_object atravรฉs do construtor explรญcito com trรชs argumentos.
DECLARE guru_emp_det emp_object; BEGIN guru_emp_det:=emp_object(1006,'PPP',20000); guru_emp_det.display_records; guru_emp_det.insert_records; COMMIT; END; /
saรญda
Employee Name:PPP Employee Number:1006 Salary:20000 Manager:1001
Code Explicaรงรฃo:
- Code linhas 46-53: Inserindo o registro usando o construtor explรญcito.
- Code linha 46: Declara 'guru_emp_det' como um objeto do tipo 'emp_object'.
- Code linha 50: A instruรงรฃo 'guru_emp_det.display_records' chama o membro 'display_records' e os valores dos atributos sรฃo exibidos.
- Code linha 51: A instruรงรฃo 'guru_emp_det.insert_records' chama o membro 'insert_records' e os valores dos atributos sรฃo inseridos na tabela. Como apenas trรชs argumentos sรฃo passados, o construtor explรญcito define o ID do gerente para seu valor padrรฃo, 1001.
Heranรงa no tipo de objeto
A propriedade de heranรงa permite que um subtipo de objeto acesse todos os atributos e membros do supertipo de objeto, ou tipo de objeto pai.
O tipo de subobjeto รฉ chamado de tipo de objeto herdado, e o tipo de objeto super รฉ chamado de tipo de objeto pai. A sintaxe abaixo mostra como criar tipos de objeto pai e herdado. A captura de tela abaixo mostra a sintaxe do tipo pai (SUPER) marcada como NรO FINAL.
CREATE TYPE <object_type_name_parent> AS OBJECT ( <attribute_l><datatype>, . . )NOT FINAL; /
Explicaรงรฃo da sintaxe:
- A sintaxe acima mostra a criaรงรฃo do tipo SUPER. A clรกusula NOT FINAL permite que o tipo seja herdado.
A captura de tela abaixo mostra a sintaxe do tipo herdado (SUB) criada com a palavra-chave UNDER.
CREATE TYPE<object_type_name_sub>UNDER<object_type_name_parent> ( <attribute_l><datatype>, . ); /
Explicaรงรฃo da sintaxe:
- A sintaxe acima mostra a criaรงรฃo do tipo SUB. Ele contรฉm todos os membros e atributos do tipo de objeto pai.
1 exemplo: No exemplo abaixo, usamos a propriedade de heranรงa para inserir um registro com o ID do gerente '1002' para o registro ('RRR', 1007, 20000). Executamos o programa nas seguintes etapas.
- Passo 1: Crie o tipo SUPER.
- Passo 2: Crie o tipo SUB e o corpo.
- Passo 3: Crie um bloco anรดnimo para chamar o tipo SUB.
Passo 1) Crie um tipo SUPER ou um tipo pai.
A captura de tela abaixo mostra o supertipo emp_object sendo criado com a clรกusula NOT FINAL.
CREATE TYPE emp_object AS OBJECT( emp_no NUMBER, emp_name VARCHAR2(50), salary NUMBER, manager NUMBER, CONSTRUCTOR FUNCTION emp_object(p_emp_no NUMBER,p_emp_name VARCHAR2(50), p_salary NUMBER)RETURN SELF AS RESULT), MEMBER PROCEDURE insert_records, MEMBER PROCEDURE display_records)NOT FINAL; /
Code Explicaรงรฃo:
- Code linhas 1-9: Criando o tipo de objeto 'emp_object' com 4 atributos e 3 membros. Ele contรฉm a definiรงรฃo de um construtor com apenas 3 parรขmetros. Foi declarado como 'NOT FINAL', portanto รฉ um tipo pai.
Passo 2) Crie um tipo SUB sob o tipo SUPER.
A captura de tela abaixo mostra o tipo herdado sub_emp_object e seu corpo sendo criado.
CREATE OR REPLACE TYPE sub_emp_object UNDER emp_object (default_manager NUMBER,MEMBER PROCEDURE insert_default_mgr); / CREATE OR REPLACE TYPE BODY sub_emp_object AS MEMBER PROCEDURE insert_default_mgr IS BEGIN INSERT INTO emp VALUES(emp_no,emp_name,salary,manager); END; END; /
Code Explicaรงรฃo:
- Code linhas 10-13: Criando 'sub_emp_object' como o tipo herdado com um atributo adicional 'default_manager' e uma declaraรงรฃo de procedimento membro.
- Code linha 14: Criando o corpo para o tipo de objeto herdado.
- Code linhas 16-21: Define o procedimento membro que insere registros na tabela 'emp' com os valores do tipo de objeto SUPER, exceto o valor do gerente. Para o valor do gerente, utiliza 'default_manager' do tipo SUB.
Etapa 3) Criando um bloco anรดnimo para chamar o tipo SUB.
A captura de tela abaixo mostra o bloco anรดnimo que chama o tipo SUB e insere o ID do gerenciador padrรฃo.
DECLARE guru_emp_det sub_emp_object; BEGIN guru_emp_det:= sub_emp_object(1007,'RRR',20000,1000,1002); guru_emp_det.insert_default_mgr; COMMIT; END; /
Code Explicaรงรฃo:
- Code linha 25: Declarando 'guru_emp_det' como tipo 'sub_emp_object'.
- Code linha 27: Inicializando o objeto com o construtor implรญcito. O construtor possui 5 parรขmetros (4 atributos do tipo PARENT e 1 atributo do tipo SUB). O รบltimo parรขmetro (1002) define o valor para o atributo default_manager.
- Code linha 28: Chamando o membro 'insert_default_mgr' para inserir o registro com o ID do gerente padrรฃo passado no construtor.
Igualdade de objetos PL/SQL
Instรขncias de objetos que pertencem ao mesmo tipo de objeto podem ser comparadas para verificar igualdade. Para isso, o tipo de objeto precisa de um mรฉtodo especial chamado mรฉtodo ORDER.
Este mรฉtodo ORDER deve ser uma funรงรฃo que retorna um tipo numรฉrico. Ele recebe dois parรขmetros como entrada (primeiro parรขmetro: o ID da instรขncia do objeto; segundo parรขmetro: o ID de outra instรขncia do objeto).
Os IDs das duas instรขncias de objeto sรฃo comparados e o resultado รฉ retornado como um nรบmero.
- Um valor positivo indica que a instรขncia do objeto SELF รฉ maior que a outra instรขncia.
- Um valor negativo indica que a instรขncia do objeto SELF รฉ menor que a outra instรขncia.
- O valor zero indica que a instรขncia do objeto SELF รฉ igual ร outra instรขncia.
- Se alguma das instรขncias for nula, a funรงรฃo retorna nulo.
A captura de tela abaixo mostra a sintaxe da funรงรฃo membro ORDER que deve ser incluรญda no corpo do tipo para a verificaรงรฃo de igualdade.
CREATE TYPE BODY<object_type_name_ 1>AS OBJECT ( ORDER MEMBER FUNCTION match(<parameter> object_type_name_ 1) RETURN INTEGER IS BEGIN IF <attribute_name>parameter <attribute_name>THEN RETURN -1; --any negative number will do ELSIF id>c.id THEN RETURN 1; --any positive number will do ELSE RETURN 0; END IF; END; . . ); /
Explicaรงรฃo da sintaxe:
- A sintaxe acima mostra a funรงรฃo ORDER que deve ser incluรญda no corpo do tipo para a verificaรงรฃo de igualdade.
- O parรขmetro para esta funรงรฃo deve ser uma instรขncia do mesmo tipo de objeto.
- A funรงรฃo pode ser chamada como โobj_instance_1.match(obj_instance_2)โ, e essa expressรฃo retorna o valor numรฉrico mostrado, onde obj_instance_1 e obj_instance_2 sรฃo instรขncias do tipo objeto.
1 exemplo: No exemplo a seguir, comparamos dois objetos. Criamos duas instรขncias e comparamos o atributo 'salรกrio' entre elas. Fazemos isso em duas etapas.
- Passo 1: Crie o tipo e o corpo do objeto.
- Etapa 2: Crie o bloco anรดnimo para comparar as instรขncias do objeto.
Etapa 1) Criando o tipo e o corpo do objeto.
As capturas de tela abaixo mostram a especificaรงรฃo emp_object_equality e seu corpo, que define a funรงรฃo ORDER que compara o atributo de salรกrio.
CREATE TYPE emp_object_equality AS OBJECT( salary NUMBER, ORDER MEMBER FUNCTION equals(c emp_object_equality)RETURN INTEGER); /
CREATE TYPE BODY emp_object_equality AS ORDER MEMBER FUNCTION equals(c emp_object_equality)RETURN INTEGER IS BEGIN IF salary<c.salary THEN RETURN -1; ELSIF salary>c.salary THEN RETURN 1; ELSE RETURN 0; END IF; END; END; /
Code Explicaรงรฃo:
- Code linhas 1-4: Criando o tipo de objeto 'emp_object_equality' com 1 atributo e 1 membro.
- Code linhas 6-16: Define a funรงรฃo ORDER que compara o atributo 'salรกrio' da instรขncia SELF com o da instรขncia do parรขmetro. Ela retorna um valor negativo se o salรกrio de SELF for menor, um valor positivo se o salรกrio de SELF for maior e 0 se os salรกrios forem iguais.
Code Saรญda:
Tipo criado
Etapa 2) Criaรงรฃo do bloco anรดnimo para comparar as instรขncias do objeto.
A captura de tela abaixo mostra o bloco anรดnimo que compara duas instรขncias de emp_object_equality pelo salรกrio.
DECLARE l_obj_1 emp_object_equality; l_obj_2 emp_object_equality; BEGIN l_obj_1:=emp_object_equality(15000); l_obj_2:=emp_object_equality(17000); IF l_obj_1.equals(l_obj_2)>0 THEN Dbms_output.put_line('Salary of first instance is greater'); ELSIF l_obj_1.equals(l_obj_2)<0 THEN Dbms_output.put_line('Salary of second instance is greater'); ELSE Dbms_output.put_line('Salaries are equal'); END IF; END; /
saรญda
Salary of second instance is greater
Code Explicaรงรฃo:
- Code linha 20: Declarando 'l_obj_1' do tipo 'emp_object_equality'.
- Code linha 21: Declarando 'l_obj_2' do tipo 'emp_object_equality'.
- Code linha 23: Inicializando 'l_obj_1' com o valor salarial '15000'.
- Code linha 24: Inicializando 'l_obj_2' com o valor salarial '17000'.
- Code linhas 25-33: Imprimindo a mensagem com base no nรบmero retornado pela funรงรฃo ORDER.


















