Вы, вероятно, хотели сказать MAX + 1
(см. Строки 7 и 12), т.е.
SQL> create table customers
2 (customer_id number,
3 customer_name varchar2(20),
4 card_number varchar2(20));
Table created.
SQL> DECLARE
2 v_cname customers.customer_name%type := '&customer_name';
3 v_cardno customers.card_number%type := '&card_number';
4 v_lastcid customers.customer_id%type;
5
6 BEGIN
7 SELECT nvl(max(customer_id), 0) INTO v_lastcid from customers
8 where customer_id = (select max(customer_id) from customers);
9 dbms_output.put_line(v_lastcid);
10
11 INSERT INTO customers(customer_id, customer_name, card_number)
12 VALUES(v_lastcid + 1, v_cname, v_cardno);
13 COMMIT;
14 END;
15 /
Enter value for customer_name: Little
Enter value for card_number: Foot
0
PL/SQL procedure successfully completed.
SQL> select * from customers;
CUSTOMER_ID CUSTOMER_NAME CARD_NUMBER
----------- -------------------- --------------------
1 Little Foot
SQL>
Хотя он работает , он обречен на неудачу в многопользовательской среде, если два (или более) пользователя получают одно и то же значение MAX
; вставка завершится с ошибкой DUP-VAL-ON-INDEX
(если идентификатор должен быть уникальным).
Следовательно, используйте последовательность (именно это и предлагает NEXTVAL
в вашем коде):
SQL> create sequence seq_cust;
Sequence created.
SQL> DECLARE
2 v_cname customers.customer_name%type := '&customer_name';
3 v_cardno customers.card_number%type := '&card_number';
4 v_lastcid customers.customer_id%type;
5 BEGIN
6 INSERT INTO customers(customer_id, customer_name, card_number)
7 VALUES(seq_cust.nextval, v_cname, v_cardno);
8 COMMIT;
9 END;
10 /
Enter value for customer_name: Big
Enter value for card_number: Foot
PL/SQL procedure successfully completed.