正则表达式学习一
//入门 /////////////////////////////////////////////////////// //$str = "{111}{222}{333}@{AAA}{BBB}{CCC}"; //$array= array(); //preg_match_all('/{(.*?)}/', $str, $array); //var_dump($array); //$str = "hi php histr HImysql"; //$array = array(); //preg_match_all('/\bhi\b/', $str, $array); //var_dump($array); //\b是正则表达式规定的一个特殊代码,叫元字符,代表着单词的开头或结尾,也就是单词的分界处,虽然通常 //英文的单词是由空格,标点符号或者换行来分隔的,但是\b并不匹配这些单词分隔字符中的任何一个,它只匹配位置 //假如你要找的是hi后面不远处跟着一个php,你应该用\bhi\b.*\bphp\b。 //$str = "hi xxdxxd php histr HImysql"; //$array = array(); //preg_match_all('/\bhi\b.*\bphp\b/', $str, $array); //var_dump($array); //.匹配除了换行符以外任意符 //*它代表的不是一个字符,也不是位置,而是数量 它指定*前边的内容可以连续重复使用任意以使整个表达式得到匹配 //.*连接一起就意味着任意个任意符(但不能是换行)字会 //\d匹配0到9之间的数字 //$str = "010-12345678 010-98765432"; //$array = array(); //preg_match_all('/0\d{2}-\d{8}/', $str, $array); //var_dump($array); //元字符 /////////////////////////////////////////////////////// // 表1.常用的元字符 // . 匹配除换行符以外的任意字符 // \w 匹配字母或数字或下划线或汉字 // \s 匹配任意的空白符 // \d 匹配数字 // \b 匹配单词的开始或结束 // ^ 匹配字符的开始 // $ 匹配字符的结束 //匹配以a开始后面任意字符的单词 //$str = "area abbr append apple"; //$array = array(); //preg_match_all('/\ba\w*\b/', $str, $array); //var_dump($array); //匹配以a开始后面有三个字母的单词 //$str = "area abbr append apple"; //$array = array(); //preg_match_all('/\ba\w{3}\b/', $str, $array); //var_dump($array); //如果不使用^和$的话,对于\d{5,12}而言,使用这样的方法就只能保证字符串里包含5到12连续位数字,而不是整个字符串就是5到12位数字。 //无字符^和$都匹配一个位置,这和\b有点类似,^匹配你要用来查找的字符串的开头,$匹配结尾 /* $str = "411086544"; $array = array(); preg_match_all('/^\d{5,12}$/', $str, $array); var_dump($array); $string = "411086544"; if(ereg ("^[0-9]{5,9}$", $string)){ //操蛋要写成[0-9]才行 echo "ok"; }else{ echo "no"; }*/ //这里的{5,12}和前面介绍过的{2}是类似的,只不过{2}匹配只能不多不少重复2次,{5,12}则是重复的次数不能少于5次,不能多于12次,否则都不匹配。 //因为使用了^和$,所以输入的整个字符串都要用来和\d{5,12}来匹配,也就是说整个输入必须是5到12个数字,因此如果输入的QQ号能匹配这个正则表达式的话,那就符合要求了。 /*$string = "unibetter.com"; if(ereg ("unibetter\.com", $string)){ echo "ok"; }else{ echo "no"; }*/ /*$string = "c:\Windows"; //这里用//不行 if(ereg ("c:\\Windows", $string)){ }else{ echo "no"; }*/ //转义字符 /////////////////////////////////////////////////////// //如果你想查找元字符本身的话,比如你查找.,或者*,就出现了问题:你没办法指定它们,因为它们会被解释成别的意思。这时你就得使用\来取消这些字符的特殊意义。因此,你应该使用\.和\*。当然,要查找\本身,你也得用\\. //重复 /////////////////////////////////////////////////////// // * 重复零次或更多次 // + 重复一次或更多次 // ? 重复零次或一次 // {n} 重复n次 // {n,} 重复n次或更多次 // {n, m} 重复n次到m次 /*$string = "Windows1"; if(ereg ("Windows\d?", $string)){ echo "ok"; }else{ echo "no"; }*/ //字符类 /////////////////////////////////////////////////////// //要想查找数字,字母或数字,空白是很简单的,因为已经有了对应这些字符集合的元字符,但是如果你想匹配没有预定义元字符的字符集合(比如元音字母a,e,i,o,u),应该怎么办? //很简单,你只需要在方括号里列出它们就行了,像[aeiou]就匹配任何一个英文元音字母,[.?!]匹配标点符号(.或?或!)。 //我们也可以轻松地指定一个字符范围,像[0-9]代表的含意与\d就是完全一致的:一位数字;同理[a-z0-9A-Z_]也完全等同于\w(如果只考虑英文的话)。 //\(?0\d{2}[) -]?\d{8} //这个表达工可以匹配几种格式的电话号码. //像(010)88886666 022-22334455 02912345678 //首先是一个转义符\(, 它能出现0次或1次(?) // ‘(’能出现0次或者一次 //然后是一个0,后面跟着2个数字 \d{2} //然后是)或者-或者空格中的一个,它出现一次或者不出现(?) [) -]? //最后是8个数字(\d{8}) /*$number = "(010)12345678"; //哦[) -]这里的')'没有转义是因为在[]符内所以不用转义了 if(ereg("\(?0[0-9]{2}[) -]?[0-9]{8}", $number)) echo "ok"; else echo "no";*/ //分枝条件 /////////////////////////////////////////////////////// //正则表达式里的分枝条件指的是有几种规则,如果满足其中任意怀种规则都应该当成匹配,具体方法是|把不同的规则分隔开,听不明白?没关系 //0\d{2}-\d{8} | 0\d{3}-\d{7} //这个表达式能匹配两种以连字号分隔的电话号码,一种是三位区号,8位本地号(010-12345678) //一种是4位区号 7位本地号(0378-1234567) /*$number = "0234-1234567"; if(ereg("0[0-9]{2}-[0-9]{8}|0[0-9]{3}-[0-9]{7}", $number)) echo "ok"; else echo "no";*/ // \(0\d{2}\)[- ]?\d{8} | 0\d{2}[- ]?\d{8} //这个表达式匹配3位区号的电话号码,其中区号可以用小括号插起来,也可以不用,区号本地号间可以用连字号或空格间隔,也可以没有间隔 //$number = "02312345679"; //$number = "023-12345679"; /*$number = "(023)-12345679"; if(ereg("\(0[0-9]{2}\)[- ]?[0-9]{8}|0[0-9]{2}[- ]?[0-9]{8}", $number)) echo "ok"; else echo "no";*/ // \d{5}-\d{4}|\d{5}这个表达式用于匹配美国邮政编码, //美国邮编的规则是5位数字。或者连字号间隔的9位数字,之所以要给出这个例子因为它能说明一个问题 // 使用分枝条件时,要注意各个条件的顺序,如果你把它改成\d{5}|\d{5}-\d{4}的话 // 那么就会匹配5位邮编(以及9位邮编的前5位)。原因是匹配分枝条件时,次会从左到右地测试每个条件 // 如果满足了某个分枝的话,就不会再管其它的条件了 //分组 /////////////////////////////////////////////////////// //我们已经提到了自重复单个字符(直接在字符后面加上限定就行了);但是如果想要重复多个字符又该怎么办? //你可以用小括号来指定子表达式(也叫分组),然后你就可以指定这个子表达式的重复次数了,你也可以对子有达式进行其它一些操作 //(\d{1,3}\.){3} \d{1,3} //是一个简单的IP地址匹配表达式,要理解这个表达式,请按下列顺序分析它: // \d{1,3}匹配1到3位的数字,(\d{1,3}\.){3}匹配三位数字加上一个英文句号(这个整体也就是这个分组)重复3次,最后再加一一个一到三位的数字(\d{1,3}) /* $number = "256.300.888.999"; if(ereg("([0-9]{1,3}\.){3}[0-9]{1,3}", $number)) echo "ok"; else echo "no";*/ //不幸的是,它也将匹配256.300.888.999这种不可能存在的IP地址。如果能使用算术比较的话,或许能简单地解决这个问题,但是正则表达式中并不提供关于数学的任何功能,所以只能使用冗长的分组,选择,字符类来描述一个正确的IP地址:((2[0-4]\d|25[0-5]|[01]?\d\d?)\.){3}(2[0-4]\d|25[0-5]|[01]?\d\d?)。 //((2[0-4]\d|25[0-5]|[01]?\d\d?)\.){3}(2[0-4]\d|25[0-5]|[01]?\d\d?) /*$number = "254.254.254.101"; if(ereg("((2[0-4][0-9]|25[0-5]|[01]?[0-9][0-9]?)\.){3}(2[0-4][0-9]|25[0-5]|[01]?[0-9][0-9]?)", $number)) echo "ok"; else echo "no"; */ //反义 /////////////////////////////////////////////////////// //有时需要查找不属于某个能简单定义的字符类的字符,比如想查找除了数字以外,其它任意字符都行的情况且 //这时需要用到反义 //表3.常用的反义代码 // \W 匹配任意不是字母,数据字,下划线,汉字的字符 // \S 匹配任意不是空白符的字符 // \D 匹配任意非数字的字符 // \B 匹配不是单词开头或结束的位置 // [^x] 匹配除了x以外的任意字符 // [^aeiou] 匹配除了aeiou这几个字母以外的任意字符 //$number = " phpchain "; //例子:\S+匹配不包含空白符的字符串。 //不行 //if(ereg("\S+", $number)) { //echo "ok"; //}else{ //echo "no"; //} /*$number = " phpchain "; $array = array(); //成功 preg_match_all("/\S+/", $number, $array); var_dump($array);*/ //后向引用 /////////////////////////////////////////////////////// //使用小括号指定一个子表达式后,匹配这个表达式的文本(也就是分组捕获的内容)可以在表达式或其它程序中作进一步的处理,默认情况下,每个分组会自动拥有一个组号,规则是:从左向右,以分组的左括号为标志,第一个出现的分组的组号为1,第二个为2,以此类推 //后向引用用于重复搜索前面某个分组匹配的文本; 例如\1代表分组1匹配的文本,难以理解?请看示例