使用PHP按周分组和显示MySQL条目

时间:2010-01-10 03:06:25

标签: php mysql group-by

我正在建立一个有几个“单行”的网站。这些是使用简单的PHP5格式添加的,存储在MySQL 5数据库中。每行都有一个'id'(auto_increment),'title','description','status'(1或0)和'date_added'(MySQL datetime)。

我希望按月和年分组显示它们,如下所示:

<dl>
    <dt>August 2009</dt>
    <dd><strong>title 1</strong> - description 1</dd>
    <dd><strong>title 2</strong> - description 2</dd>
    <dd><strong>title 3</strong> - description 3</dd>         
    etc...
</dl>
    <dl>
    <dt>July 2009</dt>
    <dd><strong>title 1</strong> - description 1</dd>
    <dd><strong>title 2</strong> - description 2</dd>
    <dd><strong>title 3</strong> - description 3</dd>         
    etc...
</dl>

我发现了一个MySQL代码段,它表面上按月分组行,但查询只返回几个结果,而不是完整的表:

SELECT `title`, `description`, `date_added`
FROM one_liners WHERE `status`=1 GROUP BY MONTH(date_added)

我如何对它们进行分组,然后循环显示如上所示?

非常感谢任何帮助。

谢谢!

3 个答案:

答案 0 :(得分:2)

您不希望为此使用GROUP BY子句。虽然它“听起来”像你想要的,但它具有完全不同的含义。

运行普通查询:

SELECT `title`, `description`, `date_added` FROM one_liners 
WHERE `status`= 1 ORDER BY `date_added`

然后循环结果,做这样的事情:

$query = 'SELECT `title`, `description`, `date_added` FROM one_liners WHERE `status`= 1 ORDER BY `date_added`';
$res = mysql_query( $query );
$month = null;
$year  = null;

echo '<dl>';
while($row = mysql_fetch_assoc( $res ){
  $r_month = strtotime( $row['date_added'] );
  if($month != date('m', $r_month) || $year != date('Y', $r_month)){
     echo '<dt>' . date('F Y', $r_month) . '</dt>';
     $month = date('m', $r_month);
     $year  = date('Y', $r_month);
  }
  echo '<dd><strong>' . htmlentities( $row['title'] ) . '</strong> &mdash;' . htmlentities( $row['description'] ) . '</dd>';
}
echo '</dl>';

我特意选择只使用一个dl,因为dl应该包含多个dddt元素,而不是每个列表一对。如果您不同意,请随意根据需要调整我的代码:)

答案 1 :(得分:1)

我认为你需要单独用PHP做这件事。 SQL中的分组通常用于SUM,AVG,MAX,MIN,COUNT等内容。它对实际记录集没有任何作用,以显示您可以在PHP中访问的某种分组。

我在这种情况下所做的是在循环内跟踪的变量,以便知道何时到达新组。对于你的SQL你会做:

SELECT `title`, `description`, `date_added`
FROM one_liners WHERE `status`=1 ORDER BY MONTH date_added DESC

然后在PHP中你会做:

$prevMonth = '';
while ($row = mysql_fetch_assoc($result)) {
    $currMonth = $row['date_added'];
    if ($currMonth != $prevMonth) {
        if ($prevMonth != '') {
            echo '</dl>';
        }
        echo '<dl><dt>' . $currMonth . '</dt>';
        $prevMonth = $currMonth;
    }
    echo '<dd><strong>' . $row['title'] . '</strong>';
    echo ' - ' . $row['description'] . '</dd>';
}
if (mysql_num_rows($result) > 0) {
        echo '</dl>';
}

所有这一切都是在你循环时跟踪前一行的月份。当你到达一个新的时,它将关闭旧的DL并打开一个新的。

根据您在数据库中存储日期的方式(时间戳与日期时间),您需要将$currMonth = $row['date_added'];替换为相应的代码,以将其转换为“2009年8月”或任何您想要的格式。

答案 2 :(得分:0)

您不希望在那里使用GROUP BY,请尝试使用ORDER BY