После запуска SELECT DISTINCT дубликаты все еще отображаются

#oracle #select #duplicates #distinct

#Oracle #выберите #дубликаты #distinct

Вопрос:

Я все еще вижу дубликаты в своих результатах после запуска SELECT DISTINCT , несмотря на использование всех соответствующих методов для обеспечения того, чтобы повторяющиеся строки действительно дублировались (применение обрезки ко всем полям, форматирование полей даты только как даты и т. Д.). Я даже пытался GROUP BY , но после его запуска дубликаты все равно появлялись. Есть ли у кого-нибудь хоть малейшее представление о том, что в мире происходит, и что я могу сделать?

 SELECT DISTINCT 
    ID, Address_Line_1, Address_Line_2, City, State, Zip, 
    to_date(START_DATE, 'DD-MON-YYYY') as START_DATE, 
    to_date(END_DATE, 'DD-MON-YYYY') as END_DATE 
FROM 
    AddressHistory
ORDER BY 
    ID, START_DATE DESC;
 

введите описание изображения здесь

Комментарии:

1. Вы пробовали то, что я предложил, когда вы опубликовали тот же вопрос вчера? Я не вижу, чтобы TRUNC применялся к датам в вашем запросе в этом вопросе. Исходя из этого, предполагая, что «даты» действительно являются типом данных, почему вы применяете к ним TO_DATE? TO_DATE следует применять к строкам , чтобы преобразовать их в даты.

2. Предоставьте тестовый пример: СОЗДАЙТЕ ТАБЛИЦУ и ВСТАВЬТЕ В несколько выборочных строк (будет достаточно «E 3RD ST»), чтобы мы увидели, что у вас действительно есть, что возвращает ваш запрос и почему.

3. Каков тип данных столбцов start_date и end_date? Если это типы ДАТЫ, тогда используйте TRUNC — никогда не используйте TO_DATE для значения, которое уже является ДАТОЙ. Если они являются строковыми типами данных, то у вас могут быть такие значения, как «01-Jan-2020» и «01-JAN-2020», и еще один пример, почему никогда не следует хранить значения даты / времени в виде строки.

4. Если вы select dump(column_name) from table , вы увидите, что именно вычисляет каждый столбец / выражение в двоичном выводе и в чем разница. Без воспроизводимого примера я предполагаю, что одна из дат находится в столетии, отличном от того, которое вы ожидаете (т. Е. Одна дата приходится на 2013 год, а другая — на 1913 или 0013 год).). Но это всего лишь предположение без дополнительной информации.

5. @mathguy, когда я выполняю Trunc(Start_Date), я получал следующую ошибку. Это было связано с тем, что в некоторых записях были нули, поэтому при обнаружении нулей выдавалась ошибка. Вот почему я попробовал что-то еще, но я понимаю, что вы говорите ORA-01722: недопустимый номер 01722. 00000 — «недопустимый номер» * Причина: указанный номер был недействительным. * Действие: укажите допустимое число.

Ответ №1:

Попробуйте

 SELECT DISTINCT 
     ID, Address_Line_1, Address_Line_2, City, State, Zip, 
     trunc(to_date(START_DATE, 'DD-MON-YYYY')) as START_DATE, 
     trunc(to_date(END_DATE, 'DD-MON-YYYY')) as END_DATE  FROM 
AddressHistory 
ORDER BY ID, START_DATE DESC;
 

Это сокращает время даты и выполняется быстрее, чем преобразование приведения типов.

Какой тип данных START_DATE в вашем примере? Возможно, вы можете полностью избавиться от приведения типов?

Комментарии:

1. Похоже, что комбинация использования обрезки вокруг определенных полей (для удаления скрытых символов) И подход trunc(to_date(START_DATE, ‘DD-MON-ГГГГ’)) as START_DATE решил проблему

Ответ №2:

Это связано с тем, что фактор времени в вашем столбце START_DATE и END_DATE не совпадает, вы должны получить distinct, если вы напишете свой запрос следующим образом.

 SELECT DISTINCT * FROM
(
    SELECT  ID, Address_Line_1, Address_Line_2, City, State, Zip, to_date(START_DATE, 'DD-MON-YYYY') as START_DATE, to_date(END_DATE, 'DD-MON-YYYY') as END_DATE

    FROM AddressHistory
)T

ORDER BY ID, START_DATE desc; 
 

Комментарии:

1. Этот ответ неверен (несмотря на то, что один голос уже был поддержан). Неправильно, поскольку приложение TO_DATE находится в запросе OP, если оно не выдает ошибку, это приведет к датам с компонентом времени суток, равным полуночи.