Page 1 of 1

ORDER BY RAND() + SHUFFLE

Posted: Mon Jan 13, 2003 3:30 am
by nologic
Hi All!

I'm a novice programmer with a very small knowledge of loops and arrays.
Maybe someone can help me clean up my code.

Goal: I have a table with the fields: image, link, imagetype, and description. There are ten different types of image-types defined by a value 1-10. For each image-type, there may be 5-20 images.

I want to select one random image(row) of each image-type in the table. Then, I want to shuffle the results so that the images are displayed in a random order too.

Here is my programming vomit :oops:
<?
// Connect to the database
mysql_connect ('localhost', 'name', 'password') ;
mysql_select_db (name');

// Edit this number to however many links you want displaying
$num_displayed = 1 ;

// Select random rows from the database
$result1 = mysql_query ("SELECT * FROM someimages WHERE (imagetype = 1) ORDER BY RAND() LIMIT $num_displayed");
$result2 = mysql_query ("SELECT * FROM someimages WHERE (imagetype = 2) ORDER BY RAND() LIMIT $num_displayed");
$result3 = mysql_query ("SELECT * FROM someimages WHERE (imagetype = 3) ORDER BY RAND() LIMIT $num_displayed");
$result4 = mysql_query ("SELECT * FROM someimages WHERE (imagetype = 4) ORDER BY RAND() LIMIT $num_displayed");
$result5 = mysql_query ("SELECT * FROM someimages WHERE (imagetype = 5) ORDER BY RAND() LIMIT $num_displayed");
$result6 = mysql_query ("SELECT * FROM someimages WHERE (imagetype = 6) ORDER BY RAND() LIMIT $num_displayed");
$result7 = mysql_query ("SELECT * FROM someimages WHERE (imagetype = 7) ORDER BY RAND() LIMIT $num_displayed");
$result8 = mysql_query ("SELECT * FROM someimages WHERE (imagetype = 8 ) ORDER BY RAND() LIMIT $num_displayed");
$result9 = mysql_query ("SELECT * FROM someimages WHERE (imagetype = 9) ORDER BY RAND() LIMIT $num_displayed");
$result10 = mysql_query ("SELECT * FROM someimages WHERE (imagetype = 10) ORDER BY RAND() LIMIT $num_displayed");

// For all the rows that you selected
$row1 = mysql_fetch_array($result1);
$row2 = mysql_fetch_array($result2);
$row3 = mysql_fetch_array($result3);
$row4 = mysql_fetch_array($result4);
$row5 = mysql_fetch_array($result5);
$row6 = mysql_fetch_array($result6);
$row7 = mysql_fetch_array($result7);
$row8 = mysql_fetch_array($result8);
$row9 = mysql_fetch_array($result9);
$row10 = mysql_fetch_array($result10);

// $placement = array ("$row1", "$row2", "$row3", "$row4", "$row5", "$row6", "$row7", "$row8", "$row9", "$row10");
$number = array ($row1, $row2, $row3, $row4, $row5, $row6, $row7, $row8, $row9, $row10);

srand ((float)microtime()*1000000);
shuffle ($number);

while (list (, $number) = each ($number)) {

// Display them to the screen...

?>
<a href="<? print $number["link"]; ?>"><img="http://www.foobar.com/images/<? print $number["image"]; ?>"></a>
<?

}
?>
I receive the following error:
Warning: Variable passed to each() is not an array or object in /foobar.com/httpdocs/test.php on line 39
I would really appreciate it if someone can help.

Posted: Mon Jan 13, 2003 3:36 am
by volka
there might be a more elegant way to solve this but anyway...
while (list (, $number) = each ($number)) {
you're assigning the single element to the same variable as the array. So it's no array anymore the second time the loop passes its condition header ;)

Posted: Mon Jan 13, 2003 4:35 am
by nologic
Thanks for your reply.

How about something like this for an elegant solution. It still does not work but the structure seems more elegant.

If someone could help me tweak it out, then you da bomb!

Code: Select all

<?
// Connect to the database
$hostName = "localhost";
$userName = "un";
$password = "pw";
$dbName = "name";

// make connection to database 
mysql_connect($hostName, $userName, $password) or die("Unable to connect to host $hostName");

mysql_select_db($dbName) or die("Unable to select database $dbName");

$image_number = range (1,10);

srand ((float)microtime()*1000000);
shuffle ($image_number);

// Define a function
function get_image($image_number)
&#123;
// Select the fields from the appropriate tables

// Edit this number to however many links you want displaying
$num_displayed = 1 ;

// Select random rows from the database
$result = mysql_query ("SELECT * FROM someimages WHERE (imagetype = $image_number) ORDER BY RAND() LIMIT $num_displayed");

for ($i=0; $i<$image_number; $i++) &#123;
     $link = mysql_result($result, $i, "link");
     $image = mysql_result($result, $i, "image");

// Display them to the screen...
?>
<a href="<? print "$link"; ?>"><img="http://www.foobar/images/<? print "$image"; ?>"></a>
<?
&#125;
&#125;
?>

Posted: Mon Jan 13, 2003 2:02 pm
by crazyjimsmith
Isnt there a problem with the shuffle and random functions. I know that when I tried to use them there were problems. When I checked the manual there was stuff about the functions not working properly.

They dont sort the array randomly.

Posted: Mon Jan 13, 2003 2:12 pm
by nologic
Shuffle works FINE on my server. I think they fixed it in the latest release of PHP.

Anyone got any suggestions for my code?

Posted: Mon Jan 13, 2003 2:17 pm
by glo-wurm
Yeah, the shuffle function doesn't seem to shuffle too well. I have used a shuffle function posted in the user comments on the shuffle documentation page though. Seems to work rather well. Here is the function...

Code: Select all

// Taken from user comments on http://www.php.net/manual/en/function.shuffle.php
// Fisher-Yates Shuffle an array in place (pass-by-reference) 
// Converted from "perldoc -q shuffle" 
function f_y_Shuffle(&$arr) &#123; 
	// Reverse a splice in an array (used by f_y_Shuffle() 
	function reverse_splice(&$splice, $i1, $i2) &#123; 
		if($i1>$i2) &#123; $swp = $i1; $i1 = $i2; $i2 = $swp; &#125; 
		for($k=$i2;$k>=$i1;$k--)&#123;$tmpArr&#1111;] = $splice&#1111;$k];&#125; 
		for($k=0;$k<count($tmpArr);$k++) &#123;$splice&#1111;$i1+$k] = $tmpArr&#1111;$k];&#125; 
	&#125; 

	$i = count($arr); 
	mt_srand((double)microtime()*1000000); 
	while($i>0) &#123; 
		--$i; 
		$j = @mt_rand(0, $i); 
		if($i!=$j) &#123; 
			reverse_splice($arr, $i, $j); 
		&#125; 
	&#125; 
&#125;

Posted: Mon Jan 13, 2003 4:32 pm
by nologic
I got an answer from member WHISK at another forum and SHUFFLE and ORDER BY RAND() works great! :D