2012-02-07 7 views
10

Próbuję wstawić do tabeli i używa jednej instrukcji select dla jednej kolumny. Poniżej znajduje się ilustracja mojego zapytania.ORA-00907 Brakuje problemu z prawym rodzajem - wybierz z zamówieniem za pomocą wewnętrznego zapytania wstawiania

INSERT INTO MY_TBL (MY_COL1, MY_COL2) 
VALUES (
(SELECT DATA FROM FIR_TABL WHERE ID = 1 AND ROWNUM = 1 ORDER BY CREATED_ON DESC), 
1 
); 

Rzuca ORA-00907 Missing right Parenthesis. Jeśli usuniemy z tego ORDER BY, działa zgodnie z oczekiwaniami. Ale potrzebuję go zamówić. Proszę o wyjaśnienie.

Z góry dziękuję.

+4

bym pytanie modelu danych, jeśli „polegać” na zlecenie danych umieszczonych w tabeli bazy danych. Kolejność wstawiania powinna być nieistotna, podczas sortowania danych wykonujesz porządek. – Ollie

+0

Jak myślisz, co w tym kontekście zrobi dla Ciebie "ZAMÓW"? –

+0

Podałem przykład, może być wiele wierszy dla tego wyboru. Ponadto w kolumnie MY_TBL znajduje się wiele kolumn. Sprawdź moją aktualizację. – Vaandu

Odpowiedz

20

zarówno bieżącą odpowiedzi ignorować faktu, że za pomocą order by i rownum w tej samej kwerendy jest z natury niebezpieczne. Nie ma absolutnie żadnej gwarancji, że dostaniesz dane, które chcesz. Jeśli chcesz pierwszy wiersz z uporządkowanym zapytania ty musi korzystania sub-zapytanie:

insert into my_tbl (col1, col2) 
select data, 'more data' 
    from (select data 
      from fir_tabl 
      where id = 1 
      order by created_on desc) 
where rownum = 1 
     ; 

Można również użyć funkcji takich jak rank zamówić dane w sposób chcesz, ale jeśli miał dwa created_on daty, które były identyczne, skończyłoby się 2 wartościami z rnk = 1.

insert into my_tbl (col1, col2) 
select data, 'more data' 
    from (select data 
       , rank() over (order by created_on desc) as rnk 
      from fir_tabl 
      where id = 1) 
where rnk = 1 
     ; 
+0

To wydaje się naprawić dla Oracle. Przekonwertuj go, aby użyć dodatkowej kwerendy, a "brakujący nawias prawostronny" (nawet jeśli nie brakuje nawiasu) zniknie. Dzięki! – rogerdpack

+0

Czy istnieje jakiekolwiek odniesienie do faktu, że używanie zamówienia przez i rownum w tym samym zapytaniu jest z natury niebezpieczne? – jeromerg

+0

Jestem pewna, że ​​Tom Kate napisał coś na temat @jeromerg, ale powinieneś być w stanie to zobaczyć na podstawie pierwszych zasad. Tabela sterty jest przechowywana, a zatem pobierana, nieposortowana. Klauzula ORDER BY jest zawsze ostatnią operacją do wykonania. Dlatego predykat ROWNUM zostanie użyty przed zamówieniem nieuporządkowanego zestawu. Najpierw musisz zamówić i ze względu na kolejność działania instrukcji SQL, zamówienie musi się odbyć w wewnętrznym select (do 12c ze składnią FETCH N ROWS i tylko z nią) – Ben

0

Nie używasz SELECT, gdy używasz słowa kluczowego VALUES. Użyj tego zamiast:

INSERT INTO MY_TBL (MY_COL) 
SELECT DATA FROM FIR_TABL WHERE ID = 1 ORDER BY CREATED_ON DESC 
; 

Twój edytowany kwerendy wyglądałby następująco:

INSERT INTO MY_TBL (MY_COL1, MY_COL2) 
SELECT DATA, 1 FROM FIR_TABL WHERE ID = 1 AND ROWNUM = 1 ORDER BY CREATED_ON DESC 
; 
0

Zgadzam się, że należy zamawiać podczas wyodrębniania danych, a nie podczas wstawiania.

Jednak jako obejście problemu można było wyodrębnić klauzulę ORDER BY z INSERT, włączając w to cały SELECT do innego SELECT.

To pozwoli uniknąć błędu:

INSERT INTO MY_TABLE (
SELECT * FROM (
    SELECT columns 
    FROM table 
    ORDER BY clause 
    ) 
) 
Powiązane problemy