2

This code works just fine, but i don't like the idea of a while loops within loops.

Is there another way with JOINS that will work more efficiently?

$region_results = mysql_query("SELECT id,region_name FROM regions WHERE page_id='$page_id' ORDER BY position ASC",$con_web) or die (mysql_error());
while($region_rows=mysql_fetch_array($region_results))
{
  $region_id=$region_rows["id"];
  $region_name=$region_rows["region_name"];

  echo "  <li>$region_name\n";
  echo "   <ul>\n";

  $block_results = mysql_query("SELECT id,block_name FROM blocks WHERE region_id='$region_id' ORDER BY position ASC",$con_web) or die (mysql_error());
  while($block_rows=mysql_fetch_array($block_results))
  {
    $block_id=$block_rows["id"];
    $block_name=$block_rows["block_name"];

    echo "    <li>$block_name\n";
    echo "     <ul>\n";

    $object_results = mysql_query("SELECT id,object_name FROM objects WHERE block_id='$block_id' ORDER BY position ASC",$con_web) or die (mysql_error());
    while($object_rows=mysql_fetch_array($object_results))
    {
      $object_id=$object_rows["id"];
      $object_name=$object_rows["object_name"];

      echo "      <li>$object_name</li>\n";
    }

    echo "     </ul>\n";
    echo "    </li>\n";
  }

  echo "   </ul>\n";
  echo "  </li>\n";
}

this code produces:

  <li>Left Content
   <ul> 
    <li>Block 1
     <ul> 
      <li>Object 1</li> 
     </ul> 
    </li> 
    <li>Block 2
     <ul> 
      <li>Object 1</li> 
     </ul> 
    </li> 
    <li>Block 3
     <ul> 
      <li>Object 1</li> 
     </ul> 
    </li> 
   </ul> 
  </li> 
  <li>Right Panel
   <ul> 
    <li>Block 1
     <ul> 
      <li>Object 1</li> 
      <li>Object 2</li> 
     </ul> 
    </li> 
   </ul> 
  </li> 

Thank you.

3 Answers 3

1
SELECT  b.id AS block_id, b.block_name, o.id, o.object_name
FROM    blocks b
JOIN    objects o
ON      o.block_id = b.id
WHERE   b.region_id = '$region_id'
ORDER BY
        b.position, b.id, o.position

Record the value of block_id and close/open the block tags whenever it changes.

Sign up to request clarification or add additional context in comments.

2 Comments

This is where i got stuck! how do echo out the results in a single fetch. so that it looks like my output example?
@Lewis: if ($prev_block_id != $rows["block_id"]) { close_and_open_block_tags(); }; @prev_block_id = $rows["block_id"];
0

It isn't so much the nested WHILE loops that is going to be an efficiency problem. I think your problem is more that you are making a lot of separate calls to the DB that might be more efficient if they were combined.

Try combining your queries into a single query using joins then loop through the rows detecting when the groupings change.

Comments

0

what is wrong with whiles within whiles? unless they are not guarantee to end, and if you could avoid them by querying just one time, I don't see any problem.

Maybe you should use a more high level API to do this job. That would be better for your code.

2 Comments

Performing SQL queries in a loop is a performance anti-pattern. How many database queries would it take if there are 20 regions, 10 blocks within each region and 10 objects within each block?
for sure (+1). That's why I would use a more high level API and concentrate in my business logic.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.