4.6.3 字符串(4)
使用与以前相同的word和words字符串,该代码段将产生相同的输出。因为LastIndexOf()往回搜索,所以开始的索引值是words->Length-1,对应字符串中最后一个字符。现在如果发现word出现时,我们必须将index减1,以便下次往回搜索时从当前word之前的那个字符开始。如果word正好出现在words的头部-- 即索引位置是0,则使index减1的结果是-1,这不是LastIndexOf()函数的合法参数,因为搜索的开始位置必须总在字符串之内。在循环条件中检查index是不是负值可以避免上述情况发生。如果&&运算符的右操作数是false,则不再计算左操作数。
最后一个需要提及的搜索函数是IndexOfAny(),它在字符串中搜索作为参数提供给它的、<wchar_t>类型的数组中任何字符的第一个实例。与IndexOf()函数类似,IndexOfAny()函数也有从字符串的头部或从指定的索引位置开始搜索的版本。下面是使用IndexOfAny()函数的一个完整示例。
试一试:搜索任意一组字符
该程序在字符串中搜索标点符号:
- // Ex4_19.cpp : main project file.
- // Searching for punctuation
-
- #include "stdafx.h"
-
- using namespace System;
-
- int main(array<System::String ^> ^args)
- {
- array<wchar_t>^ punctuation = {L'"', L'\'',
L'.', L',', L':', L';', L'!', - L' '};
- String^ ssentence = L"\"It's chilly in here\",
the boy's mother said - coldly.";
-
- // Create array of space characters same length as sentence
- array<wchar_t>^ indicators = gcnew array<wchar_t>
(sentence->Length){L' '}; -
- int index = 0; // Index of character found
- int count = 0; // Count of punctuation characters
- while((index = sentence->IndexOfAny(punctuation, index)) >= 0)
- {
- indicators[index] = L'^'; // Set marker
- ++index; // Increment to next character
- ++count; // Increase the count
- }
- Console::WriteLine(L"There are {0} punctuation characters in the
- string:",count);
- Console::WriteLine(L"\n{0}\n{1}", sentence,
gcnew String(indicators)); - return 0;
- }
该示例应该生成下面的输出:
- There are 6 punctuation characters in the string:
-
- "It's chilly in here", the boy's mother said coldly.
- ^ ^ ^^ ^ ^
示例说明
我们首先创建包含要查找的字符的数组,还要创建将被搜索的字符串:
- array<wchar_t>^ punctuation = {L'"', L'\'', L'.',
L',', L':', L';', L'!', L' '}; - String^ ssentence = L"\"It's chilly in here\",
the boy's mother said coldly.";
注意,必须使用转义序列来指定单引号字符,因为单引号在字符字面值中是定界符。我们可以在字符字面值中显式地使用双引号,因为在该上下文中不存在将其解释为定界符的风险。
接着定义一个字符数组,将该数组的元素初始化成空格符:
- array<wchar_t>^ indicators = gcnew array<
wchar_t>(sentence->Length){L' '};
该数组的元素数与sentence字符串中的字符数一样多。我们将在输出中用该数组来标记标点符号在sentence字符串中出现的位置。只要找到一个标点符号,就将适当的数组元素修改为'^'。注意在数组说明后面的大括号中用一个初值初始化所有数组元素的方式。
搜索发生在while循环中:
- while((index = sentence->IndexOfAny(punctuation, index)) >= 0)
- {
- indicators[index] = L'^'; // Set marker
- ++index; // Increment to next character
- ++count; // Increase the count
- }
循环条件本质上与我们在前面的代码段中看到的相同。在循环体内,我们将index位置的数组元素初始化为'^'字符,然后使index加1,为下次执行循环作好准备。当该循环结束时,count包含找到的标点符号的数量,而indicators将在sentence中这些字符所在的位置上包含'^'字符。
由下面这两条语句产生输出:
- Console::WriteLine(L"There are {0} punctuation characters in the string:",
- count);
- Console::WriteLine(L"\n{0}\n{1}" sentence, gcnew String(indicators));
第二条语句通过将indicators数组传递给String类的构造函数,从而在堆上根据该数组创建一个新的String对象。当被调用时,类的构造函数将创建本类的对象。当我们研究如何定义自己的类时,将学习与构造函数有关的更多内容。