views:

79

answers:

5

I don't know PHP very well, so please bear with me.

My client has a database with information and one of the fields is ff_date_time in the format "Tue Oct 5 14:43:10 2010". There are a lot of entries in here and I need to display a list of just the days that have entries: ie,

  • Tue Oct 5, 2010
  • Thurs Oct 7, 2010
and so on. There may be hundreds of entries on a certain day, so obviously when I pull in dates from the db I need to go through and extract the right data and filter it. Here's what I have so far:

$query = "SELECT ff_date_time FROM booth_submit"; 
$query_result = mysql_query($query);
$datetimes = array();
$dates = array();

while ($row = mysql_fetch_array($query_result)) {
  $datetimes[] = $row['ff_date_time'];
}

for ($i = 0; $i < sizeOf($datetimes); $i++) {
  $temp = explode(" ", $datetimes[$i]);
  $dates[] = ($temp[0]." ".$temp[1]." ".$temp[2]." ".$temp[4]);  # Breaks date_time into 'Mon Oct 5 2010' format
}

$dates = array_unique($dates);                      
for ($i = 0; $i < sizeOf($dates); $i++) {
  echo('<a href="#">'.$dates[$i].'</a><br />'); 
}

I'm doing a similar thing for two others fields that work fine, but for some reason, this always yields a $dates array that is the right length (ie: 4 unique dates, array is size 4), but only the first $dates element has any info. The output looks like this:

<a href="#">Mon Oct 3 2010</a><br />
<a href="#"></a><br />
<a href="#"></a><br />
<a href="#"></a><br />

When I don't use array_unique and just test values to check if everything is getting loaded and parsed correctly, the array is just as it should be ("Mon Oct 3 2010","Mon Oct 3 2010","Mon Oct 3 2010","Mon Oct 4 2010","Mon Oct 5 2010","Mon Oct 5 2010","Mon Oct 6 2010").

Any clues what's going wrong here?

A: 

How about instead of treating the symptom, you remove the cause.

Add GROUP BY ff_date_time to the end of your query, or wrap DISTINCT() around ff_date_time in the select. Then you'll only get unique dates in your sql result.

edit: ok, assuming that ff_date_time is actually a datetime field, then in order to ignore time of day, make that GROUP BY DATE(ff_date_time) which will use only the day part and not the time part. If it's not a datetime field, and just a string, you will have to do substring functions, or use someone else's answer.

Tesserex
Looks like he trims the time off the datetime stamp, so a GROUP BY would still return multiple results for the same date. But maybe taking a substring of the ff_date_time might work in conjunction with the GROUP BY
Phill Pafford
Might not be the expected result since in the DB there is a part that contains the time which is removed in his PHP code
slosd
+1  A: 

What is the output of var_dump($dates) after you used array_unique?

Try foreach instead of a for loop:

foreach($dates as $date) {
  echo('<a href="#">'.$date.'</a><br />'); 
}
slosd
+2  A: 

array_unique preserves the keys so your resulting array has elements [0], [4] and [6].

I suggest using

foreach  ($dates as $date) {
  echo('<a href="#">'.$date.'</a><br />'); 
}
Colin Fine
This worked perfectly. I didn't know that the key was preserved. I was thinking it was more like ruby's .uniq!. Thanks!
Bradley Herman
I find I hardly ever use 'for' in PHP - I nearly always use 'foreach'.
Colin Fine
+1  A: 

I would rather recommend you another approach. Using the built-in datetime functions.

$all_dates = array();
foreach($datetimes as $date) {
  $all_dates[] = date('D M j Y', strtotime($date));
}

$unique = array_unique($all_dates);
mhitza
his solution is almost 10 times faster. Why call date and strtotime for such a simple task?
slosd
@slosd provide a benchmark to your affirmation if you want me to believe you. And as a second point, I recommended my approach because it is easier to maintain, and that is the most important aspect. While it may be easy to understand now what holds each value of the array resulted after the `explode` function. It is strictly dependent of context. Returning at a later time, you will have to make a database query to actually see the raw format of the date, necessary to understand the code again.
mhitza
This would be a good situation to use comments to clarify what the data from the DB looks like ;) - Here is the script I tested: http://dev.freedig.org/files/date.php - On my webserver the date/strtotime version is even slower (15 times)
slosd
Touché. But I still wouldn't sacrifice the code readability for that improvement. As far as code commenting goes, I rather not comment trivial tasks; but that is a personal preference.
mhitza
+1  A: 

Assign the unique array to another array variable. And use foreach.

$newarr = array();
$newarr = array_unique($dates);
foreach ($newarr as $date) {
  echo('<a href="#">'.$date.'</a><br />' . "\n"); 
}
Ruel