PHP 2d Array loop - php

I have the following.
while($row = mysql_fetch_array($result))
{
$item = "itemCount_".$row['id'];
if ($_POST[$item] > 0)
{
$items2 = array( $i=> array($row['item'],$row['price']));
$i++;
echo $item." = ".$_POST[$item]." ".$i."<br>";
}
}
I would have thought that this would put each item in a array but it only puts the last item in the loop in. where is my fundamental flaw?

$items2 = array( $i=> array($row['item'],$row['price']));
That just keeps reassigning $items2 to a new array. Don't even worry about the $i counter and use
$items2[] = array($row['item'], $row['price']);
PHP Arrays

You're initializing a new array every time you go through the loop, it's better to use the array_push() function.

Related

PHP find double values in array and enumerate them

Hi I'm looking forward do find an easy solution to find and enumerate double values.
array("Papples", "Gelato", "Gelato", "Banana", "Papples","Papples")
to:
array("Papples", "Gelato", "Gelato2", "Banana", "Papples2","Papples3")
I could do it with a loop with if and write to second array procedure but isn't there a better solution for it?
Thank you!
you can try
<?php
$arr = array("Papples", "Gelato", "Gelato", "Banana", "Papples","Papples");
$countarray = array_count_values($arr);
$resultarray = array();
foreach ($countarray as $key=>$value) {
for ($i = 1; $i <= $value; $i++) {
$resultarray[]=$key.$i;
}
}
print_r($resultarray);
?>
Go with the loop and if, it's not difficult and will be pretty fast.
$delicatessen = [
"Papples", "Gelato", "Gelato", "Banana", "Papples","Papples"
];
foreach ($delicatessen as $e) {
if (#$counter[$e]++) $e .= $counter[$e];
$new[] = $e;
}
Basically what this does is to always add the element to the new array,
clearly, but modifying it or not. The condition is the $counter array
which will store the amount of times an item appears. All is created "on
the fly", PHP allows that.
When we retrieve $counter[$e] this element does not exist yet, so the
returned value makes the condition fail. However there is a side effect
that after the undef is returned, it will be increased (with ++) so
now $counter[$e] will be 1.
If on a future iteration this is accessed again the returned value of
1 will make the condition pass, with the side affect that at the point
the if statement is executed $counter[$e] will already be 2. The
statement concatenated this number to the end of the element.
This way, in the first time nothing is concatenated but there is the
side effect. On next iterations the number is concatenated to the
element.
The # operator is used here to suppress PHP notices. Since you're
dealing with undefined elements on first pass, you would get notices.
Script wouldn't break though. Of course this operator should be used
with caution, but in this case it just really helps simplifying code,
making it less strict.
$arr = array("Papples", "Gelato", "Gelato", "Banana", "Papples","Papples");
$arr_count = array_count_values($arr);
$new_arr = array();
foreach($arr_count as $key=>$val){
if($val > 1){
$k = 1;
for($i=0; $i<$val; $i++){
if($i==0){
$new_arr[] = $key;
}else{
$new_arr[] = $key.++$k;
}
}
}else{
$new_arr[] = $key;
}
}
echo "<pre>"; print_r($new_arr);
Test script: https://3v4l.org/iGf1s

PHP Array into array

I've had a look through searches but there are so many differently worded question that I'm not sure which I should be looking for. Nor can I think how to word this to the best of my ability, but here goes:
I would like to take a mysqli_fetch_assoc() result and create an array for each row.
Let's say the result had two rows:
[0][0] = Cheese
[0][1] = 1
[1][0] = Milk
[1][1] = 2
How can I drop those into a newly created array let's say called $items?
What I'm hoping to achieve is:
$items = array(
array("Cheese",1),
array("Milk", 2)
);
The only code I have so far is this:
if($row = mysqli_fetch_assoc($q)) {
for($i=0;$i<$total;$i++) {
$items[$i][] = $row[$i];
}
}
I have not tried this, but I have this very unsettling feeling that it definitely won't be working.
would this not do it?
if($row = mysqli_fetch_assoc($q)) {
foreach($row as $r) {
$items[] = $r;
}
}
$new_arr = array();
while ($row = mysql_fetch_assoc($q))
{
foreach($row as $value){
$new_arr[][$value[0]] = $value[1];
}
}
I think this is what you need
while ($row = mysql_fetch_assoc($q))
{
$arr = [];
foreach ($row as $value)
$arr[] = $value;
$items[] = $arr;
}
var_dump($items);
mysqli_result::fetch_all()
"Returns an array of associative or numeric arrays holding result rows"
I think you're thinking too hard. A two dimensional array is already an array containing arrays. In your case, the result of fetch_all is precisely an array containing 'an array for each row'
If you're not intending to store the whole result set then you can do:
$rows[] = Array();
while ($row = mysqli_fetch_row() && $someCondition) $rows[] = $row;
but really you'd be better off to put a LIMIT on the query if possible.

Make a while loop when the array is empty?

I have code that will make an array or arrays of UNKNOWN length because it depends on how many new people have been added to the mysql DB. (this is where I'm getting confused)
The array has $x items, each item is an array of first name, last name, and e-mail address.
I want the loop to run till the array is ended.
$x = 0;
while($array[$x]['per_LastName'] != 'NULL') {
$batch[] = array('EMAIL'=>$array[$x]['per_Email'], 'FNAME'=>$array[$x]['per_FirstName'], 'LNAME'=>$array[$x]['per_LastName']);
$x = $x+1;
}
apparently I'm looping infinity because it uses all the memory.
Use a foreach loop which will loop through all elements of the array.
foreach($array as $key => $value) {
$batch[] = array('EMAIL'=>$value['per_Email'], 'FNAME'=>$value['per_FirstName'], 'LNAME'=>$value['per_LastName']);
}
Instead you should use a for loop
for($x = 0; $x<count($array); $x++){
$batch[] = array('EMAIL'=>$array[$x]['per_Email'], 'FNAME'=>$array[$x]['per_FirstName'], 'LNAME'=>$array[$x]['per_LastName']);
}
why not use foreach and avoid counters and unnecessary checks?
foreach($array as $eachArray)
{
$batch[] = array('EMAIL'=>$eachArray['per_Email'], 'FNAME'=>$eachArray['per_FirstName'], 'LNAME'=>$eachArray['per_LastName']);
}

how to skip elements in foreach loop

I want to skip some records in a foreach loop.
For example, there are 68 records in the loop. How can I skip 20 records and start from record #21?
Five solutions come to mind:
Double addressing via array_keys
The problem with for loops is that the keys may be strings or not continues numbers therefore you must use "double addressing" (or "table lookup", call it whatever you want) and access the array via an array of it's keys.
// Initialize 25 items
$array = range( 1, 25, 1);
// You need to get array keys because it may be associative array
// Or it it will contain keys 0,1,2,5,6...
// If you have indexes staring from zero and continuous (eg. from db->fetch_all)
// you can just omit this
$keys = array_keys($array);
for( $i = 21; $i < 25; $i++){
echo $array[ $keys[ $i]] . "\n";
// echo $array[$i] . "\n"; // with continuous numeric keys
}
Skipping records with foreach
I don't believe that this is a good way to do this (except the case that you have LARGE arrays and slicing it or generating array of keys would use large amount of memory, which 68 is definitively not), but maybe it'll work: :)
$i = 0;
foreach( $array as $key => $item){
if( $i++ < 21){
continue;
}
echo $item . "\n";
}
Using array slice to get sub part or array
Just get piece of array and use it in normal foreach loop.
$sub = array_slice( $array, 21, null, true);
foreach( $sub as $key => $item){
echo $item . "\n";
}
Using next()
If you could set up internal array pointer to 21 (let's say in previous foreach loop with break inside, $array[21] doesn't work, I've checked :P) you could do this (won't work if data in array === false):
while( ($row = next( $array)) !== false){
echo $row;
}
btw: I like hakre's answer most.
Using ArrayIterator
Probably studying documentation is the best comment for this one.
// Initialize array iterator
$obj = new ArrayIterator( $array);
$obj->seek(21); // Set to right position
while( $obj->valid()){ // Whether we do have valid offset right now
echo $obj->current() . "\n";
$obj->next(); // Switch to next object
}
$i = 0;
foreach ($query)
{
if ($i++ < 20) continue;
/* php code to execute if record 21+ */
}
if want to skipped some index then make an array with skipped index and check by in_array function inside the foreach loop if match then it will be skip.
Example:
//you have an array like that
$data = array(
'1' => 'Hello world',
'2' => 'Hello world2',
'3' => 'Hello world3',
'4' => 'Hello world4',
'5' => 'Hello world5',// you want to skip this
'6' => 'Hello world6',// you want to skip this
'7' => 'Hello world7',
'8' => 'Hello world8',
'9' => 'Hello world8',
'10' => 'Hello world8',//you want to skip this
);
//Ok Now wi make an array which contain the index wich have to skipped
$skipped = array('5', '6', '10');
foreach($data as $key => $value){
if(in_array($key, $skipped)){
continue;
}
//do your stuf
}
You have not told what "records" actually is, so as I don't know, I assume there is a RecordIterator available (if not, it is likely that there is some other fitting iterator available):
$recordsIterator = new RecordIterator($records);
$limited = new LimitIterator($recordsIterator, 20);
foreach($limited as $record)
{
...
}
The answer here is to use foreach with a LimitIterator.
See as well: How to start a foreach loop at a specific index in PHP
I'm not sure why you would be using a foreach for this goal, and without your code it's hard to say whether this is the best approach. But, assuming there is a good reason to use it, here's the smallest version I can think of off the top of my head:
$count = 0;
foreach( $someArray as $index => $value ){
if( $count++ < 20 ){
continue;
}
// rest of foreach loop goes here
}
The continue causes the foreach to skip back to the beginning and move on to the next element in the array. It's extremely useful for disregarding parts of an array which you don't want to be processed in a foreach loop.
for($i = 20; $i <= 68; $i++){
//do stuff
}
This is better than a foreach loop because it only loops over the elements you want.
Ask if you have any questions
array.forEach(function(element,index){
if(index >= 21){
//Do Something
}
});
Element would be the current value of index.
Index increases with each turn through the loop.
IE 0,1,2,3,4,5;
array[index];

Define 2D array with loops in php

I have an array $rows where each element is a row of 15 tab-delimited values. I want to explode $rows into a 2D array $rowData where each row is an array element and each tab-delimited value is assigned to a different array element. I've tried these two methods without success. I know the first one has a coding error but I do not know how to correct it. Any help would be amazing.
for ($i=0; $i<count($rows); $i++){
for ($j=0; $j<15; $j++){
$rowData = array([$i] => array (explode(" ", $rows[$j])));
}
}
foreach ($rows as $value){
$rowData = array( array (explode(" ", $rows[$value])));
}
$rowData = array();
foreach($rows as $value) {
$rowData[] = explode("\t", $value);
}
for ($j=0; $j<15; $j++) {
$rowData[$j] = explode("\t", $rows[$j]);
}
To expand: The problem with the following code:
$rowData = array([$i] => array (explode(" ", $rows[$j])));
is that you don't appear to know what the different things you've written mean precisely.
A call to array() returns a new array with the indicated elements. So array (explode(" ", $rows[$j])) yields an array with a single element, namely the array returned by explode(). And you're wrapping that in another call to array(), specifying the loop variable $i as the key corresponding to that element. Also, you're using the assignment symbol =, which means that every time you go through the loop, $rowData is being completely overwritten - what you wanted was to add new elements to it without getting rid of the old ones.

Categories