2017-01-13 4 views
1

EDITEDPL/SQL Oracle - Выбор из внутренней таблицы

У меня есть проблемы с выполнением какой-PL-код/​​SQL. есть реальный стол a. Я хочу взять только элементы с range<=100. Я создаю коллекцию внутри своего PL/SQL на основе этой таблицы. Затем я хочу выполнить операцию SELECT в этой коллекции. Но у меня проблемы с этим.

Подготовленная таблица (это все, например, это не проблема. Мне просто интересно узнать, как я могу выбрать из коллекции в блоке кода PL/SQL).

CREATE TABLE a (amount NUMBER); 
INSERT INTO a VALUES (50); 
INSERT INTO a VALUES (100); 
INSERT INTO a VALUES (200); 

А потом я получил этот блок:

DECLARE 
    TYPE aTable IS TABLE OF a%ROWTYPE; 
    aActual aTable; 
    temp NUMBER; 
BEGIN 
    SELECT * BULK COLLECT INTO aActual 
    FROM a WHERE amount<=100; 

    SELECT SUM(amount) INTO temp FROM TABLE(aActual); 
    DBMS_OUTPUT.PUT_LINE(temp); 
END; 

Но я получил eroor PLS-00642 и ORA-22905. Что мне делать? Почему это не работает? Я на Oracle Database 12c Enterprise Edition Release 12.1.0.2.0 - 64bit Production версии (по SELECT * FROM V$VERSION;)

+0

Если вам не нужна таблица aActual для чего-либо еще, не используйте ее. Просто выберите сумму диапазона из таблицы Kocury. –

+0

@ DanBracuk Я знаю, но мне нужна эта таблица. Здесь я представил только небольшое количество кода, чтобы объяснить, какую проблему я получу. – michalsol

ответ

4

Вы не можете это сделать, потому что aTable не является таблицей базы данных. (Да, я знаю, что это определенно с table of но не определяет таблицу Одна из тех вещей.).

Чтобы задать SQL для лечения коллекция в качестве таблицы базы данных вы должны использовать table() конструкции:

select sum(amount) into temp from table(aActual); 

хотя это потерпит неудачу в вашем примере из-за обзорные вопросы, и вы получите сам-пояснительная

PLS-00642: local collection types not allowed in SQL statements 

для того, чтобы работать, вы должны были бы типом уровня схемы, т.е. один созданный с create type:

create or replace type xyz as object (a integer, b varchar2(3), c date); 

create or replace type xyz_tt as table of xyz; 

Теперь введите xyz_tt в действие, опубликованной в SQL и его можно использовать в SQL table() выражений.

+0

Да, вы знаете, что я имею в виду :) Но когда я сделал это, я получил ошибку ORA-22905 вместо PLS-00642. Как я могу это исправить? – michalsol

+0

Кстати, нет такой вещи, как «внутренняя таблица» и «таблица» в PL/SQL фактически определяет коллекцию. С точки зрения PL/SQL Oracle могла бы использовать более понятное ключевое слово, такое как 'array' (как в Ada) или' collection', но они также нуждались в синтаксисе для ссылки на [вложенные столбцы таблицы] (http: // www .orafaq.com/wiki/NESTED_TABLE) в таблицах базы данных. –

+0

Ну, на самом деле у меня есть оба сообщения в стеке ошибок, когда я тестировал его с локальным типом коллекции. Добавьте его к своему вопросу, и я посмотрю. –

0

Как показал WilliamRobertson, вы не можете использовать коллекцию PL/SQL в SQL-запросе. Вы можете перебрать коллекцию и добавить каждую сумму в свою временную переменную, сначала инициализируя ее нулем:

temp := 0; 
for i in 1..aActual.count loop 
    temp := temp + aActual(i).amount; 
end loop; 
DBMS_OUTPUT.PUT_LINE(temp); 
+1

Вы можете использовать коллекции PL/SQL в SQL-запросах в Oracle 12.1 позже. –

+0

Да, я хотел сказать об этом. Из ошибок я не думаю, что OP находится на 12c. –

+0

В нем говорится, что я использую версию Oracle Database 12c Enterprise Edition Release 12.1.0.2.0. Я обновил свой вопрос – michalsol

Смежные вопросы