Loop through mysqli results array once to get all information - php

I am querying the database for data, but in order to do what I need, I end up looping through that results array at least three times. How do I get all of the info I need out of the array without having to loop so many times? I need to get data from the array based on the results from the previous loops. The code below is the only way I could figure out in order to only query the database once.
$recordSQL = mysqli_query($link, $sqlString);
$resultMonths = array();
while($recordResult = mysqli_fetch_assoc($recordSQL)) $resultMonths[] = $recordResult['date'];
mysqli_data_seek($recordSQL, 0);
$uniqueMonths = array_unique($resultMonths);
foreach($uniqueMonths as $key => $date){
echo '</div><div class="current-month">'.translateDate($date, '').'</div>';
$resultCompanies = array();
while($companyResult = mysqli_fetch_assoc($recordSQL)){
if($companyResult['date'] == $date) $resultCompanies[] = $companyResult['company'];
}
mysqli_data_seek($recordSQL, 0);
$uniqueCompanies = array_unique($resultCompanies);
$oldco = '';
foreach($uniqueCompanies as $key => $company){
$x = 0;
while($typeResult = mysqli_fetch_assoc($recordSQL)){
if($typeResult['date'] == $date && $typeResult['company'] == $company){
if($oldco != $typeResult['company']){
if($x != 0) echo '</div>';
echo '<div class="company-record">'.$typeResult['name'].' - ';
}
if($x > 0) echo ', ';
echo translateID('Type', $typeResult['type']).'('.translateID('Section', $typeResult['section']).')';
$oldco = $typeResult['company'];
$x++;
}
}
echo '</div>';
mysqli_data_seek($recordSQL, 0);
}
}

FYI, you are actually looping N**3 times. Do it this way:
$month_company_rows = array();
while ($row = mysqli_fetch_assoc($recordSQL)) {
$month_company_rows[$row['date']][$row['company']][] = $row;
}
foreach ($month_company_rows as $date => $company_rows) {
echo '</div><div class="current-month">'.translateDate($date, '').'</div>';
foreach ($company_rows as $company => $rows) {
echo '<div class="company-record">'.$company.' - ';
foreach ($rows as $x => $row) {
if($x > 0) echo ', ';
echo translateID('Type', $row['type']).'('.translateID('Section', $row['section']).')';
}
echo '</div>';
}
}

Related

Warp two row with a class after query

I want to warp every two row with a class. So I saw some guideline from here and googling and found foreach array_chunk to do this. And I tried as below which can't display any result. Without foreach its work well. Were is my wrong here please?
In the above picture that I want to do; my every two category warp with a class. And add a divider after each top category.
Here is my tried:
echo '<ul class="dropdown-menu dropdown-menu-large row">';
$sql = "SELECT id,name FROM main_cata ORDER BY id ASC";
$execute = $dbh->query("$sql");
$rowcount = $execute->num_rows ;
$row = $dbh->query($sql) ;
while ($row = $execute->fetch_assoc()) {
foreach (array_chunk($row, 2, true) as $array){
echo'<li class="col-sm-3">';
foreach($array as $rows){
echo '<ul><li class="dropdown-header">'.$rows->name.'</li>';
$sql2 = "SELECT id,name,page FROM catagory WHERE m_cata = '".$rows->id."' ORDER BY id ASC";
$execute2 = $dbh->query("$sql2");
$rowcount2 = $execute2->num_rows ;
$row = $dbh->query($sql) ;
while ($row = $execute2->fetch_assoc()) {
$cid = $row['id'];
$cname = $row['name'];
$page = $row['page'];
echo '<li>'.$cname.'</li>';
}
echo '<li class="divider"></li></ul>';
}
echo '</li>';
}
}
echo '</ul>';
while ($row = $execute->fetch_assoc()) {
fetch_assoc returns 1 row (id, name) from the query, then you are using the result and spliting in 2 (https://secure.php.net/manual/pt_BR/mysqli-result.fetch-assoc.php), What you can do is, make a counter instead of the array chunk that resets every time it reachs 2.
foreach (array_chunk($row, 2, true) as $array){
The content of $row is, for example, array('id' => 1, 'name' => 'Category 1').
foreach($array as $rows){
You are iterating again without needing to.
A simple version:
counter = 0;
echo "<ul>";
while (row = execute->fetch_assoc()) {
if (counter == 0) {
echo "init li";
}
echo "subinit li";
get subcategories
while (row2 = execute2->fetch_assoc()) {
print content
}
echo "subend li";
if (counter == 2) {
counter == 0;
echo "end li";
} else {
counter++;
echo "divider";
}
}
echo "</ul>";

Crawling with PHP and XPATH

I'm crawling a page because I want to show it on our website. I have a problem with getting the link on each team though. I get the team name, but I cant get the href attribute.
My code looks like this:
elements = $xpath->query("//table/tr[contains(#class,'sr')]/td[contains(#class,'c')]");
$count = 0;
foreach ($elements as $elt) {
if($count == 0)
{
$stringInsert = utf8_decode($elt->textContent);
}
else if($count == 1)
{
// tries to echo the href here, but dont get it.
echo $elt->getAttribute('href')
$stringInsert .= ", '".trim(utf8_decode($elt->textContent))."'";
}
else if($count == 3)
{
$stringInsert .= ", ".utf8_decode($elt->textContent);
}
else if($count == 4)
{
$stringInsert .= ", ".utf8_decode($elt->textContent);
}
else if($count == 5)
{
$stringInsert .= ", ".utf8_decode($elt->textContent);
}
else if($count == 6)
{
$stringInsert .= ", ".utf8_decode($elt->textContent);
}
else if($count == 7)
{
$stringInsert .= ", ".utf8_decode($elt->textContent);
}
else if($count == 9)
{
$stringInsert .= ", ".utf8_decode($elt->textContent);
}
else if($count == 10)
{
$stringInsert .= ", ".utf8_decode($elt->textContent);
}
$count++;
if($count == 12)
{
echo $stringInsert;
$count = 0;
}
}
As you can see in the code, i try to echo the $elt->getAttribute('href') in count == 1, but it does not show anything.
I have tried to add a /a to the xpath conditions, but then it only gets the Team name and not all the other stuff like, score, point and etc.
You seem to query for the td Elements, which won't have an attribute href.
May this example is helpful:
//array to store the results
$res = array();
//loop over all <tr> elements of the table.srPoolPosition
foreach ($path->query("//table[contains(#class,'srPoolPosition')]/tr") as $row) {
//new array to store results in each row
$rowRes = array();
//get the <td> elements in current <tr>
$fields = $path->query('td', $row);
//skip if not 12 fields
if ($fields->length < 12) {
continue;
}
//loop over those
foreach ($fields as $field) {
//store the textcontent in the current rows array
$rowRes[] = utf8_decode($field->textContent);
}
//query for the link in the current row
$link = $path->query("a", $row)->item(0)->getAttribute('href');
//add the link to the results array
rowRes[] = $link;
//then add it to the results
$res[] = $rowRes;
}
//example loop over the results
foreach ($res as $tableRow) {
echo sprintf(
'%s: %s - %s<br>',
$tableRow[13], //link href
$tableRow[1], //name
$tableRow[7], //score 1
$tableRow[9] //score 2
);
}

How to show the value of two related arrays in php?

I have two arrays myarray1 has name of images and myarray2 has the address of images,
I am going to show image names and their addresses in pagination but do not know how to complete the code.
$pages = array_chunk($myarray1,10);
$addrs = array_chunk($myarray2,10);
$page_number = 1
$count = 0;
echo'<table>';
echo'<tr>';
foreach ($pages[$page_number] as $i) {
$counter++;
if ($count == 5) {
echo '</tr><tr>';
$counter = 0;
}
echo'<td>'.$i. " AND " . <<Value of addrs array goes here
echo'</td>';
}
.......
I'll do it on this way
$count = 1;
foreach ($pages[$page_number] as $key => $i) {
if ($count % 5 == 0) {
echo '</tr><tr>';
echo '</div>';
echo '</div>';
}
echo'<td>'.$i. " AND " . $addrs[$page_number][$key]
echo'</td>';
$count++; // increase at the end.
}
if you can try to var_dump those arrays before foreach just to be clear how structure looks like.
Try something like this: (note also the counter++ is changed in $count++)
foreach ($pages[$page_number] as $key => $i) {
$count++;
if ($count == 5) {
echo '</tr><tr>';
echo '</div>';
echo '</div>';
$count = 0;
}
echo'<td>'.$i. " AND " . $addrs[$page_number][$key]
echo'</td>';
}

Using DOM to get dynamic table data but not following tables sort

I've got a table that is default sorted ascendingly by its 2nd column by numeric value.
I'm trying to grab the top 5 rows from this table, but my script doesn't seem to want to follow the tablesorter forced sort order I have, it's just taking the default non sorted data.
So how do I get my script to grab the sorted table data? I don't want to have to grab all the data and sort it again for this script.
here is my code
<?php
include("bestbrokers_array.php");
require('simple_html_dom.php');
$table = array();
$html = file_get_html('http://www.forexfbi.com/best-forex-brokers-comparison/');
$num=1;
foreach($html->find('tr') as $row) {
if($num <= 6)
{
$rating = $row->find('td',1)->innertext;
$name = $row->find('td',0)->plaintext;
$table[$name][$rating] = true;
$num++;
}
}
html_show_array($table);
?>
and..
<?php
function do_offset($level){
$offset = ""; // offset for subarry
for ($i=1; $i<$level;$i++){
$offset = $offset . "<td></td>";
}
return $offset;
}
function show_array($array, $level, $sub){
if (is_array($array) == 1){ // check if input is an array
foreach($array as $key_val => $value) {
$offset = "";
if (is_array($value) == 1){ // array is multidimensional
echo "<tr>";
$offset = do_offset($level);
echo $offset . "<td>" . $key_val . "</td>";
show_array($value, $level+1, 1);
}
else{ // (sub)array is not multidim
if ($sub != 1){ // first entry for subarray
echo "<tr nosub>";
$offset = do_offset($level);
}
$sub = 0;
echo $offset . "<td main ".$sub." width=\"120\">" . $key_val .
"</td>";
echo "</tr>\n";
}
} //foreach $array
}
else{ // argument $array is not an array
return;
}
}
function html_show_array($array){
echo "<table cellspacing=\"0\" border=\"2\">\n";
show_array($array, 1, 0);
echo "</table>\n";
}
?>

php mysql_fetch_array every 25 items wrap a div

I want to mysql_fetch_array 100 items from mysql database. then every 25 items wrap a div.
also, I make a total items result check.
My code as below, but it will add <div> to every item, no as my require. So how to make it easier? Thanks.
if (mysql_num_rows($result) != 0) {
$total = mysql_num_rows($result);
$num = 1;
while ($row = mysql_fetch_array($result)) {
if ($num === 1) {
echo '<div>';
}
echo $row['title'] . '<br />';
if ($total < 26) {
echo '</div>';
}
else {
if ($num === 26) {
echo '<div>';
}
if ($total < 51) {
echo '</div>';
}
else {
if ($num === 51) {
echo '<div>';
}
if ($total < 76) {
echo '</div>';
}
else {
if ($num === 75) {
echo '<div>';
}
if ($total < 101) {
echo '</div>';
}
}
}
}
$num++;
}
}
You can use the mod operator.
See: http://php.net/manual/en/internals2.opcodes.mod.php
echo '<div>';
while($row = mysql_fetch_array($result)){
....
if (($num % 25) === 1) { echo '</div><div>' }
$num++;
}
echo '</div>';
Try This...
if(mysql_num_rows($result)!=0){
$total = mysql_num_rows($result);
$num=1;
while($row = mysql_fetch_array($result)){
if($num===1)
echo '<div>';
echo $row['title'].'<br />';
if($num==25){
echo '</div>';
$num=1;
}
$num++;
}
}
use the mod operator.
$num =1;
while($row = mysql_fetch_array($result)){
if (($num % 25) === 1) { echo '<div>' }
-------here data ----
if (($num % 25) === 0) { echo '</div>' }
$num++;
}
My advice is to separate your concerns... Give it a shot more like this:
// first get all your data.
$results = array();
while($row = mysql_fetch_array($result)){
$results[] = $row;
}
// now you have an array of all of your records.
if (!empty($results)) {
// total count of the array up front.
$total = count($results);
$interval = 0;
// save the data in a buffer for echoing later.
$buffer = array('<div>');
foreach($results as $row) {
$buffer[] = $row['title'] . '<br />';
if (++$interval === 24) { // notice the prefix ++
$interval = 0;
// close and re-open divs
$buffer[] = '</div><div>';
}
}
// one final close tag
$buffer[] = '</div>';
// now we zip it up and echo the content.
echo implode('', $buffer);
}
Here is how I do it...
$count = 0;
while($row = mysql_fetch_array($result)){
if ($count%$25 == 0)
{
echo "<div>";
}
//whatever your data goes here
count++
if ($count%$25 == 0)
{
echo "</div>";
}
}

Categories