не может создать единый набор результатов оракула или подзапросы - PullRequest
0 голосов
/ 29 декабря 2011

У меня есть три основных запроса, которые связаны друг с другом, и мне нужен один набор результатов для возврата.

Упрощенная:

Query1 (возможный возврат, не показанный пробник, возврат null):

SELECT * FROM monkey WHERE monkey.ENDDATE IS NULL AND monkey.TEMPLATEID = 1

Query2 (возможен возврат, но не показывать пробку, возвращать ноль):

SELECT * FROM banana WHERE banana.ENDDATE IS NULL AND banana.TEMPLATEID = 1

Query3 (должен что-то вернуть):

SELECT * FROM tree WHERE tree.TEMPLATEID = 1

Запросы 1 и 2 могут возвращать или не возвращать значение (возвращать ноль).

Третий должен будет вернуть результат (или нет), если третий запрос возвращает что-то, что я, и запрос 1 или 2 не выполнен. Я все еще хочу вернуть что-то.

Я не могу выполнить внешнее объединение с двумя запросами, потому что оракул не даст мне сказать ошибку… a.b (+) = b.b and a.c(+) = c.c is not allowed instead turn b+c into a view.

Мне кажется, я понимаю логическую причину, тем не менее мне нужно вернуть запрос 3 и, возможно, запрос 1, 2 или 1 и 2 вместе с 3 в виде единого набора результатов.

Надеюсь, это имеет смысл.

Ответы [ 2 ]

4 голосов
/ 29 декабря 2011

Кажется, вы попали в ORA-01417.Используя составленные таблицы и данные, которые вы не предоставили, или условия соединения, я могу получить тот же эффект, пытаясь выполнить внешнее соединение monkey с tree и banana - полностью надуманным способом,курс:

with banana as (select 'yellow' as colour, 1 as template_id, null as enddate
        from dual),
    monkey as (select 'capuchin' as monkeytype, 1 as template_id, null as enddate
        from dual),
    tree as (select 'tropical' as treetype, 1 as template_id from dual)
select t.treetype, b.colour, m.monkeytype
from tree t, banana b, monkey m
where t.template_id = 1
and b.template_id (+) = t.template_id
and b.enddate (+) is null
and m.template_id (+) = t.template_id
and m.enddate (+) is null
and m.template_id (+) = b.template_id;

Error at Command Line:10 Column:22
Error report:
SQL Error: ORA-01417: a table may be outer joined to at most one other table
01417. 00000 -  "a table may be outer joined to at most one other table"
*Cause:    a.b (+) = b.b and a.c (+) = c.c is not allowed
*Action:   Check that this is really what you want, then join b and c first
           in a view.

если вы используете «новый» (начиная с 9i, ​​я думаю) синтаксис объединения ANSI, а не специфическую для Oracle нотацию (+), вы можете сделать больше:

with banana as (select 'yellow' as colour, 1 as template_id, null as enddate
        from dual),
    monkey as (select 'capuchin' as monkeytype, 1 as template_id, null as enddate
        from dual),
    tree as (select 'tropical' as treetype, 1 as template_id from dual)
select t.treetype, b.colour, m.monkeytype
from tree t
left join banana b on b.template_id = t.template_id
    and b.enddate is null
left join monkey m on m.template_id = t.template_id
    and m.enddate is null
    and m.template_id = b.template_id
where t.template_id = 1;

TREETYPE COLOUR MONKEYTYPE 
-------- ------ ---------- 
tropical yellow capuchin   

См. документацию для ознакомления с некоторыми ограничениями на (+);Oracle рекомендует использовать версию ANSI, хотя они, похоже, большую часть времени используют свои собственные примеры в документации.

1 голос
/ 29 декабря 2011

Я подозреваю, что таблицы «monkey», «banana» и «tree» имеют разные типы столбцов, в противном случае вы можете легко получить то, что хотите, используя оператор «UNION» или «UNION ALL».

Кроме того, поскольку вы не поделились таблицей defn.из этих таблиц я не знаю, есть ли у вас какие-либо внешние ключи для присоединения к этим таблицам или нет.Так что я предполагаю, что они совершенно не связаны.

Итак, с этими двумя допущениями ....

Вот еще один способ возврата комбинированных результатов из разных запросов.

SELECT CURSOR(QRY1), CURSOR(QRY2), CURSOR(QRY3) FROM DUAL;

Это даст вам все три набора результатов в одном запросе.Но каждый набор результатов является реф-курсором, по которому вам придется перемещаться в вашем приложении.

При использовании java тип java каждого из 3 столбцов - это ResultSet, который у вас будетдля навигации, чтобы получить отдельные результаты запроса.

например,

String qry1= "SELECT * FROM monkey WHERE monkey.ENDDATE IS NULL";
String qry2 = " SELECT * FROM banana WHERE banana.ENDDATE IS NULL AND banana.TEMPLATEID = 1";
String qry3= "SELECT * FROM tree WHERE tree.ENDDATE IS NULL AND tree.TEMPLATEID = 1";

String qry = "SELECT CURSOR("+qry1+"), CURSOR("+qry2+"), CURSOR("+qry3+") FROM DUAL";

ResultSet rs = conn.createStatement().executeQuery(qry);

if(rs.next()) { //no while loop necessary, as we are expecting only one row

    ResultSet rs1 = (ResultSet) rs.getObject(1);
    ResultSet rs2 = (ResultSet) rs.getObject(2);
    ResultSet rs3 = (ResultSet) rs.getObject(3);


    while(rs1.next()) {
        // retrive results of qry1
    }

    // same for rs2 and rs3
}

Надеюсь, что помог.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...