Введение 8 Этапы создания Windowsприложения 8
Скачать 6.98 Mb.
|
9.2. Посимвольная обработка строкиСуществует несколько способов обрабатывать строку символов. Один из них – посимвольная обработка. В этом случае строка рассматривается как массив символов. Соответственно, для ее обработки организуется цикл по всем символам строки. Так как нумерация символов начинается с единицы, то начальное значение счетчика берут равным единице, а не нулю, как при работе с одномерным массивом. Номер последнего символа совпадает с длиной строки, поэтому конечное значение счетчика записывают в виде Len(s), где s – обрабатываемая строка. В теле цикла строку обрабатывают так же, как и одномерный массив. С помощью функции Strings.Mid выделяют один символ, его анализируют и обрабатывают. В качестве примера посимвольной обработки рассмотрим следующую задачу. В строке заменить каждый символ, стоящий после буквы «а» на символ звездочка (*). Для решения задачи нам потребуются две переменные. В строковой переменной s мы будем хранить обрабатываемую строку. Dim s As String Так как посимвольная обработка выполняется в цикле, то для его организации нам потребуется целочисленный счетчик i. Dim i As Integer Очищаем окно списка от предыдущих результатов работы программы. lstText.Items.Clear() Вводим строку, которую надо обработать. Обратите внимание, при вводе строки не используется преобразование Val. Более того, использование данного преобразования является логической ошибкой, не позволяющей получить правильные результаты. s = InputBox("Введите строку") В окно списка выводим исходную строку текста, чтобы пользователь мог контролировать результаты работы программы. lstText.Items.Add(s) Организуем цикл для посимвольной обработки строки. Обработку будем начинать с первого символа (так как нулевого символа не существует). Заканчивать обработку будем на предпоследнем символе строки, поскольку нам надо изменить символ, следующий за обрабатываемым. Если буква «а» является последним символом строки, то символ, стоящий за ней, обработать нельзя, так как его нет. For i = 1 To Len(s) – 1 С помощью функции Strings.Mid выделяем один символ, стоящий на i-ой позиции. Анализируем этот символ. If Strings.Mid(s, i, 1) = "а" Or _ Strings. Mid(s, i, 1) = "А" Then Если этот символ является строчной или прописной буквой «а», то символ, стоящий за ним, необходимо заменить на звездочку. Так как мы анализировали символ, стоящий на i-ой позиции, то изменять мы будем символ, стоящий на позиции (i+1). Обратите внимание, что любой символ, явно используемый в программе, берется в кавычки. Mid(s, i + 1, 1) = "*" End If Next После завершения основного цикла нам остается только вывести измененную строку в окно списка. lstText.Items.Add(s) Полный текст программы представлен в приложении 43. Пример работы программы приведен на рис. 60. Рис. 60. Пример посимвольной обработки строки 9.3. Формирование массива слов строкиФормирование массива слов строки является одной из базовых операций при обработке символьной информации. Решение большинства строковых задач начинается с ввода строки и ее разбиения на массив слов. Такой подход позволяет существенно упростить решение задач, в которых требуется найти слово, удовлетворяющее какому-либо условию. В общем случае задача формирования массива слов формулируется следующим образом. Дана строка текста, в которой слова разделены произвольным количеством пробелов. Пробелы могут стоять перед первым словом и за последним. Сформировать массив слов строки. Исходную строку и полученный массив вывести в окно списка. Существует три различных способа решения этой задачи. Рассмотрим особенности программной реализации каждого их них. Способ 1. Первый способ основан на посимвольной обработке строки. Предполагается, что внутри слова нет пробелов. Поэтому каждый символ строки анализируется. Если он не является пробелом, значит, это очередная буква слова. Тогда она дописывается в конец слова, выделяемого в данный момент. Если очередной символ не является пробелом, а сразу за ним стоит пробел, значит, это последний символ слова. Полученное слово надо дописать в массив слов, а текущее слово сделать пустым, так как оно еще не началось. Для решения задачи нам потребуются следующие переменные. В строковой переменной s мы будем хранить обрабатываемую строку. Dim s As String Так как посимвольная обработка выполняется в цикле, то для его организации нам потребуется целочисленный счетчик i. Dim i As Integer Выделяемые слова мы будем записывать в одномерный массив slova(). Этот массив обязательно будет иметь тип String. Dim slova() As String Так как каждое слово мы будем выделять посимвольно, то нам потребуется строковая переменная, в которой будет постепенно накапливаться очередное слово строки. Dim tek As String Для обработки массива необходимо знать, сколько элементов в нем содержится. Номер последнего элемента, записанного в массив слов, будем хранить в переменной n. Dim n As Integer Очищаем окно списка от предыдущих результатов работы программы. lstText.Items.Clear() Вводим строку, которую надо обработать. Обратите внимание, при вводе строки не используется преобразование Val. Более того, использование данного преобразования является логической ошибкой, не позволяющей получить правильные результаты. s = InputBox("Введите строку") В окно списка выводим исходную строку текста, чтобы пользователь мог контролировать результаты работы программы. lstText.Items.Add(s) До начала формирования массив слов пуст. В нем нет ни одного элемента. Поэтому номер последнего элемента находится за пределами массива. Возьмем его равным -1. n = -1 Перед началом выделения слов из строки очистим переменную, в которой будет находиться очередное слово. tek = "" Алгоритм предполагает, что за каждым словом строки обязательно идет пробел. Чтобы последнее слово тоже подчинялось этому правилу, допишем к исходной строке пробел. s += " " Организуем цикл для посимвольной обработки строки. Обработку будем начинать с первого символа (так как нулевого символа не существует). Заканчивать обработку будем на предпоследнем символе строки, поскольку мы анализируем не только текущий символ строки, но и следующим за ним. А для последнего символа следующий символ не существует. For i = 1 To Len(s) – 1 С помощью функции Strings.Mid выделяем один символ, стоящий на i-ой позиции. Анализируем этот символ. If Mid(s, i, 1) <> " " Then Если выделенный символ не является пробелом, то дописываем его к текущему слову. tek += Mid(s, i, 1) End If Теперь анализируем текущий символ и символ, следующий за ним. If Mid(s, i, 1) <> " " And _ Mid(s, i + 1, 1) = " " Then Если текущий символ не является проблем, а за ним следует пробел, значит, текущий символ был последним в слове. Следовательно, очередное слово строки выделено полностью, и его надо записать в массив слов. При этом номер последнего слова в массиве увеличится на единицу. n += 1 Изменяем размер массива. Использование ключевого слова Preserve позволяет сохранить ранее найденные слова. ReDim Preserve slova(n) В массив слов на последнюю позицию записываем выделенное слово. slova(n) = tek Так как следующее слово еще не началось, полагаем его пустым. tek = "" End If Next После завершения цикла массив слов полностью сформирован, и нам остается только вывести его в окно списка. Сначала выводим горизонтальную черту, чтобы зрительно отделить исходную строку от полученного массива. lstText.Items.Add("--------------------------------") Затем выводим поясняющий заголовок. lstText.Items.Add("Слова строки") Теперь мы организуем цикл для вывода всех элементов массива слов. Обратите внимание, что элементы массива слов нумеруются с нуля. For i = 0 To n На каждом шаге цикла выводим очередное слово в окно списка. lstText.Items.Add(slova(i)) Next После завершения цикла вывода массив слов можно обрабатывать как любой одномерный массив. Способ 2. Второй способ предлагает обрабатывать строку с помощью функций Visual Basic 2005. Сначала из строки удаляются все пробелы, стоящие перед первым словом и за последним. Затем убираются лишние пробелы, чтобы между словами осталось ровно по одному пробелу. Наконец к строке дописывается равно один пробел, чтобы за каждым словом строки шел пробел, в том числе и за последним. После этого переходят к выделению слов. Ищут позицию первого пробела в строке. Все, что стоит до пробела, является первым словом. Его записывают в массив и удаляют из основной строки вместе с пробелом. Процесс повторяется многократно до тех пор, пока в строке не останется ни одного слова. Для решения задачи нам потребуются следующие переменные. В строковой переменной s мы будем хранить обрабатываемую строку. Dim s As String Так как массив слов выводится в цикле, то для его организации нам потребуется целочисленный счетчик i. Dim i As Integer Выделяемые слова мы будем записывать в одномерный массив slova(). Этот массив обязательно будет иметь тип String. Dim slova() As String Для обработки массива необходимо знать, сколько элементов в нем содержится. Номер последнего элемента, записанного в массив слов, будем хранить в переменной n. Dim n As Integer В процессе выделения очередного слова мы будем искать в строке первый пробел. Его позицию мы будем хранить в целочисленной переменной pos. Dim pos As Integer Очищаем окно списка от предыдущих результатов работы программы. lstText.Items.Clear() Вводим строку, которую надо обработать. Обратите внимание, при вводе строки не используется преобразование Val. Более того, использование данного преобразования является логической ошибкой, не позволяющей получить правильные результаты. s = InputBox("Введите строку") В окно списка выводим исходную строку текста, чтобы пользователь мог контролировать результаты работы программы. lstText.Items.Add(s) Удаляем пробелы, стоящие перед первым словом и за последним. s = Strings.Trim(s) Удаляем лишние пробелы между словами. Для этого во всей строке многократно заменяем два подряд идущих пробела на один. Процесс замены повторяется до тех пор, пока в строке не останется ни одного сдвоенного пробела. Другими словами, цикл завершится тогда, когда функция Strings.InStr, ищущая два подряд идущих пробела, вернет значение ноль, которое означает, что в заданной строке нет искомой подстроки. Do Until Strings.InStr(s, " ") = 0 Функция Strings.Replace используется для замены всех сдвоенных пробелов одинарными. s = Strings.Replace(s, " ", " ") Loop До начала формирования массив слов пуст. В нем нет ни одного элемента. Поэтому номер последнего элемента находится за пределами массива. Возьмем его равным -1. n = -1 Чтобы последнее слово тоже подчинялось этому правилу, допишем к исходной строке пробел. s += " " Процесс выделения слов продолжается до тех пор, пока в исходной строке есть хотя бы одно слово. При этом ее длина обязательно будет больше нуля. Как только в строке не останется ни одного слова, ее длина станет равной нулю, и выполнение цикла прекратится. Do While Len(s) > 0 Ищем в строке первый пробел и запоминаем его позицию. pos = Strings.InStr(s, " ") Переходим выделению очередного слова. Так как новое слово будет записано в массив, то номер последнего элемента в этом массиве увеличится на единицу. n += 1 Изменяем размер массива. Использование ключевого слова Preserve позволяет сохранить ранее найденные слова. ReDim Preserve slova(n) На место последнего элемента массива записываем очередное слово. Это слово является левой подстрокой обрабатываемой строки, которая закончится перед пробелом. slova(n) = Strings.Left(s, pos - 1) Теперь удаляем выделенное слово из строки. Для этого достаточно выделить правую подстроку обрабатываемой строки, начиная с символа, стоящего сразу после пробела. s = Strings.Mid(s, pos + 1) Loop После завершения цикла массив слов полностью сформирован, и нам остается только вывести его в окно списка. Сначала выводим горизонтальную черту, чтобы зрительно отделить исходную строку от полученного массива. lstText.Items.Add("-------------------------------") Затем выводим поясняющий заголовок. lstText.Items.Add("Слова строки") Теперь мы организуем цикл для вывода всех элементов массива слов. Обратите внимание, что элементы массива слов нумеруются с нуля. For i = 0 To n На каждом шаге цикла выводим очередное слово в окно списка. lstText.Items.Add(slova(i)) Next После завершения цикла вывода массив слов можно обрабатывать как любой одномерный массив. Способ 3. Третий способ формирования массива слов основан на использовании функции Strings.Split, описанной в разделе 9.1. Эта функция разбивает строку на слова, которые записывает в массив. Перед использованием этой функции строку необходимо преобразовать: удалить из нее все пробелы, стоящие перед первым словом и за последним, и убрать лишние пробелы между словами. То есть слова в строке должны быть разделены ровно одним пробелом. Для решения задачи нам потребуются следующие переменные. В строковой переменной s мы будем хранить обрабатываемую строку. Dim s As String Так как массив слов выводится в цикле, то для его организации нам потребуется целочисленный счетчик i. Dim i As Integer Выделяемые слова мы будем записывать в одномерный массив slova(). Этот массив обязательно будет иметь тип String. Dim slova() As String Для обработки массива необходимо знать, сколько элементов в нем содержится. Номер последнего элемента, записанного в массив слов, будем хранить в переменной n. Dim n As Integer Очищаем окно списка от предыдущих результатов работы программы. lstText.Items.Clear() Вводим строку, которую надо обработать. Обратите внимание, при вводе строки не используется преобразование Val. Более того, использование данного преобразования является логической ошибкой, не позволяющей получить правильные результаты. s = InputBox("Введите строку") В окно списка выводим исходную строку текста, чтобы пользователь мог контролировать результаты работы программы. lstText.Items.Add(s) Удаляем пробелы, стоящие перед первым словом и за последним. s = Strings.Trim(s) Удаляем лишние пробелы между словами. Для этого во всей строке многократно заменяем два подряд идущих пробела на один. Процесс замены повторяется до тех пор, пока в строке не останется ни одного сдвоенного пробела. Другими словами, цикл завершится тогда, когда функция Strings.InStr, ищущая два подряд идущих пробела, вернет значение ноль, которое означает, что в заданной строке нет искомой подстроки. Do Until Strings.InStr(s, " ") = 0 Функция Strings.Replace используется для замены всех сдвоенных пробелов одинарными. s = Strings.Replace(s, " ", " ") Loop Теперь можно вызвать функцию Strings.Split, которая сформирует массив слов. Так как в нашей строке слова разделяются пробелом, то его в качестве разделителя можно не указывать. slova = Strings.Split(s) Чтобы иметь возможность обрабатывать массив слов нам необходимо узнать номер последнего элемента в этом массиве. Для этого в Visual Basic 2005 есть специальная функция UBound. Она возвращает номер последнего элемента массива, который указан в круглых скобках и, следовательно, является единственным аргументом этой функции. n = UBound(slova) Теперь массив слов полностью сформирован, и нам остается только вывести его в окно списка. Сначала выводим горизонтальную черту, чтобы зрительно отделить исходную строку от полученного массива. lstText.Items.Add("--------------------------------") Затем выводим поясняющий заголовок. lstText.Items.Add("Слова строки") Теперь мы организуем цикл для вывода всех элементов массива слов. Обратите внимание, что элементы массива слов нумеруются с нуля. For i = 0 To n На каждом шаге цикла выводим очередное слово в окно списка. lstText.Items.Add(slova(i)) Next После завершения цикла вывода массив слов можно обрабатывать как любой одномерный массив. Полный текст программы представлен в приложении 44. Пример работы программы приведен на рис. 61. Рис. 61. Пример работы программы формирования массива слов |