字符串中判断存在的几种模式和效率(string.contains、string.IndexOf、Regex.Match)

  通常情况下,我们判断一个字符串中是否存在某值常常会用string.contains,其实判断一个字符串中存在某值的方法有很多种,最常用的就是前述所说的string.contains,相对来说比较常用的还有string.IndexOf和Regex.Match。直接上代码,后面在说些什么吧,通常情况下功能的实现最重要,作者的话,只对有心者有效。


using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Text.RegularExpressions;

namespace ExistsInString
{
    class Program
    {
        static void Main(string[] args)
        {
            string str0 = "|456|";
            string str1 = "|444|";
            string str2 = "|111|222|333|444|555|666|777|888|999|000|";

            //------------------------------------------
            //String.Contains方法

            if (str2.Contains(str0))
                Console.WriteLine("String.Contains->true");
            else
                Console.WriteLine("String.Contains->false");

            if (str2.Contains(str1))
                Console.WriteLine("String.Contains->true");
            else
                Console.WriteLine("String.Contains->false");

            //------------------------------------------
            //String.IndexOf方法
            int val1 = str2.IndexOf(str0);//不存在返回-1
            Console.WriteLine("String.IndexOf(no exists)->" + val1);
            int val2 = str2.IndexOf(str1);//存在返回str1首字符所在str2中的位置(>=0)
            Console.WriteLine("String.IndexOf(exists)->" + val2);

            //------------------------------------------
            //正则匹配方法
            if (Regex.Match(str2, "[|]456[|]").Success)
                Console.WriteLine("Regex.Match(no exists)->true");
            else
                Console.WriteLine("Regex.Match(no exists)->false");

            if (Regex.Match(str2, "[|]444[|]").Success)
                Console.WriteLine("Regex.Match(exists)->true");
            else
                Console.WriteLine("Regex.Match(exists)->false");

            Console.ReadKey();

            /*
             *如果上述三种方式都处理大量数据,效率如何呢?
             *以下循环六组数据说明
             */

            int loopCount = (int)10e6;
            DateTime lasttime = DateTime.Now;
            DateTime nowtime = DateTime.Now;

            for (int loop = 1; loop < 7; loop++)
            {
                Console.WriteLine("\r\nloop " + loop + " >>>>>>>");

                //------------------------------------------
                //String.Contains方法

                //no exists
                lasttime = DateTime.Now;
                for (int i = 0; i < loopCount; i++)
                    if (str2.Contains(str0)) { };
                nowtime = DateTime.Now;
                TimeSpan tsStrConNoExists = nowtime - lasttime;

                //exists
                lasttime = DateTime.Now;
                for (int i = 0; i < loopCount; i++)
                    if (str2.Contains(str1)) { };
                nowtime = DateTime.Now;
                TimeSpan tsStrConExists = nowtime - lasttime;

                //------------------------------------------
                //String.IndexOf方法

                //no exists
                lasttime = DateTime.Now;
                for (int i = 0; i < loopCount; i++)
                    if (str2.IndexOf(str0) >= 0) { };//上述已经提到不存在返回-1,存在返回一个非负整数,这里为什么不用 == -1 ,而是用了 >= 0 ,这是一个值得深思的问题?
                nowtime = DateTime.Now;
                TimeSpan tsStrIndNoExists = nowtime - lasttime;

                //exists
                lasttime = DateTime.Now;
                for (int i = 0; i < loopCount; i++)
                    if (str2.IndexOf(str1) >= 0) { };
                nowtime = DateTime.Now;
                TimeSpan tsStrIndExists = nowtime - lasttime;

                //------------------------------------------
                //Regex.Match方法

                //no exists
                Regex Reg0 = new Regex("[|]456[|]");
                lasttime = DateTime.Now;
                for (int i = 0; i < loopCount; i++)
                    if (Reg0.Match(str2).Success) { };
                nowtime = DateTime.Now;
                TimeSpan tsStrRegNoExists = nowtime - lasttime;

                //exists
                Regex Reg1 = new Regex("[|]444[|]");
                lasttime = DateTime.Now;
                for (int i = 0; i < loopCount; i++)
                    if (Reg1.Match(str2).Success) { };
                nowtime = DateTime.Now;
                TimeSpan tsStrRegExists = nowtime - lasttime;

                Console.WriteLine("no exists >>>");
                Console.WriteLine("tsStrConNoExists = " + tsStrConNoExists.Milliseconds);
                Console.WriteLine("tsStrIndNoExists = " + tsStrIndNoExists.Milliseconds);
                Console.WriteLine("tsStrRegNoExists = " + tsStrRegNoExists.Milliseconds);
                Console.WriteLine("exists >>>");
                Console.WriteLine("tsStrConExists = " + tsStrConExists.Milliseconds);
                Console.WriteLine("tsStrIndExists = " + tsStrIndExists.Milliseconds);
                Console.WriteLine("tsStrRegExists = " + tsStrRegExists.Milliseconds);
            }

            Console.ReadKey();
        }
    }
}

输入结果:

String.Contains->false
String.Contains->true
String.IndexOf(no exists)->-1
String.IndexOf(exists)->12
Regex.Match(no exists)->false
Regex.Match(exists)->true

loop 1 >>>>>>>
no exists >>>
tsStrConNoExists = 796
tsStrIndNoExists = 687
tsStrRegNoExists = 171
exists >>>
tsStrConExists = 484
tsStrIndExists = 234
tsStrRegExists = 796

loop 2 >>>>>>>
no exists >>>
tsStrConNoExists = 46
tsStrIndNoExists = 671
tsStrRegNoExists = 234
exists >>>
tsStrConExists = 546
tsStrIndExists = 437
tsStrRegExists = 734

loop 3 >>>>>>>
no exists >>>
tsStrConNoExists = 62
tsStrIndNoExists = 875
tsStrRegNoExists = 171
exists >>>
tsStrConExists = 609
tsStrIndExists = 562
tsStrRegExists = 781

loop 4 >>>>>>>
no exists >>>
tsStrConNoExists = 78
tsStrIndNoExists = 921
tsStrRegNoExists = 218
exists >>>
tsStrConExists = 609
tsStrIndExists = 640
tsStrRegExists = 828

loop 5 >>>>>>>
no exists >>>
tsStrConNoExists = 156
tsStrIndNoExists = 268
tsStrRegNoExists = 265
exists >>>
tsStrConExists = 609
tsStrIndExists = 578
tsStrRegExists = 890

loop 6 >>>>>>>
no exists >>>
tsStrConNoExists = 109
tsStrIndNoExists = 46
tsStrRegNoExists = 546
exists >>>
tsStrConExists = 625
tsStrIndExists = 609
tsStrRegExists = 953



测试结果中不难发现,如果strA中不包括strB,使用strA.Contains(strB)更优;反之,如果strA中包括strB,使用strA.IndexOf(strB)更优。(Regex.Match在此方法中貌似没有体现出任何优势,它更适用于模糊匹配)

具体要使用string.Contains,或是string.IndexOf要看形势。

之前有看过string下很多方法实现的代码(微软的,非他人),string.Contains是基于string.IndexOf上的一个方法,使用string.Contains的时候,会调用

string.IndexOf,按原理,使用string.IndexOf的效率是要高于string.Contains的,但是这个测试结果让我大跌眼镜,应该是我在上述代码中使用的判断语句造成的这种非理想的测试结果,按照个人的意愿,还是希望多使用string.IndexOf。



其实一次微小的改变在当前可能影响不了什么,但是在日积月累中,它的优势就显而易见了。想要快速变得比他人更强,不需要多么费劲,只需要每天多做一点点(千分之一)

一年之后:(1 + 0.001)365 =  1.44倍

十年之后(1 + 0.001)3650 =  38.4倍

这是一种优势的计算,这是一种能力的计算,这是一种薪水的计算,...,不管是什么的计算,请记得每天只需进步一点点,随着时间的积累,你将会蜕变。该吃吃,该喝喝,该玩玩,该睡睡...只需要将你每天白日梦呓和漫无目的做无意义事情的时间用到它该用到的地方,你就在进步。

时间: 2024-08-02 17:28:33

字符串中判断存在的几种模式和效率(string.contains、string.IndexOf、Regex.Match)的相关文章

查询字符串中字母的个数(两种实现方式1,list与set集合 2,map集合)

题目: 取出一个字符串中字母出现的次数.如:字符串:"abcde%^kka27qoq" ,输出格式为:a(2)b(1)k(2)... 第一种方式(set和list结合使用): package itheima; import java.util.ArrayList; import java.util.LinkedHashSet; import java.util.List; import java.util.Set; /** * .取出一个字符串中字母出现的次数.如:字符串:"

【转载】iOS中delegate,notification,KVO三种模式实现通信的优缺点

原帖地址:http://blog.csdn.net/yangxt/article/details/8176636 在开发iOS中,有三种模式来实现controller之间的通信: 1.委托delegation: 2.通知中心Notification Center: 3.键值观察key value observing,KVO 因此,那为什么我们需要这些模式以及什么时候用它以及什么时候不用它. 1.delegate 基本特征: 一 个controller定义了一个协议(即一系列的方法定义).该协议描

浏览器中的user-agent的几种模式

服务器一般会根据访问的浏览器进行识别,针对不同浏览器才用不同的网站样式及结构,也是通过这个信息判断用户使用的平台模式(手机,pc或平板) 识别为手机一般有这几个关键字: "Windows Phone","iPod","iPad","Android","ios","iPhone" 具体常用的几类user-agent信息为: 1 火狐浏览器: Mozilla/5.0 (Windows NT

iOS中图片动画的三种模式及基本的代码实现

-(void)play { //第一种图片动画模式 头尾方式 //头尾方式 [UIView beginAnimations:nil context:nil];//动画开始 [UIView setAnimationDuration:10];//设置动画播放时长 /*内部写图片处理*/ [UIView commitAnimations];//提交动画 //第二种方式:图片动画结束处理模式 [UIView animateWithDuration:10 animations:^{ /*图片处理操作*/

C中操作文件的几种模式

使用文件的方式共同拥有12种,以下给出了它们的符号和意义.  文件打开方式  意义 rt  仅仅读打开一个文本文件.仅仅同意读数据  wt  仅仅写打开或建立一个文本文件,仅仅同意写数据  at  追加打开一个文本文件,并在文件末尾写数据  rb  仅仅读打开一个二进制文件.仅仅同意读数据  wb  仅仅写打开或建立一个二进制文件,仅仅同意写数据  ab  追加打开一个二进制文件,并在文件末尾写数据  rt+  读写打开一个文本文件,同意读和写  wt+  读写打开或建立一个文本文件,同意读写 

leetcode 387. 字符串中的第一个唯一字符(First Unique Character in a String)

目录 题目描述: 示例: 解法: 题目描述: 给定一个字符串,找到它的第一个不重复的字符,并返回它的索引.如果不存在,则返回 -1. 示例: s = "leetcode" 返回 0. s = "loveleetcode", 返回 2. 注意事项:您可以假定该字符串只包含小写字母. 解法: class Solution { public: int firstUniqChar(string s) { vector<int> count(128, 0); in

Java中字符串中子串的查找共有四种方法(indexof())

Java中字符串中子串的查找共有四种方法(indexof()) Java中字符串中子串的查找共有四种方法,如下:1.int indexOf(String str) :返回第一次出现的指定子字符串在此字符串中的索引. 2.int indexOf(String str, int startIndex):从指定的索引处开始,返回第一次出现的指定子字符串在此字符串中的索引. 3.int lastIndexOf(String str) :返回在此字符串中最右边出现的指定子字符串的索引. 4.int las

判断某个字符串中是否存在某些字符

//判断某个字符串中是否存在amr字符,如果不存在执行 if(audios.indexOf("amr") == -1){ audios=""; } //判断某个字符串中是否存在amr字符,如果存在执行 if(audios.indexOf("amr") != -1){ audios=""; }

字符串如何判断null.

转http://blog.sina.com.cn/s/blog_48cd37140101awgq.html Java中判断String不为空的问题 一.判断一个字符串str不为空的方法有: 1. str!=null; 2. "".equals(str); 3. str.length()!=0; ( 注意:length是属性,一般集合类对象拥有的属性,取得集合的大小. 例如:数组.length就是取得数组的长度. length()是方法,一般字符串类对象有该方法,也是取得字符串长度. 例