0% encontró este documento útil (0 votos)
47 vistas24 páginas

Procedimientos Funciones

Este documento contiene ejemplos de procedimientos y funciones SQL para realizar diferentes tareas como mostrar datos departamentales, contar empleados por oficio, insertar registros, calcular facturación, etc. Incluye 8 ejercicios que describen procedimientos para realizar consultas, inserciones, cálculos y actualizaciones sobre tablas relacionadas.

Cargado por

Asier Dtl34
Derechos de autor
© © All Rights Reserved
Nos tomamos en serio los derechos de los contenidos. Si sospechas que se trata de tu contenido, reclámalo aquí.
Formatos disponibles
Descarga como TXT, PDF, TXT o lee en línea desde Scribd
0% encontró este documento útil (0 votos)
47 vistas24 páginas

Procedimientos Funciones

Este documento contiene ejemplos de procedimientos y funciones SQL para realizar diferentes tareas como mostrar datos departamentales, contar empleados por oficio, insertar registros, calcular facturación, etc. Incluye 8 ejercicios que describen procedimientos para realizar consultas, inserciones, cálculos y actualizaciones sobre tablas relacionadas.

Cargado por

Asier Dtl34
Derechos de autor
© © All Rights Reserved
Nos tomamos en serio los derechos de los contenidos. Si sospechas que se trata de tu contenido, reclámalo aquí.
Formatos disponibles
Descarga como TXT, PDF, TXT o lee en línea desde Scribd
Está en la página 1/ 24

set serveroutput on;

set linesize120;
-----------------------
procedi
--------------------
create or replace procedure nombrep ()
as
v_nombre varchar2(20);
begin
select dnombre into v_nombre from depart where dept_no=dep;
dbms_output.put_line(''||);
exception
when no_data_found then
bbms;
when to_many_rows then
dbms;
when others then
dbms;
end nombrep;
/
execute nombrep();
-----------------
funcion
--------------------
create or replace function nombrefunctio()
return number
as
v_nombre number(2);
begin
select dnombre into v_nombre where.....;
return v_nombre;
end nombrefuctio;
/
begin dbms(nombrefuncti());end;/

--------------ejercicios--------------

1.- Crea un procedimiento que a trav�s del par�metro DEPT_NO de


un departamento muestre:
el n�mero de departamento, su nombre y su localidad,
as� como el n�mero de empleados que trabajan en ese departamento.
Gestiona excepciones.

CREATE OR REPLACE PROCEDURE EJERCICIO1 (NUM_DEPT NUMBER)


AS
V_DEPT_NO DEPART.DEPT_NO%TYPE;
V_DNOMBRE DEPART.DNOMBRE%TYPE;
V_LOC DEPART.LOC%TYPE;
V_NUM NUMBER(3);
BEGIN
SELECT D.DEPT_NO, DNOMBRE, LOC, COUNT(*) INTO
V_DEPT_NO, V_DNOMBRE, V_LOC, V_NUM
FROM DEPART D, EMPLE E
WHERE E.DEPT_NO=D.DEPT_NO AND D.DEPT_NO=NUM_DEPT
GROUP BY D.DEPT_NO, DNOMBRE, LOC;
DBMS_OUTPUT.PUT_LINE('Los datos son: '||NUM_DEPT||'-'
||V_DNOMBRE||'-'||V_LOC||', N�mero de empleados: '||V_NUM);
EXCEPTION
WHEN NO_DATA_FOUND THEN
DBMS_OUTPUT.PUT_LINE('Ninguna fila encontrada');
when OTHERS THEN
DBMS_OUTPUT.PUT_LINE('ERROR');
END EJERCICIO1;

2.- Pasando el Dept_no como par�metro calcula para cada oficio el n�mero de
empleados que tiene, puede salir 0. Observaci�n: Dado que s�lo tenemos cursores
impl�citos no podemos tener mas de una respuesta por cada consulta -->
necesitamos una consulta distinta para contar cada uno de los oficios.
Gestiona tambi�n las excepciones.

CREATE OR REPLACE PROCEDURE EJER_REF_8_2(DEP NUMBER)


AS
V_ANALISTA NUMBER(2);
V_EMPLEADO NUMBER(2);
V_PRESIDENTE NUMBER(2);
V_DIRECTOR NUMBER(2);
V_VENDEDOR NUMBER(2);
BEGIN
SELECT COUNT(*) INTO V_ANALISTA FROM EMPLE
WHERE DEPT_NO = DEP AND OFICIO = 'ANALISTA';
SELECT COUNT(*) INTO V_EMPLEADO FROM EMPLE
WHERE DEPT_NO = DEP AND OFICIO = 'EMPLEADO';
SELECT COUNT(*) INTO V_PRESIDENTE FROM EMPLE
WHERE DEPT_NO = DEP AND OFICIO = 'PRESIDENTE';
SELECT COUNT(*) INTO V_DIRECTOR FROM EMPLE
WHERE DEPT_NO = DEP AND OFICIO = 'DIRECTOR';
SELECT COUNT(*) INTO V_VENDEDOR FROM EMPLE
WHERE DEPT_NO = DEP AND OFICIO = 'VENDEDOR';

DBMS_OUTPUT.PUT_LINE(rpad('Vendedores: ', 15)||v_vendedor);


DBMS_OUTPUT.PUT_LINE(rpad('Directores: ', 15)||v_director);
DBMS_OUTPUT.PUT_LINE(rpad('Analistas: ', 15)||v_analista);
DBMS_OUTPUT.PUT_LINE(rpad('Empleados: ', 15)||v_empleado);
DBMS_OUTPUT.PUT_LINE(rpad('Presidente: ', 15)||v_presidente);

EXCEPTION
WHEN OTHERS THEN
DBMS_OUTPUT.PUT_LINE('ERROR');

end ejer_ref_8_2;

begin
ejer_ref_8_2(30);
end;

3.- Crea un procedimiento que al recibir el nombre de un fabricante


nos muestra la facturaci�n de ese fabricante y el n� de pedidos (COUNT(*)).

CREATE OR REPLACE PROCEDURE EJERCICIO_3 (FAB VARCHAR2)


AS
COD_FAB NUMBER(2);
NUM_PED NUMBER(3);
FACT NUMBER(8,2);
BEGIN
/* selecciono el cod_fabricante, asi evitamos combinaci�n de tablas*/
SELECT COD_FABRICANTE INTO COD_FAB FROM FABRICANTES WHERE NOMBRE=FAB;
SELECT COUNT(*) INTO NUM_PED FROM PEDIDOS WHERE COD_FABRICANTE=COD_FAB;
SELECT round(SUM(UNIDADES_PEDIDAS*PRECIO_VENTA),2) INTO FACT
FROM ARTICULOS A, PEDIDOS P
WHERE A.ARTICULO=P.ARTICULO AND A.COD_FABRICANTE=P.COD_FABRICANTE AND A.PESO=P.PESO
AND A.CATEGORIA=P.CATEGORIA AND A.COD_FABRICANTE=COD_FAB GROUP BY A.COD_FABRICANTE;

DBMS_OUTPUT.PUT_LINE('Numero de pedidos: '||NUM_PED);


DBMS_OUTPUT.PUT_LINE('Facturacion: '||FACT);
EXCEPTION
WHEN NO_DATA_FOUND THEN
DBMS_OUTPUT.PUT_LINE('Dato no encontrado');
WHEN TOO_MANY_ROWS THEN
DBMS_OUTPUT.PUT_LINE('Demasiadas filas');
WHEN OTHERS THEN
DBMS_OUTPUT.PUT_LINE('Error general');
END EJERCICIO_3;

4. Crea un procedimiento que al recibir el c�digo de un colegio nos muestre


la cantidad de profesores, por un lado, y tambi�n la cantidad de personal
que trabaja en ese colegio.

CREATE OR REPLACE PROCEDURE EJERCICIO4 (COD NUMBER)


AS
V_NUM_PROFESORES NUMBER(2);
V_NUM_PERSONAL NUMBER(2);
BEGIN

SELECT COUNT(*) INTO V_NUM_PROFESORES FROM PROFESORES WHERE COD_CENTRO=COD;


SELECT COUNT(*) INTO V_NUM_PERSONAL FROM PERSONAL WHERE COD_CENTRO=COD;

DBMS_OUTPUT.PUT_LINE('El numero de profesores es: '|| V_NUM_PROFESORES);


DBMS_OUTPUT.PUT_LINE('El numero de empleados es: '|| V_NUM_PERSONAL);

EXCEPTION
WHEN OTHERS THEN
DBMS_OUTPUT.PUT_LINE('ERROR GENERAL');
END EJERCICIO4;

5. Crea 1 tabla con los mismos datos de fabricantes y con 2 columnas m�s:
a. Facturaci�n.
b. N�mero_unidades.
Cada vez que se recibe un pedido (estos son los par�metros del procedure)
el programa recalcula la facturaci�n y el n�mero de unidades de ese fabricante,
y actualiza en la tabla nueva esos datos.
(Observaci�n: cuando crees la tabla ten presente que la necesitas con los datos.)

CREATE TABLE FAB_FACT


AS SELECT * FROM FABRICANTES;

ALTER TABLE FAB_FACT


ADD FACTURACION NUMBER(8,2);

ALTER TABLE FAB_FACT


ADD NUMERO NUMBER(5);

ALTER TABLE FAB_FACT


ADD (FACTURACION NUMBER(8,2),
NUMERO NUMBER(5));

CREATE OR REPLACE PROCEDURE EJERCICIO5


(N VARCHAR2, ART VARCHAR2, COD NUMBER, PES NUMBER, CAT VARCHAR2, UNI NUMBER)
AS
v_existe_tienda number(1);
v_existe_articulo number(1);
V_FACT NUMBER(6,2);
V_UNI NUMBER(4);
noexiste EXCEPTION;
/*declaramos la excepcion*/
BEGIN

select count(*) into v_existe_tienda from tiendas where nif = N;


select count(*) into v_existe_articulo from articulos
where articulo = ART and cod_fabricante = COD AND peso = PES AND categoria=CAT;

IF (v_existe_tienda = 1 and v_existe_articulo = 1) then


INSERT INTO PEDIDOS
VALUES (N, ART, COD, PES, CAT, SYSDATE, UNI);
else
dbms_output.put_line('El articulo o la tienda no existen');
raise noexiste;
/* lanzamos la excepcion */
end if;

SELECT SUM(UNIDADES_PEDIDAS*PRECIO_VENTA) INTO V_FACT


FROM ARTICULOS A, PEDIDOS P WHERE A.ARTICULO=P.ARTICULO
AND A.COD_FABRICANTE=P.COD_FABRICANTE
AND A.PESO=P.PESO AND A.CATEGORIA=P.CATEGORIA
AND P.COD_FABRICANTE=COD group by a.cod_fabricante;

SELECT SUM(UNIDADES_PEDIDAS) INTO V_UNI


FROM PEDIDOS WHERE COD_FABRICANTE=COD GROUP BY COD_FABRICANTE;
/* Una vez calculada la facturaci�n y el n�mero de unidades
se procede a la actualizaci�n de la tabla resumen*/
UPDATE FAB_FACT
SET FACTURACION=V_FACT, NUMERO=V_UNI
WHERE COD_FABRICANTE=COD;

EXCEPTION
/* tratamiento de la excepcion */
WHEN NOEXISTE THEN
DBMS_OUTPUT.PUT_LINE('No existe alg�n registro padre');
WHEN NO_DATA_FOUND THEN
DBMS_OUTPUT.PUT_LINE('No hay datos');
WHEN OTHERS THEN
DBMS_OUTPUT.PUT_LINE('Error');
END EJERCICIO5;

execute ejercicio5('5555-B','Macarrones', 20, 1, 'Primera', 10);


execute ejercicio5('5555-B','Macarro', 20, 1, 'Primera', 10);

6. Crea un procedimiento que realiza las siguientes acciones:


1.- inserta un art�culo nuevo y pasamos todos sus datos como par�metros.
(se comprueba que el fabricante existe en la tabla FABRICANTES)
2.- insertar un pedido y una venta para cada una de las
tiendas existentes (Unidades pedidas 5, Unidades vendidas 5).
3.- Mostrar� la suma de las unidades pedidas y la suma de las unidades vendidas.
Observaciones:
PK Art�culos: Art�culo, Cod_fabricante, Peso, Categor�a.
Gestiona excepciones: S�lo las suficientes y necesarias.

CREATE OR REPLACE PROCEDURE EJERCICIO6


(ART VARCHAR2, COD NUMBER, PES NUMBER, CAT VARCHAR2,PV NUMBER,PC NUMBER,EXIS
NUMBER)
AS
SUM_UNI_VEN NUMBER(3);
SUM_UNI_PED NUMBER(3);
v_existe number(1);
BEGIN
select count(*) into v_existe from fabricantes where cod_fabricante=cod;
if (v_existe=1) then
INSERT INTO ARTICULOS VALUES (ART, COD, PES, CAT, PV, PC, EXIS);
IF (SQL%ROWCOUNT = 0) THEN
DBMS_OUTPUT.PUT_LINE('ARTICULO NO INSERTADO');
ELSE
INSERT INTO PEDIDOS SELECT NIF, ART, COD, PES, CAT, SYSDATE, 5 FROM TIENDAS;
INSERT INTO VENTAS SELECT NIF, ART, COD, PES, CAT, SYSDATE, 5 FROM TIENDAS;

SELECT SUM(UNIDADES_PEDIDAS) INTO SUM_UNI_PED FROM PEDIDOS


WHERE ARTICULO=ART AND COD_FABRICANTE=COD AND CATEGORIA=CAT AND PESO=PES;
SELECT SUM(UNIDADES_VENDIDAS) INTO SUM_UNI_VEN FROM VENTAS
WHERE ARTICULO=ART AND COD_FABRICANTE=COD AND CATEGORIA=CAT AND PESO=PES;

DBMS_OUTPUT.PUT_LINE('Suma de unidades pedidas: '||SUM_UNI_PED);


DBMS_OUTPUT.PUT_LINE('Suma de unidades vendidas: '||SUM_UNI_VEN);
END IF;
else
dbms_output.put_line('El fabricante no existe');
end if;
EXCEPTION
WHEN OTHERS THEN
DBMS_OUTPUT.PUT_LINE('ERROR GENERAL');
END EJERCICIO6;

7. Crea un procedimiento que recibe los datos de un empleado


(EMP_NO, APELLIDO, OFICIO, DIR, FECHA_ALT, COMISION, DEPT_NO) La comisi�n por
defecto ser� 0.
(Recuerda que la asignaci�n de valores a los par�metros es posicional en la
ejecuci�n del procedimiento).
EL SALARIO estar� en funci�n del departamento en el que se inserte al empleado,
siendo este salario el salario
medio de su departamento aumentado en un 3% y sin decimales.
Observaciones:
Controla que el empleado se inserta en un departamento existente
y que el salario y la comisi�n son positivos.
Gestiona las excepciones necesarias y suficientes.

CREATE OR REPLACE PROCEDURE


EJERCICIO7 (EMP NUMBER, APE VARCHAR2, OFI VARCHAR2, D NUMBER, FECHA DATE,
DEPT NUMBER, COM NUMBER DEFAULT 0)
AS
V_SALARIO NUMBER(6,2);
V_NUM NUMBER(1);
BEGIN
SELECT COUNT(*) INTO V_NUM FROM DEPART WHERE DEPT_NO=DEPT;

IF (V_NUM=1 AND COM>=0) THEN


SELECT abs(TRUNC(AVG(SALARIO)*1.03)) INTO V_SALARIO FROM EMPLE
WHERE DEPT_NO=DEPT;
INSERT INTO EMPLE VALUES (EMP, APE, OFI, D, FECHA, V_SALARIO, COM, DEPT);
IF (SQL%ROWCOUNT=1) THEN
DBMS_OUTPUT.PUT_LINE('Empleado insertado');
end if;

ELSE
DBMS_OUTPUT.PUT_LINE('EL DEPARTAMENTO NO EXISTE o la comision es negativa');
END IF;

EXCEPTION
WHEN OTHERS THEN
DBMS_OUTPUT.PUT_LINE('EL DEPARTAMENTO NO EXISTE');
END EJERCICIO7;

8. Crea un procedimiento que a partir del nombre de un


banco muestra los siguientes datos:
a. N�mero de sucursales que tiene.
b. N�mero de cuentas que tiene (en total, no agrupadas por sucursal)
c. Suma de saldo_debe y de saldo_haber de todas sus cuentas.
SELECT SUM(SALDO_DEBE), SUM(SALDO_HABER) INTO V1, V2

CREATE OR REPLACE PROCEDURE EJERCICIO_8(P_NOMBRE VARCHAR2)


AS
V_COD_BANCO BANCOS.COD_BANCO%TYPE;
V_NUM_SUCURSALES NUMBER(3);
V_NUM_CUENTAS NUMBER(4);
V_SUMA_DEBE NUMBER(10);
V_SUMA_HABER NUMBER(10);
BEGIN

SELECT COD_BANCO INTO V_COD_BANCO FROM BANCOS


WHERE NOMBRE_BANC=P_NOMBRE;

SELECT COUNT(*) INTO V_NUM_SUCURSALES FROM SUCURSALES


WHERE COD_BANCO = V_COD_BANCO;

DBMS_OUTPUT.PUT_LINE('El banco '|| p_nombre ||' tiene '||v_num_sucursales||'


sucursales.');

SELECT COUNT(*) INTO V_NUM_CUENTAS FROM CUENTAS


WHERE COD_BANCO = V_COD_BANCO;

DBMS_OUTPUT.PUT_LINE('El banco '|| p_nombre ||' tiene '||v_num_cuentas||'


cuentas.');

SELECT SUM(SALDO_DEBE) INTO V_SUMA_DEBE


FROM CUENTAS
WHERE COD_BANCO = V_COD_BANCO;

SELECT SUM(SALDO_HABER) INTO V_SUMA_HABER


FROM CUENTAS
WHERE COD_BANCO = V_COD_BANCO;

DBMS_OUTPUT.PUT_LINE('El banco '|| p_nombre ||' tiene '||v_suma_debe||' suma


debe.');
DBMS_OUTPUT.PUT_LINE('El banco '|| p_nombre ||' tiene '||v_suma_haber||' suma
haber.');

exception
when no_data_found then
DBMS_OUTPUT.PUT_LINE('No existe '||p_nombre);
when others then
DBMS_OUTPUT.PUT_LINE('Error general');

END EJERCICIO_8;

9. Crea un procedimiento que recibe los datos de una cuenta nueva


(en una sucursal concreta, con unos saldos concretos) y
despu�s se realiza una llamada al procedimiento anterior
para ver los datos generales del banco
donde se ha insertado esa cuenta nueva.

CREATE OR REPLACE PROCEDURE EJERCICIO_9


(P_COD_BANCO NUMBER, P_COD_SUCUR NUMBER, P_NUM_CTA NUMBER, P_NOMBRE_CTA VARCHAR2,
P_DIREC_CTA VARCHAR2, P_POBLA_CTA VARCHAR2, P_SALDO_HABER NUMBER DEFAULT 0,
P_SALDO_DEBE number DEFAULT 0)
AS
V_EXISTE NUMBER(1);
V_NOMBRE_BANC VARCHAR2(20);
BEGIN
SELECT COUNT(*) INTO V_EXISTE FROM SUCURSALES
WHERE COD_SUCUR=P_COD_SUCUR and cod_banco = p_cod_banco;
IF V_EXISTE=1 THEN

INSERT INTO CUENTAS VALUES


(P_COD_BANCO, P_COD_SUCUR, P_NUM_CTA, SYSDATE,P_NOMBRE_CTA,
P_DIREC_CTA, P_POBLA_CTA, P_SALDO_HABER, P_SALDO_DEBE);

SELECT NOMBRE_BANC INTO V_NOMBRE_BANC from bancos WHERE COD_BANCO = P_COD_BANCO;

EJERCICIO_8(V_NOMBRE_BANC);
ELSE
DBMS_OUTPUT.PUT_LINE('No existe banco/sucursal, no se inserta la cta.');
END IF;
EXCEPTION
WHEN OTHERS THEN
DBMS_OUTPUT.PUT_LINE('Error general.');
END EJERCICIO_9;
/

10. Crea un procedimiento que a partir del nombre de un banco elimina ese banco
y todo lo relativo a �l.

CREATE OR REPLACE PROCEDURE EJERCICIO_10 (P_NOMBRE_BANC VARCHAR2)


AS
v_existe number(2);
V_COD_BANCO BANCOS.COD_BANCO%TYPE;
BEGIN
select count(*) into v_existe from bancos where nombre_banc=P_NOMBRE_BANC;

if v_existe = 1 then
SELECT COD_BANCO INTO V_COD_BANCO from bancos
WHERE NOMBRE_BANC = P_NOMBRE_BANC;

DELETE FROM MOVIMIENTOS WHERE COD_BANCO=V_COD_BANCO;


DELETE FROM CUENTAS WHERE COD_BANCO=V_COD_BANCO;
DELETE FROM SUCURSALES WHERE COD_BANCO=V_COD_BANCO;
DELETE FROM BANCOS WHERE COD_BANCO=V_COD_BANCO;
else
dbms_output.put_line('No existe el banco');
end if;

EXCEPTION
WHEN OTHERS THEN
dbms_output.put_line('Error general');
END EJERCICIO_10;

execute ejercicio_10('BANCO DE ESPA�A');

13. Crea un procedimiento que a partir de una provincia nos


dice cu�l es la tienda que mas vende en esa provincia. Adem�s tambi�n filtrar� por
fechas.

CREATE OR REPLACE PROCEDURE EJER_REF_8_13(P_fechai date,


p_fechaf date, p_provincia varchar2)
AS
v_nombre tiendas.nombre%type;
v_num number(6);
BEGIN
SELECT NOMBRE, COUNT(*) into v_nombre, v_num
FROM TIENDAS T, VENTAS V
WHERE T.NIF = V.NIF
AND FECHA_VENTA BETWEEN P_FECHAI AND P_FECHAF
AND PROVINCIA = P_PROVINCIA
GROUP BY NOMBRE
HAVING COUNT(*) = (SELECT MAX(COUNT(*)) FROM TIENDAS T, VENTAS V
WHERE T.NIF = V.NIF
AND FECHA_VENTA BETWEEN P_FECHAI AND P_FECHAF
AND PROVINCIA = P_PROVINCIA
GROUP BY NOMBRE);
dbms_output.put_line('La tienda: '||v_nombre||' ha realizado '||v_num||' ventas');
exception
when too_many_rows then
dbms_output.put_line('Demasiados datos');
when no_data_found then
dbms_output.put_line('No hay datos');
when others then
dbms_output.put_line('error');
END EJER_REF_8_13;

15. Crea un procedimiento que elimina los art�culos que no tienen ni pedidos ni
ventas en los �ltimos 2 a�os.
(utiliza sysdate) Si no ha eliminado ninguno, avisa por pantalla. Si se han
eliminado filas no indica nada.

CREATE OR REPLACE PROCEDURE EJER_REF_8_15


AS
BEGIN

DELETE FROM ARTICULOS


WHERE (ARTICULO, COD_FABRICANTE, PESO, CATEGORIA) NOT IN
(SELECT distinct ARTICULO, COD_FABRICANTE, PESO, CATEGORIA
FROM VENTAS WHERE FECHA_VENTA >= SYSDATE-730)
AND (ARTICULO, COD_FABRICANTE, PESO, CATEGORIA) NOT IN
(SELECT distinct ARTICULO, COD_FABRICANTE, PESO, CATEGORIA
FROM PEDIDOS WHERE FECHA_PEDIDO >= SYSDATE-730);

IF (SQL%ROWCOUNT=0) THEN
{dbms_output.put_line('0 articulos eliminados');}
ELSE
{dbms_output.put_line(sql%rowcount ||' articulos eliminados');}
END IF;
EXCEPTION
WHEN OTHERS THEN
dbms_output.put_line('error');
END EJER_REF_8_15;
/
12. Crea un procedimiento que recibe los datos de un empleado.
Si el salario es mayor que la media de su departamento le asigna
exactamente la media del salario de su departamento. Los dem�s
datos se mantienen. La comisi�n es por defecto 0.

CREATE OR REPLACE PROCEDURE EJER_REF_8_12(P_EMP_NO NUMBER,


P_APELLIDO VARCHAR2, P_OFICIO VARCHAR2, P_DIR NUMBER, P_SALARIO NUMBER,
P_DEPT_NO NUMBER, P_COMISION NUMBER DEFAULT 0)
AS
V_SALARIO_MEDIO NUMBER(5);
V_SALARIO NUMBER(5);
BEGIN
SELECT TRUNC(AVG(SALARIO)) INTO V_SALARIO_MEDIO
FROM EMPLE WHERE DEPT_NO = P_DEPT_NO;

IF P_SALARIO > V_SALARIO_MEDIO THEN


V_SALARIO := V_SALARIO_MEDIO;
ELSE
V_SALARIO := P_SALARIO;
END IF;

INSERT INTO EMPLE


VALUES (P_EMP_NO, P_APELLIDO, P_OFICIO, P_DIR,SYSDATE, P_SALARIO, P_COMISION,
P_DEPT_NO);

IF (sql%rowcount=1) THEN
dbms_output.put_line('empleado insertado');
ELSE
dbms_output.put_line('empleado no insertado');
END IF;

EXCEPTION
when no_data_found then
dbms_output.put_line('no hay datos');
when others then
dbms_output.put_line('error');
END EJER_REF_8_12;

1.Crea un procedimiento que recibe los datos de un profesor:


a. Comprueba que el centro existe.
b. Comprueba que su clave no se repite.
c. Si los datos son correctos el registro se inserta.
d. Gestiona posibles excepciones.

CREATE OR REPLACE PROCEDURE EJERCICIO_9_1


(COD NUMBER, DN NUMBER, APE VARCHAR2, ESP VARCHAR2)
AS
NUM NUMBER(2);
CLAVE NUMBER(2);
BEGIN
SELECT COUNT(*) INTO NUM FROM CENTROS WHERE COD_CENTRO = COD;
SELECT COUNT(*) INTO CLAVE FROM PROFESORES WHERE DNI= DN;
IF (NUM=1 AND CLAVE=0) THEN
INSERT INTO PROFESORES VALUES (COD, DN, APE, ESP);
ELSE
DBMS_OUTPUT.PUT_LINE('EL CENTRO NO EXISTE O EL DNI SE REPITE');
END IF;
EXCEPTION
WHEN OTHERS THEN
DBMS_OUTPUT.PUT_LINE('ERROR GENERAL');
END EJERCICIO_9_1;

-------------------------------------------------------------------------

CREATE OR REPLACE PROCEDURE EJERCICIO_9_1


(COD NUMBER, DN NUMBER, APE VARCHAR2, ESP VARCHAR2)
AS
NUM NUMBER(2);
CLAVE NUMBER(2);
BEGIN
SELECT COUNT(*) INTO NUM FROM CENTROS WHERE COD_CENTRO = COD;
IF (NUM=1) THEN
SELECT COUNT(*) INTO CLAVE FROM PROFESORES WHERE DNI= DN;
if (clave=0) then
INSERT INTO PROFESORES VALUES (COD, DN, APE, ESP);
ELSE
DBMS_OUTPUT.PUT_LINE('EL DNI SE REPITE');
END IF;
else
DBMS_OUTPUT.PUT_LINE('EL CENTRO NO EXISTE');
end if;
EXCEPTION.
WHEN OTHERS THEN
DBMS_OUTPUT.PUT_LINE('ERROR GENERAL');
END EJERCICIO_9_1;

-----------------------------------------------------------------------------------
-----------------------------------------

2.Crea un procedimiento que recibe los datos de un empleado y realiza las


siguientes acciones:
a. Comprueba que existe el dir y el departamento del empleado.
b. Comprueba que el salario es positivo.
c. Si todos los datos son correctos inserta el empleado.
d. Muestra por pantalla el gasto total en salarios del departamento del nuevo
empleado.
e. Gestiona posibles excepciones.

CREATE OR REPLACE PROCEDURE EJERCICIO_9_2(EMP NUMBER, APE VARCHAR2,


OFI VARCHAR2, D NUMBER, FECHA DATE, SAL NUMBER, COM NUMBER, DEP NUMBER)
AS
V_DIR NUMBER(2);
V_DEPT_NO NUMBER(2);
V_SUM_SAL NUMBER(7);
BEGIN
IF (SAL > 0) THEN
SELECT COUNT(*) INTO V_DIR FROM EMPLE WHERE EMP_NO=D;
SELECT COUNT(*) INTO V_DEPT_NO FROM DEPART WHERE DEPT_NO=DEP;

IF (V_DIR=1 AND V_DEPT_NO=1) THEN


INSERT INTO EMPLE VALUES (EMP, APE, OFI, D, FECHA, SAL, COM, DEP);
DBMS_OUTPUT.PUT_LINE('EMPLEADO INSERTADO');
SELECT SUM(SALARIO) INTO V_SUM_SAL FROM EMPLE WHERE DEPT_NO=DEP GROUP BY DEPT_NO;
DBMS_OUTPUT.PUT_LINE('EL GASTO EN SALARIO DEL DEPARTAMENTO '||DEP||' ES '||
V_SUM_SAL);
ELSE
DBMS_OUTPUT.PUT_LINE('EL JEFE O EL DEPARTAMENTO NO EXISTEN');
END IF;

ELSE
DBMS_OUTPUT.PUT_LINE('EL SALARIO ES NEGATIVO O CERO');
END IF;
EXCEPTION
WHEN OTHERS THEN
DBMS_OUTPUT.PUT_LINE('ERROR');
END EJERCICIO_9_2;

BEGIN EJERCICIO_9_2(11,'MARTINEZ','VENDEDOR',7369, SYSDATE, 2000,0,10); END;


-------------------------------------------------------------------------------

CREATE OR REPLACE PROCEDURE EJERCICIO_9_2(EMP NUMBER, APE VARCHAR2,


OFI VARCHAR2, D NUMBER, FECHA DATE, SAL NUMBER, COM NUMBER, DEP NUMBER)
AS
V_DIR NUMBER(2);
V_DEPT_NO NUMBER(2);
V_SUM_SAL NUMBER(7);
BEGIN
SELECT COUNT(*) INTO V_DIR FROM EMPLE WHERE EMP_NO=D;
SELECT COUNT(*) INTO V_DEPT_NO FROM DEPART WHERE DEPT_NO=DEP;

IF (SAL > 0 and V_DIR=1 AND V_DEPT_NO=1) THEN

INSERT INTO EMPLE VALUES (EMP, APE, OFI, D, FECHA, SAL, COM, DEP);
DBMS_OUTPUT.PUT_LINE('EMPLEADO INSERTADO');
SELECT SUM(SALARIO) INTO V_SUM_SAL FROM EMPLE WHERE DEPT_NO=DEP GROUP BY DEPT_NO;
DBMS_OUTPUT.PUT_LINE('EL GASTO EN SALARIO DEL DEPARTAMENTO '||DEP||' ES '||
V_SUM_SAL);

ELSE
DBMS_OUTPUT.PUT_LINE('EL JEFE O EL DEPARTAMENTO NO EXISTEN o el salario es
negativo');
END IF;

EXCEPTION
WHEN OTHERS THEN
DBMS_OUTPUT.PUT_LINE('ERROR');
END EJERCICIO_9_2;
-----------------------------------------------------------------------------------
-------------------------------------------------------------
3.Crea un procedimiento que recibe los datos de un pedido y realiza las siguientes
acciones:
a. Comprueba que el art culo existe en la tabla padre.
b. Comprueba que la tienda existe.
c. Si las unidades del pedido es superior que las existencias, s lo asigna al
pedido
el 20% de las existencias.
d. La fecha de pedido es la actual.
e. Una vez insertado el pedido resta las unidades pedidas a las existencias del
art culo.

CREATE OR REPLACE PROCEDURE EJERCICIO_9_3(N VARCHAR2, ART VARCHAR2, COD NUMBER,


PES NUMBER, CAT VARCHAR2,UNID NUMBER, FECHA DATE DEFAULT SYSDATE)
AS
V_ART NUMBER(2);
V_NIF NUMBER(2);
V_EXIST NUMBER(4);
V_UNI NUMBER(3);
BEGIN
SELECT COUNT(*) INTO V_ART FROM ARTICULOS
WHERE ARTICULO=ART AND PESO=PES AND COD_FABRICANTE = COD AND CATEGORIA=CAT;
SELECT COUNT(*) INTO V_NIF FROM TIENDAS WHERE NIF=N;

IF (V_ART=1 AND V_NIF=1) THEN


SELECT EXISTENCIAS INTO V_EXIST FROM ARTICULOS
WHERE ARTICULO=ART AND PESO=PES AND COD_FABRICANTE = COD AND CATEGORIA=CAT;
IF (V_EXIST < UNID) THEN
V_UNI:=TRUNC(V_EXIST*0.2);
ELSE
V_UNI:=UNID;
END IF;
INSERT INTO PEDIDOS VALUES (N, ART, COD, PES, CAT, FECHA, V_UNI);
UPDATE ARTICULOS SET EXISTENCIAS = EXISTENCIAS-V_UNI
WHERE ARTICULO=ART AND PESO=PES AND COD_FABRICANTE = COD AND CATEGORIA=CAT;
ELSE
DBMS_OUTPUT.PUT_LINE('EL NIF O EL ARTICULO NO EXISTEN');
END IF;
EXCEPTION
WHEN OTHERS THEN
DBMS_OUTPUT.PUT_LINE('ERROR');
END EJERCICIO_9_3;

BEGIN EJERCICIO_9_3('1111-A', 'Macarrones', 20, 1, 'Primera', 1000, sysdate); END;

-----------------------------------------------------------------------------------
----------------------------------------------------------------
4. Crea un procedimiento que al recibir los datos de una venta realiza las
siguientes acciones:
a. Muestra la facturaci n de la tienda (en ventas) antes de insertarse la venta.
b. Se comprueba que todos los datos de la venta son correctos, como en el
ejercicio 3.
c. Se inserta la venta.
d. Vuelve a mostrar la facturaci n de la tienda una vez insertada la venta.
e. Gestiona las posibles excepciones.
CREATE OR REPLACE PROCEDURE EJERCICIO_9_4(N VARCHAR2, ART VARCHAR2, COD NUMBER, PES
NUMBER, CAT VARCHAR2, UNID NUMBER)
AS
V_ART NUMBER(2);
V_NIF NUMBER(2);
V_EXIST NUMBER(4);
V_UNI NUMBER(3);
V_FACT NUMBER(8,2);
BEGIN
SELECT COUNT(*) INTO V_ART FROM ARTICULOS
WHERE ARTICULO=ART AND PESO=PES AND COD_FABRICANTE = COD AND CATEGORIA=CAT;
SELECT COUNT(*) INTO V_NIF FROM TIENDAS WHERE NIF=N;

IF (V_ART=1 AND V_NIF=1) THEN

SELECT SUM(PRECIO_VENTA*UNIDADES_VENDIDAS) INTO V_FACT


FROM ARTICULOS A, VENTAS V
WHERE A.ARTICULO=V.ARTICULO AND A.COD_FABRICANTE=V.COD_FABRICANTE
AND A.PESO=V.PESO AND A.CATEGORIA=V.CATEGORIA AND NIF=N;

DBMS_OUTPUT.PUT_LINE(V_FACT);

SELECT EXISTENCIAS INTO V_EXIST FROM ARTICULOS


WHERE ARTICULO=ART AND PESO=PES AND COD_FABRICANTE = COD AND CATEGORIA=CAT;
IF (V_EXIST < UNID) THEN
V_UNI:=TRUNC(V_EXIST*0.2);
ELSE
V_UNI:=UNID;
END IF;

INSERT INTO VENTAS VALUES (N, ART, COD, PES, CAT, SYSDATE, V_UNI);

UPDATE ARTICULOS SET EXISTENCIAS = EXISTENCIAS-V_UNI


WHERE ARTICULO=ART AND PESO=PES AND COD_FABRICANTE = COD AND CATEGORIA=CAT;

SELECT SUM(PRECIO_VENTA*UNIDADES_VENDIDAS) INTO V_FACT


FROM ARTICULOS A, VENTAS V
WHERE A.ARTICULO=V.ARTICULO AND A.COD_FABRICANTE=V.COD_FABRICANTE
AND A.PESO=V.PESO AND A.CATEGORIA=V.CATEGORIA AND NIF=N;
DBMS_OUTPUT.PUT_LINE(V_FACT);
ELSE
DBMS_OUTPUT.PUT_LINE('EL NIF O EL ARTICULO NO EXISTEN');
END IF;
EXCEPTION
WHEN OTHERS THEN
DBMS_OUTPUT.PUT_LINE('ERROR');
END EJERCICIO_9_4;

BEGIN EJERCICIO_9_4('1111-A', 'Macarrones', 20, 1, 'Primera', 23); end;

-----------------------------------------------------------------------------------
---------------------------------------------------------------
5. Crea un procedimiento que recibe 2 fechas, y muestra la facturaci n de la
venta
y los pedidos de todas las tiendas entre esas dos fechas.
CREATE OR REPLACE PROCEDURE FACT(F1 DATE, F2 DATE)
AS
FACT_PEDIDOS NUMBER(8,2);
FACT_VENTAS NUMBER(8,2);
BEGIN
SELECT nvl(SUM(UNIDADES_PEDIDAS*PRECIO_VENTA),0) INTO FACT_PEDIDOS
FROM ARTICULOS A, PEDIDOS P
WHERE A.ARTICULO=P.ARTICULO AND A.COD_FABRICANTE=P.COD_FABRICANTE
AND A.PESO=P.PESO
AND A.CATEGORIA=P.CATEGORIA AND FECHA_PEDIDO BETWEEN F1 AND F2;

SELECT nvl(SUM(UNIDADES_VENDIDAS*PRECIO_VENTA),0) INTO FACT_VENTAS


FROM ARTICULOS A, VENTAS V
WHERE A.ARTICULO=V.ARTICULO AND A.COD_FABRICANTE=V.COD_FABRICANTE
AND A.PESO=V.PESO
AND A.CATEGORIA=V.CATEGORIA AND FECHA_venta BETWEEN F1 AND F2;

DBMS_OUTPUT.PUT_LINE('Facturacion de pedidos: '||FACT_PEDIDOS);


DBMS_OUTPUT.PUT_LINE('Facturacion de ventas: '||FACT_VENTAS);

EXCEPTION
WHEN OTHERS THEN
DBMS_OUTPUT.PUT_LINE('ERROR');
END FACT;

BEGIN DBMS_OUTPUT.PUT_LINE(FACT('01/01/2005','31/12/2006')); END;


-----------------------------------------------------------------------------------
---------------------------------------------------------------------

6.- Crea una funci n que recibe como par metro el n mero de departamento
y nos devuelve
el n mero de empleados que existen en ese departamento.
Despu s crea un procedimiento que realiza una llamada a esa funci n.
---------------funci n--------------------------------------------------
CREATE OR REPLACE FUNCTION EJER_6(N_DEPT NUMBER)
RETURN NUMBER
AS
V_NUM NUMBER(2);
BEGIN
SELECT COUNT(*) INTO V_NUM FROM EMPLE WHERE DEPT_NO=N_DEPT;
RETURN V_NUM;
END EJER_6;

------------------procedimiento que llama a la funci n------------------


CREATE OR REPLACE PROCEDURE EJER_6_PROC(N_DEPT NUMBER)
AS
V NUMBER(2);
BEGIN
V := EJER_6(N_DEPT); --llamada a la funci n.
DBMS_OUTPUT.PUT_LINE('El numero de empleados de '||N_DEPT||' es '||V);
EXCEPTION
WHEN OTHERS THEN
DBMS_OUTPUT.PUT_LINE('ERROR');
END EJER_6_PROC;

BEGIN
EJER_6_PROC(10);
END;
------------------llamada a la funci n desde bloque anonimo--------------

BEGIN
DBMS_OUTPUT.PUT_LINE(EJER_6(10));
END;
-----------------------------------------------------------------------------------
--------------------------------------------------------------------

7. Escribe una funci n que toma la PK de un art culo y nos devuelve


la suma de unidades pedidas de ese art culo.

CREATE OR REPLACE FUNCTION EJER_7


(ART VARCHAR2, COD NUMBER, PES NUMBER, CAT VARCHAR2)
RETURN NUMBER
AS
V_UNI_PEDIDAS NUMBER(4);
BEGIN
SELECT SUM(UNIDADES_PEDIDAS) INTO V_UNI_PEDIDAS FROM PEDIDOS
WHERE ARTICULO=ART AND COD_FABRICANTE=COD AND PESO=PES AND CATEGORIA=CAT;
RETURN V_UNI_PEDIDAS;

EXCEPTION
WHEN NO_DATA_FOUND THEN
DBMS_OUTPUT.PUT_LINE('SIN DATOS');
END EJER_7;

BEGIN
DBMS_OUTPUT.PUT_LINE(EJER_7('Macarrones',20,1,'Primera'));
END;

-----------------------------------------------------------------------------------
---------------------------------
8. Crea un procedimiento que actualiza las existencias de un art culo que
recibe como par metro,
restando a las existencias la suma de unidades pedidas de ese art culo.
Utiliza la funci n del ejercicio anterior.

CREATE OR REPLACE PROCEDURE EJER_8(ART VARCHAR2, COD NUMBER, PES NUMBER, CAT
VARCHAR2)
AS
V_UNI_PED NUMBER(4);
BEGIN

V_UNI_PED:=EJER_7(ART, COD, PES, CAT);

UPDATE ARTICULOS SET EXISTENCIAS=EXISTENCIAS-V_UNI_PED


WHERE ARTICULO=ART AND COD_FABRICANTE=COD AND PESO=PES AND CATEGORIA=CAT;

EXCEPTION
WHEN NO_DATA_FOUND THEN
DBMS_OUTPUT.PUT_LINE('NO HAY DATOS');

END EJER_8;

-----------------------------------------------------------------------------------
-----------------------------------
9. Crea un programa que recibe los datos de un art culo. Este programa tiene las
siguientes funcionalidades:
a. Tiene un procedimiento local almacenado que recibe los
datos del art culo y devuelve por pantalla su facturaci n.
b. Tiene un procedimiento almacenado local que calcula
el n mero de pedidos de ese art culo y lo muestra por pantalla.
c. Finalmente el procedimiento principal realiza una llamada a cada uno de los
procedimientos locales.

CREATE OR REPLACE PROCEDURE EJER_9


(ART VARCHAR2, COD NUMBER, PES NUMBER, CAT VARCHAR2)
AS
PROCEDURE FACT(ART VARCHAR2, COD NUMBER, PES NUMBER, CAT VARCHAR2)
AS V_FACT NUMBER(7,2);
BEGIN
SELECT SUM(UNIDADES_PEDIDAS*PRECIO_VENTA) INTO V_FACT FROM ARTICULOS A, PEDIDOS P

WHERE A.ARTICULO=P.ARTICULO AND A.COD_FABRICANTE=P.COD_FABRICANTE


AND A.PESO=P.PESO AND A.CATEGORIA=P.CATEGORIA
and A.ARTICULO=ART AND A.COD_FABRICANTE=COD AND A.PESO=PES AND A.CATEGORIA=CAT;
DBMS_OUTPUT.PUT_LINE(V_FACT);
END FACT;
PROCEDURE NUM_PED(ART VARCHAR2, COD NUMBER, PES NUMBER, CAT VARCHAR2)
AS V_NUM_PED NUMBER(2);
BEGIN
SELECT COUNT(*) INTO V_NUM_PED FROM PEDIDOS WHERE ARTICULO=ART
AND COD_FABRICANTE=COD AND PESO=PES AND CATEGORIA=CAT;
DBMS_OUTPUT.PUT_LINE(V_NUM_PED);
END NUM_PED;
BEGIN
FACT(ART, COD, PES, CAT);
NUM_PED(ART, COD, PES, CAT);
END EJER_9;

BEGIN EJER_9('Macarrones', 20, 1, 'Primera'); END;

-----------------------------------------------------------------------------------
---------------------------------------

10. Crea un procedimiento que recibe el numero de un departamento


y tiene los siguientes especificaciones:
a. Funci n local que con el departamento nos devuelve el n mero de empleados.
b. Funci n local que con el departamento nos devuelve el gasto en salario.
c. El procedimiento realiza llamadas a las funciones locales y muestra el
resultado por pantalla.

CREATE OR REPLACE PROCEDURE EJER_10(DEPT NUMBER)


AS
V_SUM_SALARIO NUMBER(7,2);
V_NUM_EMPLE NUMBER(2);

FUNCTION NUM_EMPLE (DEPT NUMBER)


RETURN NUMBER
AS
V_NUM NUMBER(2);
BEGIN
SELECT COUNT(*) INTO V_NUM FROM EMPLE WHERE DEPT_NO=DEPT;
RETURN V_NUM;
END NUM_EMPLE;

FUNCTION SUM_SALARIO (DEPT NUMBER)


RETURN NUMBER
AS
V_SALARIO NUMBER(7,2);
BEGIN
SELECT SUM(SALARIO) INTO V_SALARIO FROM EMPLE WHERE DEPT_NO=DEPT;
RETURN V_SALARIO;
END SUM_SALARIO;

BEGIN
V_SUM_SALARIO:=SUM_SALARIO(DEPT);
V_NUM_EMPLE:= NUM_EMPLE(DEPT);
DBMS_OUTPUT.PUT_LINE(V_SUM_SALARIO);
DBMS_OUTPUT.PUT_LINE(V_NUM_EMPLE);
END EJER_10;

EJERCICIO 10bis: Crea una funci n que devuelve la facturaci n de un fabricante que
se pasa como par metro.

CREATE OR REPLACE FUNCTION FACT_FABRICANTE (P_COD_FABRICANTE NUMBER)


RETURN NUMBER
AS

V_FACT NUMBER(8,2);

BEGIN

SELECT ROUND(SUM(PRECIO_VENTA*UNIDADES_VENDIDAS), 2) INTO V_FACT


FROM ARTICULOS A, VENTAS V
WHERE A.ARTICULO=V.ARTICULO AND A.COD_FABRICANTE=V.COD_FABRICANTE AND A.PESO=V.PESO
AND A.CATEGORIA=V.CATEGORIA AND A.COD_FABRICANTE=P_COD_FABRICANTE;

RETURN V_FACT;

EXCEPTION
WHEN OTHERS THEN
DBMS_OUTPUT.PUT_LINE('ERROR GENERAL');
END FACT_FABRICANTE;

BEGIN
DBMS_OUTPUT.PUT_LINE(FACT_FABRICANTE(15));
END;
/

Crea un procedimiento que llama a la funci n anterior.


El argumento del procedimiento es el nombre del fabricante y no su num.

CREATE OR REPLACE PROCEDURE FACT_FAB(P_NOMBRE VARCHAR2)


AS
V_COD_FACT FABRICANTES.COD_FABRICANTE%TYPE;
V_FACTURACION NUMBER(8,2);
BEGIN

SELECT COD_FABRICANTE INTO V_COD_FACT FROM FABRICANTES


WHERE NOMBRE = P_NOMBRE;

V_FACTURACION := FACT_FABRICANTE(V_COD_FACT);
DBMS_OUTPUT.PUT_LINE(P_NOMBRE||' factura '||v_facturacion);

EXCEPTION
WHEN NO_DATA_FOUND THEN
DBMS_OUTPUT.PUT_LINE('no hay registros');
WHEN TOO_MANY_ROWS THEN
DBMS_OUTPUT.PUT_LINE('demasiadas filas');
WHEN others THEN
DBMS_OUTPUT.PUT_LINE('demasiadas filas');
END FACT_FAB;

11. Crea un procedimiento con los siguientes especificaciones:


a. Recibe un nombre de centro y especialidad.
b. Tiene un procedimiento local que nos indica cuantos profesores hay con esa
especialidad
y en ese centro.
c. Tiene una funci n local que nos devuelve el n mero de profesores en total
con esa especialidad.
d. El procedimiento principal realiza llamadas a ambos programas locales.

CREATE OR REPLACE PROCEDURE EJER_REF9_11(P_NOMBRE VARCHAR2, P_ESPECIALIDAD


VARCHAR2)
AS
V NUMBER(3);

PROCEDURE CONTAR(P_NOMBRE VARCHAR2, P_ESPECIALIDAD VARCHAR2)


AS
V_TOTAL NUMBER(3);
BEGIN
SELECT COUNT(*) INTO V_TOTAL FROM PROFESORES P, CENTROS C
WHERE P.COD_CENTRO=C.COD_CENTRO AND NOMBRE=P_NOMBRE AND
ESPECIALIDAD=P_ESPECIALIDAD;
DBMS_OUTPUT.PUT_LINE(P_NOMBRE||' '||P_ESPECIALIDAD||' '||V_TOTAL);
END CONTAR;

FUNCTION CONTAR_POR_ESPECIALIDAD(P_ESPECIALIDAD VARCHAR2)


RETURN NUMBER
AS
V_TOTAL NUMBER(3);
BEGIN
SELECT COUNT(*) INTO V_TOTAL FROM PROFESORES WHERE ESPECIALIDAD=P_ESPECIALIDAD;
RETURN V_TOTAL;
END CONTAR_POR_ESPECIALIDAD;

BEGIN
CONTAR(P_NOMBRE, P_ESPECIALIDAD);
V:=CONTAR_POR_ESPECIALIDAD(P_ESPECIALIDAD);
DBMS_OUTPUT.PUT_LINE(V);
END EJER_REF9_11;

12. Crea un procedimiento que recibe los datos de un pedido con las siguientes
identificaciones:
a. Crea una funci n local que devuelve las Existencias de ese art culo.
b. Si existencias es menor que unidades_pedidas, las unidades pedidas ser n de
las existencias (Par metro de E/S).
c. Inserta el pedido y actualiza las unidades pedidas.
d. Se vuelve a llamar a la funci n para que muestre las existencias actuales.
13. Crea un procedimiento que recibe todos los datos de un pedido (Sim trico con
ventas)
que pedir :
a. Si en la llamada los recibe todos o no, har lo siguiente:
i. Si no recibe todos, inserta un articulo.
ii. Si recibe todos pregunta al usuario si quiere insertar un pedido o una venta.
iii. Una vez insertado, actualiza el stock del art culo. (S lo si es pedido) y
en la tabla T_FABRICANTES suma las unidades pedidas totales de los art
culos de
ese fabricante.
iv. Si es una venta en la tabla T_VENTAS incrementa las unidades vendidas de esa
tienda.
T_FABRICANTES (cod_fabricante, nombre, cantidad)
T_TIENDAS (Nif, Nombre, Cantidad)
CREATE OR REPLACE PROCEDURE EJER_REF_9_13(ART VARCHAR2, COD NUMBER, PES NUMBER,
CAT VARCHAR2, TIPO
VARCHAR2,
N VARCHAR2 DEFAULT 0, UNI NUMBER DEFAULT
0)
AS
BEGIN
IF (N = 0) THEN
INSERT INTO ARTICULOS (ARTICULO, COD_FABRICANTE, PESO, CATEGORIA)
VALUES
(ART, COD, PES, CAT);
ELSE
IF (TIPO = 'V') THEN
INSERT INTO VENTAS VALUES (N, ART, COD, PES, CAT, SYSDATE, UNI);

UPDATE T_TIENDAS
SET CANTIDAD = CANTIDAD + UNI
WHERE NIF = N;

ELSE
INSERT INTO PEDIDOS VALUES (N, ART, COD, PES, CAT, SYSDATE, UNI);
UPDATE ARTICULOS SET EXISTENCIAS = EXISTENCIAS + UNI
WHERE ARTICULO=ART AND COD_FABRICANTE=COD AND PESO=PES AND CATEGORIA=CAT;
UPDATE T_FABRICANTES
SET CANTIDAD = CANTIDAD + UNI
WHERE COD_FABRICANTE = COD;
END IF;
END IF;

EXCEPTION
WHEN OTHERS THEN
dbms_output.put_line('error');
END EJER_REF_9_13;
-----------------------------------------------------------------------------------
------------------
MAS EJERCICIOS
-----------------------------------------------------------------------------------
-----
--Ejercicio 1
--Haz una funci�n llamada DevolverCodDept que reciba el nombre de un departamento y
devuelva su c�digo.
create or replace function DevolverCodDept (p_nombre dept.dname%type)
return dept.deptno%type
is
v_codigo dept.deptno%type;
begin
select deptno into v_codigo
from dept
where dname=p_nombre;
return v_codigo;
exception
when NO_DATA_FOUND then
dbms_output.put_line('Departamento '||p_nombre||' no existe');
return -1;
when TOO_MANY_ROWS then
dbms_output.put_line('Departamento '||p_nombre||' repetido');
return -2;
end DevolverCodDept;

--Ejercicio 2
--Realiza un procedimiento llamado HallarNumEmp que recibiendo un nombre de
departamento,
--muestre en pantalla el n�mero de empleados de dicho departamento. Puedes utilizar
la funci�n creada en el ejercicio 1.
--Si el departamento no tiene empleados deber� mostrar un mensaje informando de
ello.
--Si el departamento no existe se tratar� la excepci�n correspondiente.
create or replace procedure HallarNumEmp (p_nombre dept.dname%type)
is
v_codigo dept.deptno%type;
v_numempleados number(4);
begin
v_codigo:=DevolverCodDept(p_nombre);
if v_codigo>=0 then
select count(*) into v_numempleados
from emp
where deptno=v_codigo;
if v_numempleados!=0 then
dbms_output.put_line('El departamento '||p_nombre||' tiene '||
v_numempleados||' empleados');
else
dbms_output.put_line('El departamento '||p_nombre||'no tiene
empleados');
end if;
end if;
end HallarNumEmp;

--Ejercicio 3
--Realiza una funci�n llamada CalcularCosteSalarial que reciba un nombre de
departamento y devuelva la suma de los
--salarios y comisiones de los empleados de dicho departamento. Trata las
excepciones que consideres necesarias.
create or replace function CalcularCosteSalarial (p_nombre dept.dname%type)
return NUMBER
is
v_codigo dept.deptno%type;
v_costetotal number(8);
begin
v_codigo:=DevolverCodDept(p_nombre);
if v_codigo>=0 then
select nvl(sum(sal+nvl(comm,0)),0) into v_costetotal
from emp
where deptno=v_codigo;
return v_costetotal;
else
return v_codigo; -- devuelvo el error de DevolverCodDept
end if;
end CalcularCosteSalarial;

--Ejercicio 4
--Realiza un procedimiento MostrarCostesSalariales que muestre los nombres de todos
los departamentos y el coste salarial
--de cada uno de ellos. Puedes usar la funci�n del ejercicio 3.
create or replace procedure MostrarCostesSalariales
is
cursor c_dept
is
select dname
from dept;
v_coste number(9);
begin
for v_nombres in c_dept loop
v_coste:=CalcularCosteSalarial(v_nombres.dname);
if v_coste>=0 then
dbms_output.put_line(v_nombres.dname||' '||v_coste);
end if;
end loop;
end MostrarCostesSalariales;

--Ejercicio 5
--Realiza un procedimiento MostrarAbreviaturas que muestre las tres primeras letras
del nombre de cada empleado.
create or replace procedure MostrarAbreviaturas
is
cursor c_emp is
select substr(ename, 1, 3) as abreviatura
from emp;
begin
for v_emp in c_emp loop
dbms_output.put_line(v_emp.abreviatura);
end loop;
end MostrarAbreviaturas;

--Ejercicio 6
--Realiza un procedimiento MostrarMasAntiguos que muestre el nombre del empleado
m�s antiguo de cada departamento
--junto con el nombre del departamento. Trata las excepciones que consideres
necesarias.
create or replace procedure MostrarMasAntiguos
is
cursor c_dept
is
select deptno, dname
from dept;
v_nomemp emp.ename%type;
begin
for v_dept in c_dept loop
v_nomemp:=BuscarMasAntiguo(v_dept.deptno);
dbms_output.put_line('Departamento: '||v_dept.dname||' Emp: '||v_nomemp);
end loop;
end MostrarMasAntiguos;

create or replace function BuscarMasAntiguo (p_dept dept.deptno%type)


return emp.ename%type
is
v_nombre emp.ename%type;
begin
select ename into v_nombre
from emp
where deptno=p_dept
and hiredate=(select min(hiredate)
from emp
where deptno=p_dept);
return v_nombre;
exception
when NO_DATA_FOUND then
return 'No tiene empleados';
when TOO_MANY_ROWS then
return 'VARIOS';
end BuscarMasAntiguo;

--Ejercicio 7
--Realiza un procedimiento MostrarJefes que reciba el nombre de un departamento y
muestre los nombres de los empleados
--de ese departamento que son jefes de otros empleados.Trata las excepciones que
consideres necesarias.
create or replace procedure MostrarJefes (p_nombre dept.dname%type)
is
cursor c_emp
is
select ename
from emp
where deptno = (select deptno
from dept
where dname=p_nombre)
and empno in (select mgr
from emp);
v_ind number:=0;
begin
for v_emp in c_emp loop
dbms_output.put_line(v_emp.ename);
v_ind:=1;
end loop;
if v_ind=0 then
dbms_output.put_line('Ning�n empleado de '||p_nombre||' es jefe');
end if;
end MostrarJefes;

--Ejercicio 8
--Realiza un procedimiento MostrarMejoresVendedores que muestre los nombres de los
dos vendedores con m�s comisiones.
--Trata las excepciones que consideres necesarias.
create or replace procedure MostrarMejoresVendedores
is
cursor c_vend
is
select ename
from emp
order by comm desc;
v_vend c_vend%rowtype;
begin
open c_vend;
fetch c_vend into v_vend;
while c_vend%FOUND and c_vend%ROWCOUNT<=3 loop
dbms_output.put_line(v_vend.ename);
fetch c_vend into v_vend;
end loop;
if c_vend%ROWCOUNT<2 then
raise_application_error(-20001,'Hay menos de dos vendedores con comisi�n');
end if;
close c_vend;
end MostrarMejoresVendedores;

--Ejercicio 9
--Realiza un procedimiento MostrarsodaelpmE que reciba el nombre de un departamento
al rev�s y muestre los nombres
--de los empleados de ese departamento. Trata las excepciones que consideres
necesarias.
Create or replace procedure MostrarsodaelpmE (p_nombre dept.dname%type)
is
v_nombredept dept.dname%type;
begin
v_nombredept:=DevolverCadalReves(p_nombre);
MostrarEmpleados(v_nombredept);
end MostrarsodaelpmE;

create or replace procedure MostrarEmpleados(p_nombre dept.dname%type)


is
cursor c_emp
is
select ename
from emp
where deptno = (select deptno
from dept
where dname=p_nombre);
begin
for v_emp in c_emp loop
dbms_output.put_line(v_emp.ename);
end loop;
end MostrarEmpleados;

create or replace function DevolverCadAlReves( p_cad VARCHAR2)


return VARCHAR2
is
v_aux VARCHAR2(30):='';
begin
for i in reverse 1..length(p_cad) loop
v_aux:=v_aux||substr(p_cad,i,1);
end loop;
return v_aux;
end DevolverCadAlReves;

--Ejercicio 10
--Realiza un procedimiento RecortarSueldos que recorte el sueldo un 20% a los
empleados cuyo nombre empiece por la letra
--que recibe como par�metro. Trata las excepciones que consideres necesarias.
create or replace procedure RecortarSueldos (p_letra VARCHAR2)
is
begin
update emp
set sal = sal � 0.2*sal
where substr(ename, 1, 1)=p_letra;
if SQL%NOTFOUND then
dbms_output.put_line('Ningun empleado actualizado');
else
dbms_output.put_line(SQL%ROWCOUNT||'empleados actualizados');
end if;
end RecortarSueldos;

--Ejercicio 11
--Realiza un procedimiento BorrarBecarios que borre a los dos empleados m�s nuevos
de cada departamento.
--Trata las excepciones que consideres necesarias.
Create or replace procedure BorrarBecarios
is
cursor c_dept
is
select deptno
from dept;
begin
for v_dept in c_dept loop
BorrarDosMasNuevos(v_dept.deptno);
end loop;
end BorrarBecarios;

create or replace procedure BorrarDosMasNuevos(p_deptno dept.deptno%type)


is
cursor c_emp
is
select empno
from emp
where deptno= p_deptno
order by hiredate desc;
v_emp c_emp%rowtype;
begin
open c_emp;
fetch c_emp into v_emp;
while c_emp%found and c_emp%rowcount<=2 loop
delete emp
where empno=v_emp.empno;
fetch c_emp into v_emp;
end loop;
close c_emp;
end BorrarDosMasNuevos;

También podría gustarte