首页 后端开发 php教程 php适用于windows的fnmatch(匹配函数),可匹配中文。_PHP教程

php适用于windows的fnmatch(匹配函数),可匹配中文。_PHP教程

Jul 13, 2016 pm 05:18 PM
windows

 

该贴中有两种方法可以实现fnmatch函数,现贴如下:

 

function fnmatch($pattern, $string)         //$pattern匹配式, $string被匹配的字符串
{
    $starStack = array();                   //创建记录pattern开始位置的栈,这个作用是像编辑器的后退
    $sstrStack = array();                   //创建记录$string开始位置的栈
    $countStack = 0;                        //栈大小,用一个同步记录栈大小,减少count()时所耗的时间
    $ptnStart = strlen($pattern) - 1;       //定位匹配式最后一个字符, 算法是从字符串后面开始匹配
    $strStart = strlen($string) - 1;        //定位字符串的最好一个字符
    for(; 0 <= $strStart; $strStart --)     //开始匹配循环, 每匹配一个字符, $strStart就往前移一个字符
    {
        $sc = $string{$strStart};           //取得当前在比较的字符
        $pc = ($ptnStart < 0) ? &#39;&#39; : $pattern{$ptnStart};//取得匹配式当前的字符,已到结束位置,给个空
        if($sc !== $pc)
        {                                   //当两个字符不相同时, 就要进行一些匹配式特殊字符的比较
            if($pc === &#39;*&#39;)                 //如果匹配式当前字符是*号, 进行*号匹配
            {
                while($ptnStart > 0 && ($pc = $pattern{$ptnStart - 1}) === &#39;*&#39;)
                    $ptnStart --;           //while这段是去除几个连续的*号, 并尝试和取得下一个字符
                if($ptnStart > 0 && ($pc === $sc || $pc === &#39;?&#39;))//比较下个字符是否相同或是?号
                {                           //如果下一个字符匹配成功
                    $starStack[$countStack] = $ptnStart;//保存这个*号的位置
                    $sstrStack[$countStack] = $strStart;//保存$string开始位置
                    $countStack ++;         //栈向下移一
                    $ptnStart -= 2;         //匹配式定位,前移两位,分别是当前*号位和已经匹配的一个
                    continue;               //进行下一次循环
                }
            }
            elseif($pc === &#39;?&#39;)             //如果匹配式当前字符是?号, 进行?号匹配
            {
                $ptnStart --;               //?号匹配是字符串同步前移一个位置
            }
            elseif($countStack > 0)         //如果不是通配符,检查栈中是否有保存上一个*号的位置
            {                               //有就还原此*号位置, 回到上一个*号处再次进行匹配
                $countStack --;
                $ptnStart = $starStack[$countStack];//还原*号位置
                $strStart = $sstrStack[$countStack];//还原$string开始位置
            }
            else 
            {
                return false;               //以上情况都没有的话, 匹配失败, 返回flase
            }
        }
        else
        {
            $ptnStart --;                   //字符串位置和匹配式位置上相同,前移一位,继续下个匹配
        }
    }                                       //匹配循环结束
    if($ptnStart === -1)                    //刚好匹配式的位置也结束, 则匹配成功, 返回true
    {
        return true;
    }
    elseif($ptnStart >= 0)                  //匹配式并没有结束, 还有一些没有匹配
    {
        while($ptnStart > 0 && $pattern{$ptnStart} === &#39;*&#39;)//检查剩下的是不是都是*号,去除这些*号
            $ptnStart --;
        if($pattern{$ptnStart} === &#39;*&#39;)     //最后的只有一个*号结束的话, 就匹配成功, 返回true
            return true;
        else
            return false;                   //否则, 返回false
    }
    return false;
}
登录后复制

if (!function_exists(&#39;fnmatch&#39;)) {
        function fnmatch($pattern, $string) {
            return @preg_match(&#39;/^&#39; . strtr(addcslashes($pattern, &#39;.+^$(){}=!<>|&#39;), array(&#39;*&#39; => &#39;.*&#39;, &#39;?&#39; => &#39;.?&#39;)) . &#39;$/i&#39;, $string);
        }
    }
登录后复制

这两个方法都可以实现,但由于我要匹配的有包含中文的,比如

我爱中国

匹配 我爱??

就无法实现了,因为“中国”这个字符算4个字符,假如 匹配 我爱???? 应该就没问题了,但是这样对于我们来说使用非常的不方便,于是我改了一个第一个函数的实现,使用mb_strlen的方法来统计和分割字符,实现如下:

function fnmatch($pattern, $string)         //$pattern匹配式, $string被匹配的字符串
{
	$encoding = gb2312;					//根据自己的页面的编码,来定义这个编码
    $starStack = array();                   //创建记录pattern开始位置的栈,这个作用是像编辑器的后退
    $sstrStack = array();                   //创建记录$string开始位置的栈
    $countStack = 0;                        //栈大小,用一个同步记录栈大小,减少count()时所耗的时间
    $ptnStart = mb_strlen($pattern, $encoding) - 1;       //定位匹配式最后一个字符, 算法是从字符串后面开始匹配
    $strStart = mb_strlen($string, $encoding) - 1;        //定位字符串的最好一个字符
    for(; 0 <= $strStart; $strStart --)     //开始匹配循环, 每匹配一个字符, $strStart就往前移一个字符
    {
		$sc = mb_substr($string, $strStart, 1, $encoding);           //取得当前在比较的字符
		$pc = ($ptnStart < 0) ? &#39;&#39; : mb_substr($pattern, $ptnStart, 1, $encoding);//取得匹配式当前的字符,已到结束位置,给个空
        if($sc !== $pc)
        {                                   //当两个字符不相同时, 就要进行一些匹配式特殊字符的比较
            if($pc === &#39;*&#39;)                 //如果匹配式当前字符是*号, 进行*号匹配
            {
                while($ptnStart > 0 && ($pc = mb_substr($pattern, $ptnStart-1, 1, $encoding)) === &#39;*&#39;)
                    $ptnStart --;           //while这段是去除几个连续的*号, 并尝试和取得下一个字符
                if($ptnStart > 0 && ($pc === $sc || $pc === &#39;?&#39;))//比较下个字符是否相同或是?号
                {                           //如果下一个字符匹配成功
                    $starStack[$countStack] = $ptnStart;//保存这个*号的位置
                    $sstrStack[$countStack] = $strStart;//保存$string开始位置
                    $countStack ++;         //栈向下移一
                    $ptnStart -= 2;         //匹配式定位,前移两位,分别是当前*号位和已经匹配的一个
                    continue;               //进行下一次循环
                }
            }
            elseif($pc === &#39;?&#39;)             //如果匹配式当前字符是?号, 进行?号匹配
            {
                $ptnStart --;               //?号匹配是字符串同步前移一个位置
            }
            elseif($countStack > 0)         //如果不是通配符,检查栈中是否有保存上一个*号的位置
            {                               //有就还原此*号位置, 回到上一个*号处再次进行匹配
                $countStack --;
                $ptnStart = $starStack[$countStack];//还原*号位置
                $strStart = $sstrStack[$countStack];//还原$string开始位置
            }
            else 
            {
                return false;               //以上情况都没有的话, 匹配失败, 返回flase
            }
        }
        else
        {
            $ptnStart --;                   //字符串位置和匹配式位置上相同,前移一位,继续下个匹配
        }
    }                                       //匹配循环结束
    if($ptnStart === -1)                    //刚好匹配式的位置也结束, 则匹配成功, 返回true
    {
        return true;
    }
    elseif($ptnStart >= 0)                  //匹配式并没有结束, 还有一些没有匹配
    {
        while($ptnStart > 0 && mb_substr($pattern, $ptnStart, 1, $encoding) === &#39;*&#39;)//检查剩下的是不是都是*号,去除这些*号
            $ptnStart --;
        if(mb_substr($pattern, $ptnStart, 1, $encoding) === &#39;*&#39;)     //最后的只有一个*号结束的话, 就匹配成功, 返回true
            return true;
        else
            return false;                   //否则, 返回false
    }
    return false;
}
登录后复制

实现完毕,可完美匹配中文了。

 

www.bkjia.comtruehttp://www.bkjia.com/PHPjc/621633.htmlTechArticle该贴中有两种方法可以实现fnmatch函数,现贴如下: function fnmatch($pattern, $string) //$pattern匹配式, $string被匹配的字符串{ $starStack = array(); //创...
本站声明
本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系admin@php.cn

热AI工具

Undresser.AI Undress

Undresser.AI Undress

人工智能驱动的应用程序,用于创建逼真的裸体照片

AI Clothes Remover

AI Clothes Remover

用于从照片中去除衣服的在线人工智能工具。

Undress AI Tool

Undress AI Tool

免费脱衣服图片

Clothoff.io

Clothoff.io

AI脱衣机

Video Face Swap

Video Face Swap

使用我们完全免费的人工智能换脸工具轻松在任何视频中换脸!

热工具

记事本++7.3.1

记事本++7.3.1

好用且免费的代码编辑器

SublimeText3汉化版

SublimeText3汉化版

中文版,非常好用

禅工作室 13.0.1

禅工作室 13.0.1

功能强大的PHP集成开发环境

Dreamweaver CS6

Dreamweaver CS6

视觉化网页开发工具

SublimeText3 Mac版

SublimeText3 Mac版

神级代码编辑软件(SublimeText3)

可以在 Windows 7 上安装 mysql 吗 可以在 Windows 7 上安装 mysql 吗 Apr 08, 2025 pm 03:21 PM

是的,可以在 Windows 7 上安装 MySQL,虽然微软已停止支持 Windows 7,但 MySQL 仍兼容它。不过,安装过程中需要注意以下几点:下载适用于 Windows 的 MySQL 安装程序。选择合适的 MySQL 版本(社区版或企业版)。安装过程中选择适当的安装目录和字符集。设置 root 用户密码,并妥善保管。连接数据库进行测试。注意 Windows 7 上的兼容性问题和安全性问题,建议升级到受支持的操作系统。

mysql 无法连接到本地主机怎么解决 mysql 无法连接到本地主机怎么解决 Apr 08, 2025 pm 02:24 PM

无法连接 MySQL 可能是由于以下原因:MySQL 服务未启动、防火墙拦截连接、端口号错误、用户名或密码错误、my.cnf 中的监听地址配置不当等。排查步骤包括:1. 检查 MySQL 服务是否正在运行;2. 调整防火墙设置以允许 MySQL 监听 3306 端口;3. 确认端口号与实际端口号一致;4. 检查用户名和密码是否正确;5. 确保 my.cnf 中的 bind-address 设置正确。

MySQL安装在特定系统版本上报错的解决途径 MySQL安装在特定系统版本上报错的解决途径 Apr 08, 2025 am 11:54 AM

MySQL安装报错的解决方法是:1.仔细检查系统环境,确保满足MySQL的依赖库要求,不同操作系统和版本需求不同;2.认真阅读报错信息,根据提示(例如缺少库文件或权限不足)采取对应措施,例如安装依赖或使用sudo命令;3.必要时,可尝试源码安装并仔细检查编译日志,但这需要一定的Linux知识和经验。最终解决问题的关键在于仔细检查系统环境和报错信息,并参考官方文档。

mySQL下载完安装不了 mySQL下载完安装不了 Apr 08, 2025 am 11:24 AM

MySQL安装失败的原因主要有:1.权限问题,需以管理员身份运行或使用sudo命令;2.依赖项缺失,需安装相关开发包;3.端口冲突,需关闭占用3306端口的程序或修改配置文件;4.安装包损坏,需重新下载并验证完整性;5.环境变量配置错误,需根据操作系统正确配置环境变量。解决这些问题,仔细检查每个步骤,就能顺利安装MySQL。

无法从终端访问 mysql 无法从终端访问 mysql Apr 08, 2025 pm 04:57 PM

无法从终端访问 MySQL 可能是由于:MySQL 服务未运行;连接命令错误;权限不足;防火墙阻止连接;MySQL 配置文件错误。

mysql怎么复制粘贴 mysql怎么复制粘贴 Apr 08, 2025 pm 07:18 PM

MySQL 中的复制粘贴包含以下步骤:选择数据,使用 Ctrl C(Windows)或 Cmd C(Mac)复制;在目标位置右键单击,选择“粘贴”或使用 Ctrl V(Windows)或 Cmd V(Mac);复制的数据将插入到目标位置,或替换现有数据(取决于目标位置是否已存在数据)。

PS怎么拉垂直参考线 PS怎么拉垂直参考线 Apr 06, 2025 pm 08:18 PM

在 Photoshop 中拉垂直参考线:启用标尺视图(视图 &gt; 标尺)。悬停鼠标在标尺垂直边缘,光标变为带有双箭头的垂直线后按住并拖动鼠标拉出参考线。通过拖动重新定位参考线,或将其悬停变为十字形后单击删除。

mysql下载时提示磁盘写入错误如何处理 mysql下载时提示磁盘写入错误如何处理 Apr 08, 2025 am 11:51 AM

MySQL下载提示磁盘写入错误,解决方案如下:1.检查磁盘空间是否不足,清理空间或更换更大磁盘;2.使用磁盘检测工具(如chkdsk或fsck)检查并修复磁盘错误,必要时更换硬盘;3.检查目标目录权限,确保用户账户拥有写入权限;4.更换下载工具或网络环境,使用下载管理器恢复中断下载;5.暂时关闭反病毒软件或防火墙,下载完成后重新启用。通过系统排查这些方面,即可解决问题。

See all articles