2010-03-25 16 views
2

Предположим, у меня есть таблица с двумя столбцами (id, flag), а id - последовательная. Я ожидаю, что в этой таблице будет много записей. Я хочу периодически выбирать первую строку, не помеченную и обновлять ее. Некоторые из записей на пути, возможно, уже отмечены, поэтому я хочу пропустить их., который является более быстрой/лучшей практикой sql?

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

select * from mytable where id > my_last_id order by id asc limit 1 

или просто получить первое unflagged строки, как:

select * from mytable where flagged = 'F' order by id asc limit 1 

Спасибо!

+0

(возможно, опечатка) Значит ли «flagged = 'F» означать, что ваша запись UNflagged? –

+0

хорошая точка .. F означает false – artsince

ответ

0

Предполагая MySQL, это один:

SELECT * 
FROM mytable 
WHERE flagged = 'F' 
ORDER BY 
     flagged ASC, id ASC 
LIMIT 1 

будет несколько менее эффективным в InnoDB и той же эффективностью в MyISAM, если у вас есть индекс по (flagged, id).

InnoDB таблицы сгруппированы по PRIMARY KEY, поэтому выбор первой записи в id не требует поиска таблицы.

В MyISAM, таблицы организованы в кучу, поэтому индекс, используемый для защиты PRIMARY KEY, хранится отдельно от таблицы.

Примечание: flagged в предложении ORDER BY может показаться излишним, но для определения нужного индекса требуется MySQL.

Кроме того, составной индекс должен быть на (flagged, id) даже в InnoDB (что неявно включает PRIMARY KEY в каждый индекс).

+0

Что такое точка заказа 'flagged', так как это фильтр (* с одним допустимым значением в наборе результатов *) ... это бесполезно ... –

+0

@Gaby: это поможет 'MySQL' выбрать правильный индекс. – Quassnoi

+0

@Quassnoi, если это неотъемлемая проблема с реализацией, тогда я объявляю свое невежество на нем :) это просто кажется довольно неинтуитивным .. (edit: спасибо за дополнительную информацию, теперь имеет больше смысла :)) –

2

Вариант второй - единственный, который имеет смысл, если вы не знаете, что вы всегда будете обрабатывать записи последовательно!

+0

Я знаю, что я всегда буду обрабатывать их по порядку. – artsince

+0

он использует 'order by' на ключе ID, поэтому он всегда находится в последовательности. –

+0

@Gaby, я это понимаю, но нет ничего, говоря, что не могли быть необработанные записи с идентификатором ниже, чем у «последний обработанный идентификатор». Это оставило бы вам дыры в ваших данных, которые никогда не могут быть заполнены на основе логики первого запроса. – ninesided

3

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

0

Вы можете использовать

Select Min(Id) as 'Id' 
From dbo.myTable 
Where Flagged='F' 

Предполагая, что Помечено = 'F' означает, что он не попадает.

+0

.. но он просит '*' не только идентификатор. –

+0

Ах да, конечно. Хотя я не уверен, почему в этом случае вы бы *. – codingbadger

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