简体   繁体   English

根据常见日期循环访问MySQL数据

[英]Loop through MySQL data based on common dates

I have a task that I've been racking my head around all day no avail. 我有一项任务,我整天都在绞尽脑汁无济于事。 I have a MySQL table that's set up as follows: 我有一个MySQL表,其设置如下:

CREATE TABLE `Shows` (
  `id` int(11) unsigned NOT NULL AUTO_INCREMENT,
  `band` varchar(255) NOT NULL,
  `month` int(2) NOT NULL,
  `day` int(2) NOT NULL,
  `year` int(4) NOT NULL,
  `venue` varchar(255) NOT NULL DEFAULT '',
  `city` varchar(255) NOT NULL DEFAULT '',
  `state` varchar(2) NOT NULL DEFAULT '',
  `timestamp` timestamp NOT NULL DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP,
  PRIMARY KEY (`id`)
)

Basically, it's a table to hold information about concerts. 基本上,它是一个保存音乐会信息的表格。 The month and day are stored numerically without leading zeros (eg February 3 would be represented as 2 in the month column and 3 in the day column). 月份和日期以数字方式存储而不带前导零(例如,2月3日将在月份列中表示为2,在日期列中表示为3)。

I'm creating an events calendar page that displays information about upcoming concerts. 我正在创建一个活动日历页面,显示有关即将举行的音乐会的信息。 I want to set it up so that it loops through each day that's equal to or after the current date so that no previous concerts show up on events that are supposed to be upcoming. 我想设置它以便它循环播放当前日期之前或之后的每一天,以便之前的音乐会不会显示应该即将发生的事件。

Here's the code I have so far: 这是我到目前为止的代码:

function displayUpcomingShows()
{   
    include "/path/to/config/file/that/contains/credentials";

    $con = mysql_connect($credentials);

    if (!$con)
    {
        die('Could not connect: ' . mysql_error());
    }

    mysql_select_db("database", $con);  

    $dateQuery = mysql_query("SELECT * FROM Shows GROUP BY month, day, year") or die(mysql_error());
    $todayMonth = date(n);
    $todayDate = date(j);
    $todayYear = date(Y);


    while ($info = mysql_fetch_array($dateQuery))
    {
        if ($todayMonth <= $info['month'] && $todayDate <= $info['day'] && $todayYear <= $info['year'])
        {
            $showDate = date("F j, Y", mktime(0, 0, 0, $info['month'], $info['day'], $info['year']));
            echo "<b><li>$showDate</li></b>";
            $concertDetails = $info['band'] . " @ " . $info['venue'] . " in " . $info['city'] . ", " . $info['state'];
            echo "<li>$concertDetails</li>";
        }
    }
    mysql_close($con);
}

This code works perfectly if there are 2 different dates. 如果有2个不同的日期,此代码可以正常工作。 That is, if the rows inserted into the table look like this: 也就是说,如果插入表中的行如下所示:

INSERT INTO `Shows` (`id`, `band`, `month`, `day`, `year`, `venue`, `city`, `state`, `timestamp`)
VALUES
(1,'Some Band',12,8,2011,'The Crocodile Cafe','Seattle','WA','2011-12-07 22:50:06'),
(2,'Some Other Band',12,15,2011,'Nectar Lounge','Seattle','WA','2011-12-07 15:17:39');

The web page displays: 网页显示:

December 8, 2011
Some Band @ The Crocodile Cafe in Seattle, WA

December 15, 2011
Some Other Band @ Nectar Lounge in Seattle, WA

Perfect, exactly what I wanted. 完美,正是我想要的。 BUT, if I change the first row so that the show is on the 15th as well, like so: 但是,如果我改变第一行,那么节目也在15日,如下:

(1,'Some Band',12,15,2011,'The Crocodile Cafe','Seattle','WA','2011-12-07 22:50:06')

The web page only prints this first entry and doesn't display the second entry (Some Other Band) at all, like this: 网页只打印第一个条目,并且根本不显示第二个条目(Some Other Band),如下所示:

December 15, 2011
Some Band @ The Crocodile Cafe in Seattle, WA

Can somebody point me in the right direction or explain what I'm doing wrong? 有人可以指出我正确的方向或解释我做错了什么? I've also tried structuring my query so that it selects the distinct dates only, loops through those using the same while loop and if statement in the code above, but then contains a new query inside the if statement that selects all information from the table where the month, day, and year match, then uses another while loops to print that data, but this causes the page to stop loading right when the function is called. 我也尝试构造我的查询,以便它只选择不同的日期,循环使用相同的while循环和if语句在上面的代码,但然后在if语句中包含一个新的查询,从表中选择所有信息其中月,日和年匹配,然后使用另一个while循环来打印该数据,但这会导致页面在调用函数时停止加载。 That code looks like this: 该代码如下所示:

function displayUpcomingShows()
{   
    (...same code as above up until here...)

    $dateQuery = mysql_query("SELECT DISTINCT month, day, year FROM Shows") or die(mysql_error());
    $todayMonth = date(n);
    $todayDate = date(j);
    $todayYear = date(Y);

    while ($info = mysql_fetch_array($dateQuery))
    {
        if ($todayMonth <= $info['month'] && $todayDate <= $info['day'] && $todayYear <= $info['year'])
        {
            $showDate = date("F j, Y", mktime(0, 0, 0, $info['month'], $info['day'], $info['year']));
            echo "<b><li>$showDate</li></b>";

            $detailsQuery = mysql_query("SELECT * FROM Shows WHERE month = $info['month'] AND day = $info['day'] AND year = $info['year']") or die(mysql_error());
            while ($concertInfo = mysql_fetch_array($detailsQuery)
            {
                    $concertDetails = $concerinfo['band'] . " @ " . $concertInfo['venue'] . " in " . $concertInfo['city'] . ", " . $concertInfo['state'];
                    echo "<li>$concertDetails</li>";
            }
        }
    }
    mysql_close($con);
}

Sorry if this particularly verbose, but I wanted to make sure I was as detailed as possible. 对不起,如果这特别冗长,但我想确保尽可能详细。 I'm making decent progress with learning PHP/MySQL more fluently, but I suppose that's why I'm still struggling. 我在学习PHP / MySQL的过程中取得了不错的进展,但我想这就是为什么我还在苦苦挣扎。

Cheers for any help. 欢呼任何帮助。

Easy update your query like so: 轻松更新您的查询,如下所示:

mysql_query("SELECT * FROM Shows WHERE timestamp >= '".date('Ymd H:i:s').'") or die(mysql_error()); mysql_query(“SELECT * FROM显示WHERE时间戳> ='”。日期('Ymd H:i:s')。'“)或死(mysql_error());

Get rid of: 摆脱:

$todayMonth = date(n); $ todayMonth = date(n); $todayDate = date(j); $ todayDate = date(j); $todayYear = date(Y); $ todayYear = date(Y);

And in your while loop get rid of the IF statement all together 并在你的while循环中一起摆脱IF语句

So your code will look like: 所以你的代码看起来像:

function displayUpcomingShows()
{   
    include "/path/to/config/file/that/contains/credentials";

    $con = mysql_connect($credentials);

    if (!$con)
    {
        die('Could not connect: ' . mysql_error());
    }

    mysql_select_db("database", $con);  

    $dateQuery = mysql_query("SELECT * FROM Shows WHERE timestamp >= '".date('Y-m-d H:i:s')."'") or die(mysql_error());


    while ($info = mysql_fetch_array($dateQuery))
    {
        $showDate = date("F j, Y", mktime(0, 0, 0, $info['month'], $info['day'], $info['year']));
        echo "<b><li>$showDate</li></b>";
        $concertDetails = $info['band'] . " @ " . $info['venue'] . " in " . $info['city'] . ", " . $info['state'];
        echo "<li>$concertDetails</li>";
    }
    mysql_close($con);
}

you have a parse error here 你在这里有一个解析错误

$detailsQuery = mysql_query("SELECT * FROM Shows WHERE month = $info['month'] AND day = $info['day'] AND year = $info['year']") or die(mysql_error());

it would need to be 它需要

$detailsQuery = mysql_query("SELECT * FROM Shows WHERE month = {$info['month']} AND day = {$info['day']} AND year = {$info['year']}") or die(mysql_error());

There's a lot of info on string if you want, although it might be hard to digest http://www.php.net/manual/en/language.types.string.php the examples should be a good reference though. 如果你想要的话,有很多关于字符串的信息,虽然它可能很难消化http://www.php.net/manual/en/language.types.string.php但这些例子应该是一个很好的参考。

do yourself a favor and turn on error reporting so php will tell you stuff like that. 帮自己一个忙,打开错误报告,这样php会告诉你这样的事情。 find your php.ini and make sure 找到你的php.ini并确保

display_errors = on
error_reporting = E_ALL

then restart the webserver to make sure changes take effect 然后重新启动Web服务器以确保更改生效

trying to code without being able to see detailed error messages is hellish. 试图编码而不能看到详细的错误消息是地狱般的。

The problem is with you select query 问题在于您选择查询

SELECT * FROM Shows GROUP BY month, day, year SELECT * FROM显示GROUP BY月,日,年

The GROUP BY is causing the problem. GROUP BY导致了这个问题。 Your basically asking the database to consolidate the data. 您基本上要求数据库合并数据。 The query sees two records but they are on the same day. 查询看到两条记录,但它们在同一天。 You asked to group records by day, so it won't show two records in a row that are on the same day. 您要求按天分组记录,因此它不会在同一天显示连续的两个记录。 Same thing happens with month and year. 月和年也发生同样的事情。 I think what you what to do is ORDER BY. 我觉得你要做的是ORDER BY。

You really should use something like phpMyAdmin to run your queries and get the bugs worked out before sticking it in your code. 你真的应该使用像phpMyAdmin之类的东西来运行你的查询并在你的代码中加入错误之前解决它们。

MySQL knows what day it is (CURRENT_DATE), so you can just ask the database for future shows without your code looking up today's date. MySQL知道它是哪一天(CURRENT_DATE),所以你可以向数据库询问未来的节目,而不需要你的代码查看今天的日期。 You can also ask it to format the date for you: 您也可以要求它为您格式化日期:

-- I prefer ANSI_QUOTES:  using "identifier" vs. `identifier`
-- and PIPES_AS_CONCAT:  a || b || c  vs.  CONCAT(a, b, c)

SET sql_mode='ANSI';

SELECT STR_TO_DATE("year"||','||"month"||','||"day", '%Y,%m,%d') AS showdate,
       band,
       venue,
       city,
       state
  FROM Shows
 WHERE "year" >= YEAR(CURRENT_DATE)
       AND
       "month" >= MONTH(CURRENT_DATE)
       AND
       "day" >= DAY(CURRENT_DATE);

Note that that query would be easier if you collapsed the broken-out date fields into a single column: 请注意,如果将分解的日期字段折叠为单个列,则查询会更容易:

...
"showdate" DATE NOT NULL,
...

Then you could simply SELECT showdate, ... FROM Shows WHERE showdate >= CURRENT_DATE 然后你可以简单地SELECT showdate, ... FROM Shows WHERE showdate >= CURRENT_DATE

Thanks for the all the help, everybody. 感谢所有人的帮助。 By piecing together some of your suggestions and correcting some of the mistakes I overlooked, I was at long last able to get my desired results using the following code: 通过拼凑你的一些建议并纠正我忽略的一些错误,我终于能够使用以下代码获得我想要的结果:

    $dateQuery = mysql_query("SELECT DISTINCT month, day, year FROM Shows") or die(mysql_error());
    $todayMonth = date(n);
    $todayDate = date(j);
    $todayYear = date(Y);

    while ($info = mysql_fetch_array($dateQuery))
    {
        if ($todayMonth <= $info['month'] && $todayDate <= $info['day'] && $todayYear <= $info['year'])
        {
            $showDate = date("F j, Y", mktime(0, 0, 0, $info['month'], $info['day'], $info['year']));
            echo "<b><li>$showDate</li></b>";

            $detailsQuery = mysql_query("SELECT * FROM Shows WHERE month = {$info['month']} AND day = {$info['day']} AND year = {$info['year']}") or die(mysql_error());
            while ($concertInfo = mysql_fetch_array($detailsQuery))
            {
                $concertDetails = $concertInfo['band'] . " @ " . $concertInfo['venue'] . " in " . $concertInfo['city'] . ", " . $concertInfo['state'];
                echo "<li>$concertDetails</li>";
            }
        }
    }

This successfully prints each unique date only once (the if loop) and subsequently prints each show associated with that date under it before moving on to the next date, like so: 这会成功打印每个唯一日期一次(if循环),然后打印与该日期相关的每个节目,然后再转到下一个日期,如下所示:

December 9, 2011
Some Band @ The Crocodile Cafe in Seattle, WA
Some Other Band @ Nectar Lounge in Seattle, WA

December 15, 2011
and so on and so forth

Cheers! 干杯!

Shaun 肖恩

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

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