Спустя 12 минут, 45 секунд (31.08.2012 - 18:20) Игорь_Vasinsky написал(а):
это довольно сложный алгоритм, во первых нельзя использовать auto_increment, если тока для идентификации не использоать доп поле, а это абсурт т.к. есть автоинкремент, и нужно делать выборку всей таблицы от начала до конца и исекать разницу между следующими друг за другами идентификаторами, которые отличаются на больше чем +1, т.е. следующий должен быть равен - предидущий + 1
Спустя 7 минут, 47 секунд (31.08.2012 - 18:27) olegod написал(а):
На этом значении и нет auto_increment, проходить всю таблицу единственный вариант? mysql ничего на этот случай не предусматривает?
Спустя 5 минут, 9 секунд (31.08.2012 - 18:33) Игорь_Vasinsky написал(а):
ну выборка это не самый страшный момент в этом деле, у парней есть БД с полтора лимона записей и сложными запросами, тут будет работать алгоритм на php
как вариант - писать в отдельную таблицу все удалённые id, с сортировкой по возрастанию
потом провсто делать запрос, брать первый удалённый id из этой таблицы и создавать с ним запись в действующей, после успешного создания очищать.
вообщем это наверно и есть самый оптимальный вариант
как вариант - писать в отдельную таблицу все удалённые id, с сортировкой по возрастанию
потом провсто делать запрос, брать первый удалённый id из этой таблицы и создавать с ним запись в действующей, после успешного создания очищать.
вообщем это наверно и есть самый оптимальный вариант
Спустя 1 час, 2 минуты, 46 секунд (31.08.2012 - 19:35) olegod написал(а):
Хм... А как бы выглядел оптимальный проход всей таблицы с поиском пропущенного значения?
Спустя 3 минуты, 27 секунд (31.08.2012 - 19:39) Игорь_Vasinsky написал(а):
ты не понял. обходить таблицу для поиска пропущенного id - не надо.
будет доп таблица - в которую заносятся все id при удалении
вот её и нужно проверять - и выбирать первое свободное
если эта таблица пуста - тогда делать запрос в действующую с LIMIT = 1 ORDER BY `id` DESC - отсюда ты получишь последний id - а значит след. id = id+1
но тока если доп таблица пуста.
я не знаю как ещё расжевать.
будет доп таблица - в которую заносятся все id при удалении
вот её и нужно проверять - и выбирать первое свободное
если эта таблица пуста - тогда делать запрос в действующую с LIMIT = 1 ORDER BY `id` DESC - отсюда ты получишь последний id - а значит след. id = id+1
но тока если доп таблица пуста.
я не знаю как ещё расжевать.
Спустя 28 минут (31.08.2012 - 20:07) olegod написал(а):
Я Вас понял, просто такой подход не подходит... Дело в том что это значение иногда вводится вручную, т.е. последнее было 1890, а введённое 8000 - тогда огромное кол-во значений между ними будет пропущено, видимо проход всей таблицы - единственный способ
Спустя 15 минут (31.08.2012 - 20:22) Игорь_Vasinsky написал(а):
это не правильный подход. значит нужен идентификатор автоинкремент и ориентироваться на него.
Спустя 3 минуты, 16 секунд (31.08.2012 - 20:25) olegod написал(а):
Такой есть, есть отдельный столбец с id, где нормальный автоинкремент... Только что это даёт, я Вас не совсем понял
Спустя 8 минут, 9 секунд (31.08.2012 - 20:33) Игорь_Vasinsky написал(а):
значит
Цитата |
и нужно делать выборку всей таблицы от начала до конца и исекать разницу между следующими друг за другами идентификаторами, которые отличаются на больше чем +1 |
но это через ж...
у меня есть фраза:
Цитата |
чтобы не кусать себя за локти во время разработки - надо думать головой во время проектирования (С) |
Спустя 9 минут, 3 секунды (31.08.2012 - 20:42) olegod написал(а):
Ну а решений нет других... Вот даже в одной ПУ игровыми серверами нашёл такую функцию:
И ничего, работает)
private function bestPort($server){
$query = mysql_query("SELECT `port` FROM `games` WHERE `server`=".$server." ORDER BY `port`");
$last = 27019;
while($one = mysql_fetch_assoc($query)){
if(($one["port"] - $last) > 1)break;
elseif($one["port"] > $last) $last = $one["port"];
}
return $last + 1;
}
И ничего, работает)
Спустя 14 минут, 32 секунды (31.08.2012 - 20:57) sergeiss написал(а):
olegod - тебе правильно говорят - надо изначально правильно спректировать БД, чтобы потом не кусать локти (с) Игорь_Vasinsky 
"Твой" вопрос уже неоднократно поднимался на форуме. И каждый раз приходили к тому, что надо просто использовать автокремент и не парить мозХ.

"Твой" вопрос уже неоднократно поднимался на форуме. И каждый раз приходили к тому, что надо просто использовать автокремент и не парить мозХ.
Спустя 21 минута, 20 секунд (31.08.2012 - 21:18) Игорь_Vasinsky написал(а):

Спустя 5 часов, 41 минута, 26 секунд (2.09.2012 - 03:00) Alchemist написал(а):
Вообще, люди конечно правы, и такой задачи не должно возникать в принципе, но если принять её как теоретическое упражнение, то вот вариант:
запрос проходит по таблице и для каждого значения поля ищет следущее по порядку. Как только не находит - останавливается и возвращает пропущеное значение.
Два условия чтобы запрос работал вменяемое время (<0.01 сек для 5к таблицы):
1) поле с числовыми значениями обязано быть индексом. (в идеале - уникальным)
2) ON условие должно быть записано именно так, как написал я (b = a + 1) и ни в коем случае не наоборот (a = b - 1)
Также, поскольку запрос ищет "следущее" значение относительно имеющегося, то проверка начинается с минимального значения в поле. Другими словами, если не будет строки с field = 1, запрос этого не увидит.
SELECT a.field + 1 AS `empty` FROM `table` AS `a` LEFT JOIN `table` AS `b` ON (b.field = a.field + 1) WHERE b.field IS NULL ORDER BY a.field LIMIT 1
запрос проходит по таблице и для каждого значения поля ищет следущее по порядку. Как только не находит - останавливается и возвращает пропущеное значение.
Два условия чтобы запрос работал вменяемое время (<0.01 сек для 5к таблицы):
1) поле с числовыми значениями обязано быть индексом. (в идеале - уникальным)
2) ON условие должно быть записано именно так, как написал я (b = a + 1) и ни в коем случае не наоборот (a = b - 1)
Также, поскольку запрос ищет "следущее" значение относительно имеющегося, то проверка начинается с минимального значения в поле. Другими словами, если не будет строки с field = 1, запрос этого не увидит.
Спустя 7 часов, 1 минута, 48 секунд (2.09.2012 - 10:01) 123456 написал(а):
1) Берем 1
2) проверяем или есть в БД
3) есть - продолжаем. Нет - Записываем
4) прибавляем +1
5) проверяем или есть в БД id+1
6) есть - повторяем алгоритм с пункта 4. Нет - Записываем
2) проверяем или есть в БД
3) есть - продолжаем. Нет - Записываем
4) прибавляем +1
5) проверяем или есть в БД id+1
6) есть - повторяем алгоритм с пункта 4. Нет - Записываем
Спустя 41 минута, 12 секунд (2.09.2012 - 10:43) Michael написал(а):
Цитата (123456 @ 2.09.2012 - 10:01) |
1) Берем 1 2) проверяем или есть в БД 3) есть - продолжаем. Нет - Записываем 4) прибавляем +1 5) проверяем или есть в БД id+1 6) есть - повторяем алгоритм с пункта 4. Нет - Записываем |
т.е. ты предлагаешь множественные запросы в цикле слать?
Alchemist, вот этот твой последний вариант - вполне рабочее решение такой задачи. А на значение 1 можно сперва и проверить.
Спустя 4 часа, 5 минут, 10 секунд (2.09.2012 - 14:48) sergeiss написал(а):
Цитата (123456 @ 2.09.2012 - 12:01) |
1) Берем 1 2) проверяем или есть в БД 3) есть - продолжаем. Нет - Записываем 4) прибавляем +1 5) проверяем или есть в БД id+1 6) есть - повторяем алгоритм с пункта 4. Нет - Записываем |
А если в таблице хотя бы 100К записей? Ты представляешь время работы твоего алгоритма?
Если уж очень хочется находить пропущенные (по причине удаления) значения, то решение есть. Но - только для удаленных величин!!! Надо просто записывать их в отдельную таблицу и выбирать оттуда первое попавшееся. И учти, что у тебя все равно ВСЕГДА будут пропуски при твоем алгоритме работы

Но еще раз повторю, что на самом деле
Цитата (sergeiss @ 31.08.2012 - 22:57) |
каждый раз приходили к тому, что надо просто использовать автокремент и не парить мозХ. |