Estoy tratando de actualizar una tabla en Oracle y estoy teniendo dificultades. Estoy portando mi código desde MySQL y algunos de los comandos que permite MySQL no son compatibles con Oracle.LIMIT/OFFSET en Oracle 11G
Aquí está el código de MySQL:
update table1 t1 set c5 = (select ContractID from table2 t2 where t1.assetid =
t2.assetid and t1.lastdate >= t2.lastdate and t1.firstdate= t2.firstdate
order by lastdate asc limit 1 offset 4);
La sentencia devuelve una lista de ContractIDS, ordenados por últimofecha y sólo quieren una en particular, por lo tanto, el comando de desplazamiento X 1 límite.
El problema es el siguiente. Oracle no admite los comandos "límite" o "desplazamiento". Hay soluciones para el problema límite utilizando rownum y consultas anidadas, pero al analizador Oracle 11G no le gustan en un comando UPDATE.
Tuve un problema similar antes donde necesitaba un límite dentro de un comando de actualización, pero no un desplazamiento. Fue resuelto aquí: MySQL to Oracle Syntax Error (Limit/Offset/Update)
Hay una solución temporal que Florin Ghita encontró utilizando funciones analíticas.
update table1 alf
set nextcontractid =
(SELECT min(contractid) keep (dense_rank first order by lasttradedate asc)
FROM table1copy alf2
WHERE alf2.assetid = alf.assetid
AND alf2.lasttradedate > alf.lasttradedate
)
where alf.complete = 0
Esta solución permite que consiga la entrada superior o inferior (mediante el uso de ASC o DESC en el comando DENSE_RANK), pero no soy capaz de encontrar un sustituto para el comando de desplazamiento, si quería el segundo o tercera fila.
Otra solución que he probado utilizaba una consulta anidada. El primero obtuvo las primeras 5 filas usando el comando rownum, las ordenó en el sentido opuesto, el MINUS-ed en las últimas cuatro filas. Esta solución falló porque el analizador de Oracle no entendía la referencia a una tabla en el comando más externo al que se hacía referencia dentro de una de las consultas anidadas.
(mismo problema que yo tenía antes: MySQL to Oracle Syntax Error (Limit/Offset/Update))
El reto no es simplemente para ejecutar una instrucción de selección en el oráculo con un límite y offset, como ya puedo hacerlo a través de consultas anidadas. El desafío es hacer que la instrucción select funcione en una declaración de actualización, porque aunque la declaración es sintácticamente correcta, el analizador de Oracle no puede decodificarlas. Hasta ahora, las consultas anidadas (y Google) me han fallado.
¿Alguien más ha tenido problemas similares?
Si actualiza a 12c, que podría ser capaz de hacer algo como 'actualización tabla1 conjunto t1 c5 = (seleccionar ContractID de t2 tabla2 donde t1.assetid = t2.assetid y t1.lastdate> = t2.lastdate y t1.firstdate = t2.firstdate order por lastdate asc offset 4 buscar next 1 row solamente); ' – beldaz
Relacionado, y probablemente útil si tiene Oracle 12cR1 (o superior): http://stackoverflow.com/a/26051830/1461424 – Krumia