2

我正在尝试构建一个简单的 sql 语句:

    // build sql statement          
    $sql = "select * from some_tbl where "; 
    if(strlen($mydetails['city']) > 0) { 
        $sql .= "cityname in (".$mydetails['city'].") and "; 
    } 
    $sql .= 'fromdate <= expirydate and expirydate >= curdate() order by rand()';

但是 $sql 缺少 < 和 > 之间的所有内容。调试器将 $sql 的值显示为:

    select * from tbl_adsinfo where fromdate = curdate() order by rand()

这是非常基本的,我只是迷路了。我不认为 < 或 > 是特殊字符,对吧?我尝试转义它们并改用双引号,但结果是一样的。

这是怎么回事?

4

4 回答 4

1

您不会碰巧通过 striptags() 函数运行 $sql 变量,对吗?这与去掉“<= expirydate and expirydate >”是一致的,因为它假定它是一个 HTML 标记。

于 2011-01-11T20:08:48.080 回答
0

我不确定是什么导致了问题。显然,作为一种安全措施,可能有一些东西会剥离 html 标记。一种建议是尝试将 '<' 和 '>' 替换为它们的 ASCII 代码:

 $sql .= 'fromdate '.chr(60).'= expirydate and expirydate '.chr(62).'= curdate() order by rand()';

编辑:您也可以使用 NOT BETWEEN 语句,如下所示:

 $sql .= '(expirydate NOT BETWEEN fromdate AND curdate()) AND (expirydate NOT BETWEEN fromdate AND 17530101) ORDER BY rand()

17530101 意味着可能是日期时间的最小值。在前面的代码中,您正在检查 expirydate 是否不在 fromdate 和 curdate() 之间,并且 expirydate 不小于其中任何一个。这意味着 expirydate 应该大于 fromdate,curdate 以使语句返回 true,这就是您要实现的目标。

于 2011-01-11T19:12:44.800 回答
0

为什么不使用BETWEEN运算符?

$sql .= 'expirydate BETWEEN fromdate AND curdate() ORDER BY rand()';

编辑:

仔细查看你也需要等号,尝试拆分操作

$sql .= 'fromdate <= expirydate and expirydate >= curdate() order by rand()';

到:

$sql .= 'expirydate >= curdate() ';
$sql .= 'AND fromdate <= expirydate ';
$sql .= 'ORDER BY rand()';

或者颠倒操作符的顺序:先做=

$sql .= 'AND fromdate =< expirydate ';
$sql .= 'ORDER BY rand()';
于 2011-01-11T19:27:42.910 回答
0

好,我知道了。问题与 PHP 无关,而是 Zend Studio 和/或 XDebugger。

让 Zend 使用调试器花了我几天的时间,而且我确信它可能并不完全符合我让它运行的方式。

如果您在 Zend Studio 中调试时将鼠标悬停在一个变量上,则会弹出一个小窗口来显示该变量的内容(有时)。这个窗口确实切断了“<”之后的任何内容。该变量仍然包含正确的字符串,但 IDE/Debugger 非常具有误导性。不幸的是,由于这个特定的字符是一个常见的问题,因为 html 解析这是一个很难识别的令人困惑的错误。如果您尝试比较 php 页面的输出,或者您正在查看非常长的输出(对于非常长的字符串,您似乎只能在调试变量窗口中看到 1024 个字符,因此字符串可能会被截断),问题会变得更加复杂。

遗憾的是,这仍然是迄今为止我为 PHP 提出的最好的 IDE。

于 2011-03-17T15:25:02.933 回答