Нэш Трей - C# 2010. Ускоренный курс для профессионалов (2010) (1160865), страница 63
Текст из файла (страница 63)
я С г1пд, вызывайте метод Яег яс гаод на применяемом кодировщике. Используемый кодировщик должен соответствовать источнику кодируемых данных. Это приводит к важному замечанию, которое всегда надо иметь в виду. При передаче строки в другие системы и обратно в низкоуровневом байтовом формате необходимо знать используемую протоколом схему кодирования.
Очень важно, что для преобразования байтового массива в яузсеп. ясгапд всегда должен применяться соответствующий кодировке объект епсос 1пд, даже если известно, что в протоколе используется точно такая же кодировка, как и внутри я уз Сею. яг г1пд на платформе, на которой строится приложение. Почему? Предположим, что приложение разрабатывается на платформе 1п1е!, где протокол кодирования предполагает, что в паре байт символа первым идет младший, при этом известно, что такой же порядок принят на целевой платформе, Вы решаете сэкономить, и отказываетесь от применения объекта Яузтегя.
техг. Епссо1пд. Яп1согге для преобразования байтов строки. Позднее вы запускаете приложение на платформе, которая внутри использует порядок байтов со старшим байтом первым. Приложение начнет сбоить из-за того. что было выдвинуто ошибочное предположение относитель- 238 Глаза Я но внутренней реализации кодирования Яувтеш. Бтг1пи. Постоянное использование кодировщина не повлияет на эффективность, потому что на платформе, где внутреннее кодирование совпадает с внешним, лишние преобразования не выполняются.
В предыдущем примере для вывода массива байтов на консоль применялся класс БТТ1пдВи11сГег. Давайте посмотрим, что он собой представляет. 81г~пдВихЫег Поскольку объекты Бу я Теш. ЯТ г1пд являются неизменяемыми, иногда они становятся узким местом для эффективности, например, при сборе строки "на лету". Для построения составной строки можно воспользоваться операцией т, как показано ниже: встанем арапе = " "; ятггпд сошроипо = "Голосуйте" + врасе е "эа" + врасе + "тишину"; Однако такой подход неэффективен, поскольку код для выполнения своей работы создает множество строк.
Создание таких промежуточных строк может увеличить нагрузку на память. Хотя эта строка кода несколько искусственна, совсем несложно представить, как пострадает эффективность сложной системы, в которой производится масса манипуляций строками, от интенсивного использования памяти. Рассмотрим случай реализации пользовательского кодировщика Ьаве64.
который последовательно добавляет символы в процессе обработки двоичного файла. Библиотека .йГЕТ уже предоставляет эту функциональность в классе Яуягеш. Сопуегг, нО давайте пока ее проигнорируем. Если многократно в цикле использовать операцию + для создания огромной строки Ьаэе64, производительность очень быстро деградирует по мере увеличения размера исходных данных. В такой ситуации можно прибегнуть к классу Бувтеш. Техс. Ятг1пдви11сгег, который реализует изменяемую строку специально для эффективного построения составных строк.
Детальное описание методов Бтг1псгВи11сгег здесь приводиться не будет, поскольку при желании его можно найти в документации МБРГт', однако будет раскрыт ряд моментов, о которых обычно умалчивается. Внутри Бтг1пдВи11сгег поддерживает массив символов. которым управляет динамически. Основными рабочими методами этого класса являются АррепсГ, 1пвегТ и АррепсГрогшас. По описанию этих методов в МЗРХ видно, что они имеют богатый набор перегрузок для поддержки добавления и вставки строк многих распространенных типов.
Для создания экземпляра ЯТТ1пдви11сгег на выбор доступны разнообразные консгрунторы. Конструктор по умолчанию создает новый экземпляр ЯТТ1идВи11сГег с определяемой системой емкостью по умолчанию. Однако эта емкость не ограничивает максимального размера создаваемой строки. Вместо этого она представляет объем строковых данных, которые объект Бтгагнуви11сгег может хранить перед тем, нак ему понадобится увеличить размер внутреннего буфера, а с ним и допустимую емкость. При наличии приблизительного представления о размере строящейся строки можно передать этот размер объекту я Т ггпоВи11сГег в виде параметра одного из нонструкторов, и тогда он инициализирует свой буфер соответствующим образом.
Это может помочь экземпляру Ятг1пдви11бег избежать необходимости в слишком частом повторном размещении буфера в памяти по мере его заполнения. Кроме того, одна из перегрузок конструктора допускает определение свойства максимальной емкости. По умолчанию максимальная емкость равна Був сепг. 1пт32. Мехиа1ие, что в настоящее время составляет 2 147 483 647 байтов. но точное значение может измениться в процессе развития системы. Если необходимо предохранить буфер ЯТг1поВи11бег от роста свыше некоторой величины, в одной из перегрузок конструктора можно предоставить альтернативную максимальную емкость. Если операция Работа со строками 239 вставки или добавления потребует увеличения буфера сверх указанного предела, будет сгенерировано исключение АгдиятепГОпГОТВапдеЕхсерг1оп.
Для удобства все методы, которые добавляют и вставляют данные в экземпляр Бсг1пдвп11с(ег, возвращают ссылку на ЬЬ1я. Поэтому операции одного и того же построителя строк можно связывать в цепочки, как показано ниже: оя1по Яувсев) оягпо Буягея.Техтт роЬ11с с1явя Епсгурогпг ( ясаггс чо1б Мягп () ( ЯсггпдВо11бег вЬ = пен Бгг1поэи11бег () яЬ.Аррепс(("Ягг1пдвп11бег ").Аррепк(("является ") .Аррепб("очень... ЯСГТПБ ЬО11С1 = ВЬ.ТОБСГ1ПО() яЬ.Арретн(("улобныы")) ягг1по Ьп11С2 = яЬ.Тоясггпч() Оопво1е.нггке11пе( Ьо11Г1 )т Оопяо1е.иг1ге11пе( Ьс11С2 )т В приведенном примере с помощью вызова яЬ. Тоагг1пд экзеькпляр Бгг1пдвп11бег по имени вЬ преобразуется в новый экземпляр Бувгеят.
Ягг1пд по имени Ьп11г1. Для достижения максимальной эффективности Ягг1поВп11бег просто передает ссылку на лежащую в его основе строку. так что создание копии не требуется. Если хорошо подумать, то часть пользы от БГ г1пдви11с(ег оказалась бы под вопросом, если бы он не поступал подобным образом. В конце концов, при создании громадной строки, скажем, размером в несколько мегабайт, такой как закодированное с помощью Ьаве64 графическое изображение. вряд ли захочется, чтобы для создания строки пришлось копировать весь буфер. Однако послевызова Бсгтпдвп11с(ег.тоагг1пя появляется переменная ягг1пд, а ясг1пдВп11бегхрвнит ссылку на ту же самую строку. Поскольку объект ясг1пя являетсянеизменяемым. в отношении лежащей в основе строки ягг1пяво11бег переключается на идиому "копирование при записи".
Таким образом, в месте, где производится добавление строки к ясг1пдво11с(ег после присваивания переменной ьп11г1, экземпляр БггапдВп11бег должен совдать новую копию внутренней строки. При работе с большими строковыми данными посредством ЯягапдВп11бег очень важно учитывать описанное поведение. Поиск строк с помощью регулярных выражений Тип Бувгекя. Бгг1пд сам по себе предлагает некоторые рудиментарные методы поиска вроде 1пбехОТ, 1пбехОЙАпу, Еаяг1пс(ехОТ, Еаяс1пк(ехОТАпу и Ясагсвкасп.
С помощью этих методов можно определить, содержит ли строка определенную подстроку, и где именно. Однако зти методы становятся весьма неуклюжими и слишком примитивными, когда возникает необходимость в более сложном поиске строк. К счастью, библиотека классов .)))ЕТ РгзгпеэюгК содержит классы, реализующие регулярные выражения (геяехр). Если вы еще не знакомы с регулярными выражениями, настоятельно рекомендуется изучить их синтаксис и способы их эффективного использования. Синтаксис регулярных выражений сам по себе является языком. Среди замечательных источников информации на эту тему — книга Джеффри Фрикка (бейгеу Е. Е Рг(есП] 240 Глаза 8 Мавсеппд Кеди!аг Ехргезз(опз, Т)нгс( ЕЙШоп (О'Ке1!!у Меб(а, 2006 г.), а также статья Кеди1аг Ехргеввюп Аапдиаде Е)етепСз (Элементы языка регулярных выражений) в документации МЯВОМ.
Возможности механизма регулярных выражений находятся наравне с аналогичными механизмами языков Рег! 5 и Ру()юп. Полное описание регулярных выражений вместе с их синтаксисом выходит за рамии настоящей книги. Тем не менее, ниже рассматриваются некоторые особенности использования регулярных выражений в . НЕТ Ргагпевюг)с. Существуют три главных типа операций.
для которых можно применять регулярные выражения. Первый — поиск в строке вхождения некоторого специфического шаблона и места такого вхождения. Поисковый шаблон может быть чрезвычайно сложным. Второй тнп подобен первому, за исключением того, что в процессе поиска искомое выражение разбивается на части. Например, при поиске в строке даты в определенном формате эту дату можно разделить на три части и разнести их по разным переменным. И, наконец, регулярные выражения часто применяются для выполнения операций поиска с заменой. Операции такого рода базируются на предыдущих двух. Давайте посмотрим, как можно достичь этих трех целей с применением реализации регулярных выражений .НЕТ Ргагпеаог)с. Поиск с помощью регулярных выражений Как и сам Яузсеш.














