Есть вопрос, который меня интересовал целую вечность, и я надеялся, что кто-то может дать мне ответ, чтобы успокоить мой разум.
Давайте предположим, что у меня есть входной поток (например, файл / сокет / канал) и я хочу проанализировать входящие данные. Давайте предположим, что каждый блок входящих данных разделен новой строкой, как большинство распространенных интернет-протоколов. Это приложение также может выполнять синтаксический анализ html, xml или любой другой интеллектуальной структуры данных. Дело в том, что данные делятся на логические блоки с помощью разделителя, а не фиксированной длины. Как я могу буферизовать данные для ожидания появления разделителя?
Ответ кажется достаточно простым: достаточно большого массива байтов / символов, чтобы вместить все это.
Но что, если разделитель появится после заполнения буфера? На самом деле это вопрос о том, как разместить динамический блок данных в блоке фиксированного размера. Я действительно могу думать только о нескольких альтернативах:
При необходимости увеличьте размер буфера. Это может потребовать значительного перераспределения памяти и может привести к исчерпанию ресурсов из специально созданных потоков (или, возможно, даже к отказу в обслуживании в случае сокетов, где мы хотим защитить себя от атак исчерпания и разрыва соединений, которые пытаются исчерпать ресурсы ... и злоумышленник начинает посылать поддельные, негабаритные пакеты для срабатывания защиты).
Начните перезаписывать старые данные, используя кольцевой буфер. Возможно, не идеальный метод, так как логический блок станет неполным.
Дамп новых данных, когда буфер заполнен. Однако в этом случае разделитель никогда не будет найден, поэтому этот выбор, очевидно, не является хорошим вариантом.
Просто сделайте чертовски большой буфер фиксированного размера и предположите, что все входящие логические блоки данных находятся в пределах его границ ... и, если он когда-либо заполнится, просто интерпретируйте полный буфер как логический блок ...
В любом случае я считаю, что мы должны предположить, что логические блоки никогда не превысят определенного размера ...
Есть мысли на эту тему? Очевидно, что должен быть способ, так как языки более высокого уровня предлагают какие-то механизмы буферизации с их readLine()
потоковыми методами.
Есть ли "лучший способ" решить это или всегда есть компромисс? Я действительно ценю все мысли и идеи по этой теме, так как этот вопрос преследует меня каждый раз, когда мне нужно написать какой-то парсер.