2009-10-15 4 views
27

Я провел часы поиска в Интернете для ответа на этот вопрос ...Oracle: Как я могу выбрать записи ТОЛЬКО со вчерашнего дня?

Вот что я в настоящее время:

select * 
from order_header oh 
where tran_date = sysdate-1 

Спасибо заранее.

+0

Я все еще получаю записи с прошлого года после попытки все предложения. –

+1

Каков тип данных столбца 'tran_date'? –

+0

Пожалуйста, разместите некоторые данные образца и точный запрос, который вы используете. Потому что нет абсолютно никакого способа, чтобы правильно написанный запрос, ограниченный на SYSDATE-1, должен возвращать строки, которые соответствуют SYSDATE-366. – APC

ответ

58

Использование:

AND oh.tran_date BETWEEN TRUNC(SYSDATE - 1) AND TRUNC(SYSDATE) - 1/86400 

Ссылка: TRUNC

Вызов функции на tran_date означает, что оптимизатор не сможет использовать индекс (если таковой существует), связанный с этим. Некоторые базы данных, такие как Oracle, поддерживают индексы на основе функций, которые позволяют выполнять функции по данным, чтобы минимизировать воздействие в таких ситуациях, но администраторы баз данных IME этого не позволят. И я согласен - они не нужны в этом случае.

+4

Одно небольшое предостережение - вам может потребоваться вычесть 1 секунду из верхней границы. В противном случае, если у вас есть TRAN_DATE, который сегодня в полночь, он будет возвращен в запросе для вставленных вчера строк. Я бы не ожидал, что это будет желаемое поведение. –

+1

Учтите, что это решение не учитывает летнее время. Это решение предполагает, что каждый день длится 24 часа, при дневном свете «день» длится 23 часа или 25 часов. – sbrbot

10
trunc(tran_date) = trunc(sysdate -1) 
+3

Если, как я полагаю, есть индекс в tran_date, на который этот запрос опирается, вызов funtion в индексированном столбце, подобный этому, уменьшит производительность запроса. – ninesided

+0

тогда метод rexem будет полезен. –

+1

В этом случае вы можете добавить индекс на основе функции: создать индекс index_name на имя_таблицы (trunc (tran_date)); –

1
to_char(tran_date, 'yyyy-mm-dd') = to_char(sysdate-1, 'yyyy-mm-dd') 
+1

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

1

Если вы не поддерживать будущие датированные операции, то что-то подобное может работать:

AND oh.tran_date >= trunc(sysdate-1) 
1

Этот комментарий для читателей, которые нашли эту запись, но с использованием MySQL вместо оракула! на MySQL вы можете сделать следующее: Сегодня

SELECT * 
FROM 
WHERE date(tran_date) = CURRENT_DATE() 

Вчера

SELECT * 
FROM yourtable 
WHERE date(tran_date) = DATE_SUB(CURRENT_DATE(), INTERVAL 1 DAY) 
+0

Я получаю «ORA-00936 недостающее выражение» на дату. См. Http://stackoverflow.com/questions/19143376/ora-00936-when-using-date-function-in-the-oracle-select-statement – NealWalters

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