繁体   English   中英

PHP中非常简单的正则表达式问题

[英]Fairly simple regex question in PHP

好吧,我是regex doofus。 我只学过足够的知识,但是我想知道如何在不使用php三元运算符的情况下执行以下正则表达式。 另外它可能很难看,但是可以用...

'^". $date[0].(($date[0] == 0)?'?':'').$date[1]."[/.-]".$date[2].(($date[2] == 0)?'?':'').$date[3]."'";

如您所见,im使用三元运算符测试日期是否包含0。如果包含,则可以忽略,如果不包含则为1或2,请不要忽略。 我确定只有正则表达式可以写这种方法吗? 如果您知道怎么办,请告诉我,我将永远幸福。 另外,以防万一您想知道这是mysql查询中的正则表达式。

您在找这个吗? match [1]是月份,match [2]是日期,match [3]是年份

$regex = '#(0?[1-9]|1[0-2])[-/]([0-2]?[1-9]|3[01])[-/](19|20)?\d\d)#';

你这里有几个问题。

首先,永远不要将尚未确定格式正确的文本放入数据库。 日期存在于数据库中(带有和不带有0)的事实是一个问题。 为什么数据库中的日期时间字段中的日期不能确保格式正确?

其次,上述正则表达式仅在使用“ mm / dd / yyyy”日期的美国有效。 如果您绑定到该正则表达式,则不可能支持其他日期格式。

第三,为什么要在数据库中执行此操作? 您的示例是WHERE生日正则表达式……。这意味着您有此日期,然后再将其传递给mySQL。 因此,首先在PHP中修复日期:

$date = strtotime($_GET['date']);
$sql = "select blah From blah WHERE birthday = '$date' blah";

确实没有任何简单的方法可以简化此过程。 问题在于您正在构建一个正则表达式,无论如何都将强制您对零进行测试。 您最好用mktime将$ date转换为真实日期,然后在查询中使用它。

$date1 = mktime(0,0,0, substr($date, 0, 2), substr($date, 2, 2));
$sqlquery = "select * from table WHERE table_date == $date1";

for($i = 0; $i < 3; $i++) {
    $date[i] = preg_replace($date[i], '0', '');
}

那消失为零。

查看PHP文档,它有很多不错的功能。 www.php.net

我建议不要在生成正则表达式的单个语句中内置太多条件逻辑。 即使有一种方法可以将其实现为本地正则表达式,我也怀疑它是否更具可读性。 如果目标是使此片段更具可读性,我建议有条件地在不同的regex表达式之间进行选择,或有条件地在不同的步骤中构建各个部分,然后将它们缝合在一起。

JDany有一个更好的解决方案,但是您正在寻找的正则表达式是:

    Month         /            Day               /     Year
(0?[1-9]|1[0-2])[/-](0?[1-9]|[1-2][0-9]|3[0-1])[/-](19|20)?\d\d)

请注意,此正则表达式无法处理/验证以下情况:

  1. 月及其对应的天数(即28、30、31天)

  2. 闰年

到目前为止,使用正则表达式解决方案的反应良好。

这是另一种方法-使用本地PHP函数strtotime ()对字符串进行规范化。 这并不完美,但是当处理人们可能用作日期的多种格式时,正则表达式解决方案也不是。

这是我将如何开始对此进行攻击的方法:

<?php

// improve strtotime by eliminating dash ambiguity
function strtotimePlus($string) {
    $bads = array('-');
    $goods = array('/');
    return strtotime(str_replace($bads,$goods,$string));
}

// return date in fomat YYYY-MM-DD
function myDateFormat($timeformat) {
    return date("Y-m-d",$timeformat);
}

// convert free-form date string to YYYY-MM-DD
function betterDate($string) {
    return myDateFormat(strtotimePlus($string));

}

// samples from examples mentioned on the thread.
$dates = array();
$dates[] = "6/6/87";
$dates[] = "06/06/87";
$dates[] = "5.3.2001";
$dates[] = "5-2-82";
$dates[] = "1/1/83";

foreach($dates as $date) {
    print $date . " becomes " . betterDate($date) . "<br />";
}

输出:

6/6/87 becomes 1987-06-06
06/06/87 becomes 1987-06-06
5.3.2001 becomes 2001-03-05
5-2-82 becomes 1982-05-02
1/1/83 becomes 1983-01-01

谢谢大家的答案!

注意事项:
1)我没有设计这个数据库,也不想对它做任何大的改变。
2)我非常了解如何将字符串转换为日期,反之亦然以及所有爵士乐。
3)我想知道的是是否有一个正则表达式运算符/表达式可以消除中间的三元语句。

我意识到我不是很清楚。 数据库中有各种格式的生日文件,数据库很大。 我要在客户生日前两周从数据库中取出日期。
所以..! 我将当前日期加上14,就得到“ 17/06/09”,这是我需要对照数据库中2000多个日期进行检查的日期。 这个日期的格式很好。 我喜欢美好的事物。 特别是日期。 美好的约会。 无论如何....

我需要根据数据库中的Mash mash检查日期,而我知道根据数据库进行检查的唯一方法是
A)拉出每条记录,正确格式化糟糕的日期,然后对照我的进行检查(这是我正在做的...占用大量CPU)
B)在我的sql中有一个regex子句,并且仅检索符合我的规范的日期。

我的逻辑健全吗? 希望如此。 如果没有,请给我指出明显的地方,我会给你一些糖果*。




*假想糖果

并不是要因解决基本问题而心灰意冷,而是...

如果您现在具有所有这些不同的日期格式,在我看来,这意味着其他应用程序可以使用不同的格式,并且可以解析,理解或至少以字符串形式显示日期。 因此,作为字符串,使用此数据的其他应用程序可以以现在使用的任何形式接受它。

因此在我看来,如果所有日期数据都继续为字符串,但恰好全部都位于一种特定的布局中(例如国际YYYY-MM-DD),那么其他所有应用程序都将同样满意这种格式和其他格式一样,必须解析实际值的任何脚本(例如您的脚本)都可以更简单地实现。

因此,我的问题是,是否允许您擦洗并重新格式化字符串,使其保持字符串状态,以使它们看起来都一样? 我的意思是在工作之前运行清理作业(作为单独的维护任务,或者就在使用数据之前),该清理作业检查日期是否为您的格式,然后将其重新格式化并以字符串形式存储在数据库中如果不是,则为最佳格式。

关于您要在数据库中的日期之前两周找到目标的问题。 如果两个值都小于12,您怎么知道用户首先输入一天还是一个月? 对于1/5/06这样的日期,您如何知道用户是5月1日还是1月5日? 我认为您必须解决这个问题,或者至少要对此做出决定,然后再减去14天。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM