2013-07-10 2 views
1

Я смущен DISTINCT в JPQL. У меня есть два JPQL запросов идентичны для «DISTINCT», за исключением одного из них:JPQL «DISTINCT» возвращает только один результат

String getObjectsForFlow = 
    "SELECT " + 
    " se.componentID " + 
    "FROM " + 
    " StatisticsEvent se " + 
    "WHERE " + 
    " se.serverID IS NOT NULL " + 
    " AND se.flowID = :uuid " + 
    " AND se.componentID IS NOT NULL " + 
    "ORDER BY " + 
    " se.timeStamp desc "; 

String getObjectsForFlowDistinct = 
    "SELECT DISTINCT " + 
    " se.componentID " + 
    "FROM " + 
    " StatisticsEvent se " + 
    "WHERE " + 
    " se.serverID IS NOT NULL " + 
    " AND se.flowID = :uuid " + 
    " AND se.componentID IS NOT NULL " + 
    "ORDER BY " + 
    " se.timeStamp desc "; 

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

NOT DISTINCT 
::: 01e2e915-35c1-6cf0-9d0e-14109fdb7235 
::: 01e2e915-35c1-6cf0-9d0e-14109fdb7235 
::: 01e2e915-35d9-afe0-9d0e-14109fdb7235 
::: 01e2e915-35d9-afe0-9d0e-14109fdb7235 
::: 01e2e915-35bd-c370-9d0e-14109fdb7235 
::: 01e2e915-35bd-c370-9d0e-14109fdb7235 
::: 01e2e915-35aa-1460-9d0e-14109fdb7235 
::: 01e2e915-35d1-2460-9d0e-14109fdb7235 
::: 01e2e915-35e1-7810-9d0e-14109fdb7235 
::: 01e2e915-35e1-7810-9d0e-14109fdb7235 
::: 01e2e915-35d0-12f0-9d0e-14109fdb7235 
::: 01e2e915-35b0-cb20-9d0e-14109fdb7235 
::: 01e2e915-35a8-66b0-9d0e-14109fdb7235 
::: 01e2e915-35a8-66b0-9d0e-14109fdb7235 
::: 01e2e915-35e2-6270-9d0e-14109fdb7235 
::: 01e2e915-357f-33d0-9d0e-14109fdb7235 
DISTINCT 
::: 01e2e915-35e2-6270-9d0e-14109fdb7235 

Адрес: Я ожидал бы список DISTINCT, содержащий одиннадцать (я думаю) записей.

+0

Что такое SQL, сгенерированный для каждого запроса? – James

+0

Не указано: SELECT objectClockSeqAndNode, objectTime FROM STATISTICSEVENT WHERE ((NOT (((sessionClockSeqAndNode IS NULL) AND (sessionTime IS NULL))) AND ((flowClockSeqAndNode =?) AND (flowTime =?))) AND NOT (((objectClockSeqAndNode IS NULL) И (objectTime IS NULL)))) ORDER BY TIMESTAMP DESC – DataN00bleus

+0

Distinct: SELECT DISTINCT objectClockSeqAndNode, objectTime, ТШЕЗТАМР ОТ STATISTICSEVENT ГДЕ ((НЕ (((sessionClockSeqAndNode IS NULL) И (sessionTime IS NULL))) AND ((flowClockSeqAndNode =?) AND (flowTime =?))) AND NOT (((objectClockSeqAndNode IS NULL) AND (objectTime IS NULL)))) ORDER BY TIMESTAMP DESC – DataN00bleus

ответ

0

Двойная проверка equals() метода на вашем объекте класса StatisticsEvent. Возможно, эти семантически разные значения возвращаются одинаково, когда вызывается equals(), производя такое поведение.

+0

StatisticsEvent не имеет реализации equals(). Ваш комментарий заставил меня написать его, и я получил те же результаты, что и раньше. – DataN00bleus

0

Проблема была в предложении «ORDER BY se.timeStamp». Чтобы выполнить запрос, JPQL добавила поле ORDER BY в предложение SELECT DISTINCT.

Это похоже на пограничный случай во взаимодействии между JPQL и SQL. Синтаксис JPQL явно применяет модификатор DISTINCT только к se.componentID, но при переходе на SQL вставляется поле ORDER BY.

Я удивлен, что поле ORDER BY должно быть выбрано вообще. Некоторые базы данных могут возвращать набор данных ORDERed с помощью поля, не входящего в SELECT. Oracle может это сделать. Моя базовая база данных - Derby - может ли это быть ограничением в Derby?

0

Oracle не поддерживает SELECT DISTINCT с заказом, если порядок по столбцам находится в SELECT. Не уверен, работают ли какие-либо базы данных. Он будет работать в Oracle, если DISTINCT не требуется (не запускается, потому что строки уникальны), но если ему нужно запустить, вы получите сообщение об ошибке.

вы получите, "ORA-01791: не выбранного выражения"

Если вы используете EclipseLink эта функциональность контролируется методом DatabasPlatform,

shouldSelectDistinctIncludeOrderBy()

Вы можете продлить ваша платформа вернет false, если ваша база данных не требует этого.

Тем не менее, я не вижу, как добавление TIMESTAMP изменит результаты запроса?

+0

Вы правы; Я был неправ. Эта ссылка объясняет, почему поле ORDER BY должно быть частью предложения SELECT DISTINCT: https://forums.oracle.com/thread/256910 – DataN00bleus

0

Оба запроса являются неправильными запросами JPQL, поскольку предложение ORDER BY относится к элементу, который не находится в списке выбора. JPA 2.0 спецификация содержит пример, который соответствует этому случаю:

Следующих два запроса не является законным, потому что это orderby_item не отражен в пункте SELECT, запрос.

ВЫБОР p.product_name ОТ порядка О РЕГИСТРИРУЙТЕСЬ o.lineItems л РЕГИСТРИРУЙТЕСЬ l.product р РЕГИСТРИРУЙТЕСЬ o.customer гр
ГДЕ c.lastname = 'Смит' И c.firstname = 'John'
ORDER BY р .price

ВЫБОР p.product_name
от порядка о, ВО (o.lineItems) л РЕГИСТРИРУЙТЕСЬ o.customer гр
где С.Lastname = «Смит» И c.firstname = «John» ORDER BY o.quantity

Конечно, было бы лучше, если бы, если реализация может дать четкое сообщение об ошибке, вместо того, чтобы пытаться угадать, что, как ожидается, результат неверный запрос.

+0

Значит, они не являются законными, но также не отклонены? Это сбивает с толку. Как вы сказали, если это недопустимый запрос, они не должны пытаться запустить его. – DataN00bleus

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