Этот баннер — требование Роскомнадзора для исполнения 152 ФЗ.
«На сайте осуществляется обработка файлов cookie, необходимых для работы сайта, а также для анализа использования сайта и улучшения предоставляемых сервисов с использованием метрической программы Яндекс.Метрика. Продолжая использовать сайт, вы даёте согласие с использованием данных технологий».
Политика конфиденциальности
|
|
|
Бинарный поиск в С
|
|||
|---|---|---|---|
|
#18+
Я хочу сделать бинарный поиск в сортированном массиве. Без рекурсии. Код: plaintext 1. 2. 3. 4. 5. 6. 7. 8. 9. 10. 11. 12. 13. 14. 15. 16. 17. 18. 19. 20. 21. 22. Если искомый элемент (key) есть в массиве (arr) то все нормально, функция возвращает индекс массива. Но если элемента нет в массиве я кручусь все время в цикле (while (!done)). Я что то никак не соображу по какому условию выйти из цикла. ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 23.10.2017, 10:00 |
|
||
|
Бинарный поиск в С
|
|||
|---|---|---|---|
|
#18+
Надо сжимать интервал, если он сжался, а ничего не нашлось, тогда ой. шпаргалка под спойлером, лучше не подглядывать, без крайней нужды. а додумать. потому что все несложно. Главное не забыть менять done - а то же там константа, поэтому цикл будет вращаться до конца света. Код: plaintext 1. 2. 3. 4. 5. 6. 7. 8. 9. 10. 11. 12. 13. 14. 15. 16. 17. 18. 19. 20. 21. 22. 23. 24. 25. 26. 27. 28. 29. 30. 31. 32. 33. 34. 35. 36. 37. 38. 39. 40. 41. 42. ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 23.10.2017, 10:26 |
|
||
|
Бинарный поиск в С
|
|||
|---|---|---|---|
|
#18+
По условию done = y, где у != 0 например внутри цикла ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 23.10.2017, 10:27 |
|
||
|
Бинарный поиск в С
|
|||
|---|---|---|---|
|
#18+
Vladimir BaskakovНадо сжимать интервал, если он сжался, а ничего не нашлось, тогда ой. шпаргалка под спойлером, лучше не подглядывать, без крайней нужды. а додумать. потому что все несложно. Главное не забыть менять done - а то же там константа, поэтому цикл будет вращаться до конца света. большое спасибо. работает. но у меня тут еще одна проблема. я хочу вставлять элемент если он не найден. то есть я хочу вернуть не -1 а индекс на место которого я хочу вставить элемент. соответсвенно все элементы перед ним я сдвину вправо. как мне модифицировать функцию? я думал ввести условие Код: plaintext 1. но что то в нем не так. ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 23.10.2017, 10:39 |
|
||
|
Бинарный поиск в С
|
|||
|---|---|---|---|
|
#18+
а проблема в том что это недостаточное условие. нужен какой то флаг - элемент не найден. но тогда получается нужно делать еще один пробег? ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 23.10.2017, 10:48 |
|
||
|
Бинарный поиск в С
|
|||
|---|---|---|---|
|
#18+
jenya7, пробег делать не надо, достаточно ещё одного сравнения. Вот из Вики: Код: plaintext 1. 2. 3. 4. 5. 6. 7. 8. 9. 10. 11. 12. 13. 14. 15. 16. 17. 18. 19. 20. 21. 22. ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 23.10.2017, 11:07 |
|
||
|
Бинарный поиск в С
|
|||
|---|---|---|---|
|
#18+
jenya7, а done чем не флаг? в integer разных значений как грязи весной ... ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 23.10.2017, 11:10 |
|
||
|
Бинарный поиск в С
|
|||
|---|---|---|---|
|
#18+
MBojenya7, пробег делать не надо, достаточно ещё одного сравнения. Вот из Вики: Код: plaintext 1. 2. 3. 4. 5. 6. 7. 8. 9. 10. 11. 12. 13. 14. 15. 16. 17. 18. 19. 20. 21. 22. а FOUND это что? дефайн? ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 23.10.2017, 11:24 |
|
||
|
Бинарный поиск в С
|
|||
|---|---|---|---|
|
#18+
а FOUND это что? дефайн? Да, там возвращается структура из двух членов - индекс и boolean признак. Достаточно нелепо. Варианты: - изменить прототип, индекс сделать аргументом, а результат - boolean - возвращать положительный индекс при наличии, отрицательный при отсутствии. - при использовании исключительно для поиска места для вставки - оставить обычный интерфейс ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 23.10.2017, 11:36 |
|
||
|
Бинарный поиск в С
|
|||
|---|---|---|---|
|
#18+
а где изменяется n? ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 23.10.2017, 11:37 |
|
||
|
Бинарный поиск в С
|
|||
|---|---|---|---|
|
#18+
не хватает условия. я могу вывести флаг аргументом наружу int BinarySearch(int a[], int first, int last, int key, int *found) но нужно еще одно условие ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 23.10.2017, 11:45 |
|
||
|
Бинарный поиск в С
|
|||
|---|---|---|---|
|
#18+
jenya7, это длина массива, она, в общем-то, не нужна и закомментарена. Код https://ru.wikipedia.org/wiki/Двоичный_поиск ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 23.10.2017, 11:46 |
|
||
|
Бинарный поиск в С
|
|||
|---|---|---|---|
|
#18+
jenya7, какое ещё условие нужно? ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 23.10.2017, 11:47 |
|
||
|
Бинарный поиск в С
|
|||
|---|---|---|---|
|
#18+
MBojenya7, какое ещё условие нужно? спасибо. сделал так Код: plaintext 1. 2. 3. 4. 5. 6. 7. 8. 9. 10. 11. 12. 13. 14. 15. 16. 17. 18. 19. 20. 21. 22. 23. 24. 25. 26. 27. 28. 29. 30. 31. 32. 33. 34. 35. 36. 37. 38. 39. 40. 41. 42. 43. похоже что работает. ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 23.10.2017, 12:37 |
|
||
|
Бинарный поиск в С
|
|||
|---|---|---|---|
|
#18+
jenya7спасибо. сделал так Код: plaintext 1. Я так понимаю found это найдено/не найдено. Обычно наоборот делают, функция возвращает ошибку, а переменная под результат в параметрах, т.е. Код: plaintext 1. ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 23.10.2017, 12:53 |
|
||
|
Бинарный поиск в С
|
|||
|---|---|---|---|
|
#18+
Dima Tjenya7спасибо. сделал так Код: plaintext 1. Я так понимаю found это найдено/не найдено. Обычно наоборот делают, функция возвращает ошибку, а переменная под результат в параметрах, т.е. Код: plaintext 1. понял. спасибо. переделаю. ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 23.10.2017, 12:57 |
|
||
|
Бинарный поиск в С
|
|||
|---|---|---|---|
|
#18+
Siemargl http://www.cplusplus.com/reference/cstdlib/bsearch/ и не надо изобретать инетересно но сложно. вопрос что будет compar в моем случае? ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 23.10.2017, 13:03 |
|
||
|
Бинарный поиск в С
|
|||
|---|---|---|---|
|
#18+
jenya7Siemargl http://www.cplusplus.com/reference/cstdlib/bsearch/ и не надо изобретать инетересно но сложно. вопрос что будет compar в моем случае? Там есть пример кода с твоим случаем, т.е. массивом int. ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 23.10.2017, 13:06 |
|
||
|
Бинарный поиск в С
|
|||
|---|---|---|---|
|
#18+
Dima Tjenya7пропущено... инетересно но сложно. вопрос что будет compar в моем случае? Там есть пример кода с твоим случаем, т.е. массивом int. а где тут поиск середины? Код: plaintext 1. 2. 3. 4. ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 23.10.2017, 13:17 |
|
||
|
Бинарный поиск в С
|
|||
|---|---|---|---|
|
#18+
jenya7Dima Tпропущено... Там есть пример кода с твоим случаем, т.е. массивом int. а где тут поиск середины? Код: plaintext 1. 2. 3. 4. Тут нет поиска середины, т.к. это компаратор, т.е. функция сравнения двух элементов массива. Сам алгоритм поиска внутри bsearch(), в которую передаются исходные данные, включая компаратор. ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 23.10.2017, 13:22 |
|
||
|
Бинарный поиск в С
|
|||
|---|---|---|---|
|
#18+
Dima Tэто компаратор, т.е. функция сравнения двух элементов массива Неправильно выразился, это функция сравнения значений по двум указателям. ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 23.10.2017, 13:26 |
|
||
|
Бинарный поиск в С
|
|||
|---|---|---|---|
|
#18+
Dima Tjenya7пропущено... а где тут поиск середины? Код: plaintext 1. 2. 3. 4. Тут нет поиска середины, т.к. это компаратор, т.е. функция сравнения двух элементов массива. Сам алгоритм поиска внутри bsearch(), в которую передаются исходные данные, включая компаратор. а нам нужна эта функция для бинарного поиска? мне кажется я могу передать нулевой указатель в качестве аргумента. все аргументы для поиска присутствуют в bsearch а компаратор как мне кажется лишний элемент. ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 23.10.2017, 13:36 |
|
||
|
Бинарный поиск в С
|
|||
|---|---|---|---|
|
#18+
jenya7Dima Tпропущено... Тут нет поиска середины, т.к. это компаратор, т.е. функция сравнения двух элементов массива. Сам алгоритм поиска внутри bsearch(), в которую передаются исходные данные, включая компаратор. а нам нужна эта функция для бинарного поиска? мне кажется я могу передать нулевой указатель в качестве аргумента. все аргументы для поиска присутствуют в bsearch а компаратор как мне кажется лишний элемент. bsearch() универсальная функция для любых типов, на входе у нее void*. Компаратор нужен для того чтобы правильно сравнить два void* ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 23.10.2017, 13:54 |
|
||
|
Бинарный поиск в С
|
|||
|---|---|---|---|
|
#18+
Dima Tjenya7пропущено... а нам нужна эта функция для бинарного поиска? мне кажется я могу передать нулевой указатель в качестве аргумента. все аргументы для поиска присутствуют в bsearch а компаратор как мне кажется лишний элемент. bsearch() универсальная функция для любых типов, на входе у нее void*. Компаратор нужен для того чтобы правильно сравнить два void* понял. спасибо. попробую. ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 23.10.2017, 14:23 |
|
||
|
Бинарный поиск в С
|
|||
|---|---|---|---|
|
#18+
jenya7MBojenya7, какое ещё условие нужно? спасибо. сделал так Код: plaintext 1. 2. 3. 4. 5. 6. 7. 8. 9. 10. 11. 12. 13. 14. 15. 16. 17. 18. 19. 20. 21. 22. 23. 24. 25. 26. 27. 28. 29. 30. 31. 32. 33. 34. 35. 36. 37. 38. 39. 40. 41. 42. 43. похоже что работает. .................................... а я бы возвращал положительное число, индекс+1 если найдено, а если не найдено - отрицательный индекс вставки - и параметр found тогда не нужен. А чего изобретаете то? или так, язык поучить? ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 24.10.2017, 11:30 |
|
||
|
Бинарный поиск в С
|
|||
|---|---|---|---|
|
#18+
плохо сказал. можно задачу ф-ции переформулировать так - найти индекс первого элемента, который больше или равен ключу. Тогда вызывающая сторона сможет посмотреть - если ей вернули -1 - вставлять в конец, если ноль и больше - посмотреть что лежит на этом месте - ключ - значит нашлось, не ключ - тогда это место вставки. параметр found точно не нужен. ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 24.10.2017, 11:40 |
|
||
|
Бинарный поиск в С
|
|||
|---|---|---|---|
|
#18+
[quot Vladimir Baskakov]jenya7пропущено... .................................... а я бы возвращал положительное число, индекс+1 если найдено, а если не найдено - отрицательный индекс вставки - и параметр found тогда не нужен. А чего изобретаете то? или так, язык поучить? Задача такая. Есть массив пакетов приходящих по TCP, в принципе не важно откуда они приходят. Я должен хранить эти пакеты, для этого я создал массив пакетов. Глубина хранения пока 512 хотя может вырасти до пару тысяч, это еще TBD. То есть размер массива пока 512. В приходящем пакете есть ИД и команда - добавить пакет, удалить пакет, редактировать пакет. Доступ к пакету должен быть максимально быстрым. Находить ИД пакета простым перебором в for долго. Поэтому решил находить бинарным поиском и если ИД не найден вставлять его на его место, чтоб массив всегда был сортирован по ИД. ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 24.10.2017, 13:47 |
|
||
|
Бинарный поиск в С
|
|||
|---|---|---|---|
|
#18+
пока что сделал так. Код: plaintext 1. 2. 3. 4. 5. 6. 7. 8. 9. 10. 11. 12. 13. 14. 15. 16. 17. 18. 19. 20. 21. 22. 23. 24. 25. 26. 27. 28. 29. 30. 31. 32. 33. 34. 35. 36. 37. 38. 39. 40. 41. 42. 43. 44. 45. 46. 47. 48. 49. 50. 51. 52. 53. 54. 55. 56. 57. 58. 59. 60. 61. 62. 63. 64. 65. 66. 67. 68. 69. 70. 71. 72. 73. 74. 75. 76. 77. 78. 79. 80. 81. 82. 83. 84. 85. 86. 87. 88. 89. 90. 91. 92. 93. 94. 95. 96. 97. 98. 99. 100. 101. 102. 103. 104. ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 24.10.2017, 13:53 |
|
||
|
Бинарный поиск в С
|
|||
|---|---|---|---|
|
#18+
тестирую так Код: plaintext 1. 2. 3. 4. 5. 6. 7. 8. 9. 10. 11. 12. 13. 14. 15. 16. 17. 18. 19. 20. 21. 22. 23. пока вроде вставка и удаление проходят нормально. ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 24.10.2017, 13:57 |
|
||
|
Бинарный поиск в С
|
|||
|---|---|---|---|
|
#18+
Задача такая. Есть массив пакетов приходящих по TCP, в принципе не важно откуда они приходят. Я должен хранить эти пакеты, для этого я создал массив пакетов. Глубина хранения пока 512 хотя может вырасти до пару тысяч, это еще TBD. То есть размер массива пока 512. В приходящем пакете есть ИД и команда - добавить пакет, удалить пакет, редактировать пакет. Доступ к пакету должен быть максимально быстрым. Находить ИД пакета простым перебором в for долго. Поэтому решил находить бинарным поиском и если ИД не найден вставлять его на его место, чтоб массив всегда был сортирован по ИД. чисто теоретически, https://habrahabr.ru/post/65617/ https://ru.wikipedia.org/wiki/B-дерево есть разные упорядоченные структуры данных для хранения сортированных данных - всякие бинарные и сбалансированные деревья. может быть среди них поискать. или - хэш-таблицы. чтобы по целому вычислять ключик, где искать - в каком сегменте, и там уже перебором или бинарным поиском. Мне думается, что хэширование - поможет. допустим, если храним 2000 значений - захешировали на сотню, и вот уже в каждом массивчике перебираемых 20 единиц (в среднем) - и вставлять быстро и искать нормально. А перерасход памяти для такого количества значений - мизернейший. ============================ всего доброго. PS а почему си, а не с++ с огромным массивом оптимизированных уже библиотек? ну дело хозяйское, в целом. ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 24.10.2017, 14:43 |
|
||
|
Бинарный поиск в С
|
|||
|---|---|---|---|
|
#18+
Vladimir BaskakovЗадача такая. Есть массив пакетов приходящих по TCP, в принципе не важно откуда они приходят. Я должен хранить эти пакеты, для этого я создал массив пакетов. Глубина хранения пока 512 хотя может вырасти до пару тысяч, это еще TBD. То есть размер массива пока 512. В приходящем пакете есть ИД и команда - добавить пакет, удалить пакет, редактировать пакет. Доступ к пакету должен быть максимально быстрым. Находить ИД пакета простым перебором в for долго. Поэтому решил находить бинарным поиском и если ИД не найден вставлять его на его место, чтоб массив всегда был сортирован по ИД. чисто теоретически, https://habrahabr.ru/post/65617/ https://ru.wikipedia.org/wiki/B-дерево есть разные упорядоченные структуры данных для хранения сортированных данных - всякие бинарные и сбалансированные деревья. может быть среди них поискать. или - хэш-таблицы. чтобы по целому вычислять ключик, где искать - в каком сегменте, и там уже перебором или бинарным поиском. Мне думается, что хэширование - поможет. допустим, если храним 2000 значений - захешировали на сотню, и вот уже в каждом массивчике перебираемых 20 единиц (в среднем) - и вставлять быстро и искать нормально. А перерасход памяти для такого количества значений - мизернейший. ============================ всего доброго. PS а почему си, а не с++ с огромным массивом оптимизированных уже библиотек? ну дело хозяйское, в целом. я думал про хэш. но пока остановились на бинарном поиске. ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 24.10.2017, 17:30 |
|
||
|
Бинарный поиск в С
|
|||
|---|---|---|---|
|
#18+
а почему? может быть на макете сверить производительность? от целого хэш-функция на 10 000 значений посчитается практически влет, и скорее всего в каждом из этих 10000 массивов будет сидеть ну три, ну пять ключей. если всего значений 2000. Хэширование даст заметно - лучшее масштабирование при увеличении кол-ва эл-тов, сокращая расходы на вставку - меньше памяти надо двигать. ну конечно по ситуации - если код для микроконтроллера - это одно, а если для машинки с кучей памяти под современной осью - совсем другое. но, не настаиваю. кому как удобнее. ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 24.10.2017, 17:45 |
|
||
|
Бинарный поиск в С
|
|||
|---|---|---|---|
|
#18+
Vladimir Baskakovа почему? может быть на макете сверить производительность? от целого хэш-функция на 10 000 значений посчитается практически влет, и скорее всего в каждом из этих 10000 массивов будет сидеть ну три, ну пять ключей. если всего значений 2000. Хэширование даст заметно - лучшее масштабирование при увеличении кол-ва эл-тов, сокращая расходы на вставку - меньше памяти надо двигать. ну конечно по ситуации - если код для микроконтроллера - это одно, а если для машинки с кучей памяти под современной осью - совсем другое. но, не настаиваю. кому как удобнее. я представил две опции. но народ выбрал бинарный поиск. я не стал спорить. если будем терять пакеты попробуем хэш. есть еще красно-черное дерево которое, как говорят, на больших массивах дает хорошие результаты. ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 24.10.2017, 17:49 |
|
||
|
Бинарный поиск в С
|
|||
|---|---|---|---|
|
#18+
что еще по ходу подумалось (я уже давным-давно не сишник, по старой памяти) char * strchr( const char * string, int symbol); вроде бы эффективно задействует возможности процессора для поиска в области памяти. вроде бы scas http://programm.ws/page.php?id=129 может быть не сортировать, а искать на уровне байт? найти первый байт искомого числа. проверить совпадение следующих. мне кажется тут есть о чем подумать, если уж надо очень, очень быстро искать в сравнительно-небольших массивах, до 10-20 килобайт вплоть до того, что весь массив в котором ищем держать в строковом виде 16-ричных чисел и искать там строковыми, высокооптимизированными ф-циями, которые были и есть в составе стандартной б-ки Си. то есть, вариантов на попробовать, даже в самом простом случае, море. Попробуйте, шутки ради, вдруг да выйдет.... ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 24.10.2017, 18:11 |
|
||
|
Бинарный поиск в С
|
|||
|---|---|---|---|
|
#18+
jenya7я думал про хэш. но пока остановились на бинарном поиске. Тут выбор между быстро искать и и быстро вставлять/удалять. Бинарный поиск ищет достаточно быстро, не факт что хэштаблица будет искать быстрее при нескольких тысячах элементов. Но вставка/удаление требует сдвига существенной части массива, что не быстро. Если вставок/удалений относительно немного, то твой способ будет нормально работать. Надо просто затестить с нагрузкой похожей на реальную. Если производительность устроит, то можешь оставить как есть. ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 24.10.2017, 18:13 |
|
||
|
Бинарный поиск в С
|
|||
|---|---|---|---|
|
#18+
jenya7я представил две опции. но народ выбрал бинарный поиск. я не стал спорить. если будем терять пакеты попробуем хэш. есть еще красно-черное дерево которое, как говорят, на больших массивах дает хорошие результаты. а время то меряли? профилировали? может и не пробежка по несортированному массиву его занимает? а какая-то предобработка, принятие пакетов, или постобработка? ну, я против народа то не пойду.... народ сказал, значит так надо. ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 24.10.2017, 18:16 |
|
||
|
Бинарный поиск в С
|
|||
|---|---|---|---|
|
#18+
Dima Tjenya7я думал про хэш. но пока остановились на бинарном поиске. Тут выбор между быстро искать и и быстро вставлять/удалять. Бинарный поиск ищет достаточно быстро, не факт что хэштаблица будет искать быстрее при нескольких тысячах элементов. Но вставка/удаление требует сдвига существенной части массива, что не быстро. Если вставок/удалений относительно немного, то твой способ будет нормально работать. Надо просто затестить с нагрузкой похожей на реальную. Если производительность устроит, то можешь оставить как есть. вот и я к тому, что надо понять где затыки сейчас, и где они могут быть, а уж потом выбор выбирать. (шутка) надеюсь, это курсовичок, а не атомный ледокол с горячей заменой кода на проде. когда бесконечный цикл не даст опустить графитовый стерженек....( конец шутки) ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 24.10.2017, 18:21 |
|
||
|
|

start [/forum/topic.php?all=1&fid=16&tid=1340253]: |
0ms |
get settings: |
9ms |
get forum list: |
13ms |
check forum access: |
3ms |
check topic access: |
3ms |
track hit: |
178ms |
get topic data: |
10ms |
get forum data: |
3ms |
get page messages: |
65ms |
get tp. blocked users: |
1ms |
| others: | 287ms |
| total: | 572ms |

| 0 / 0 |
