Duplicate the if result in foreach - php

In short, I'm downloading from the category_id, product_id, and active activity tag. The idea is that like all products assigned to a particular category_id have a value of 0, I display the echo "empty", otherwise "products contains", but the foreach loop instead passes through the product id and displays empty + category_id once, passes through $ status and displays So many echo, how many records are active.
The query is ok - I know I should not perform logical operations on arrays, but the database is structured so that I have no output.
$result = array();
foreach ($products as $detail) {
$cid = $detail['category_id'];
$pid = $detail['product_id'];
$status = $detail['active'];
$result[$cid][$pid] = $status;
$multiplier = $result[$cid][$pid];
$counter = count($result[$cid]);
$multiplier2 = 1;
$multiplier = $multiplier * $multiplier2;
echo '$status: ' .$multiplier. " | ";
if ($multiplier == 0) {
echo '$cid: '.$cid.' | empty <br />';
} else {
echo '$cid: '.$cid.' | products contains <br />';
}
}
Duplicate cause, but I do not know how to change the code in this code
Array
(
[0] => Array
(
[product_id] => 1
[0] => 1
[category_id] => 221
[1] => 221
[active] => 0
[2] => 0
)
[1] => Array
(
[product_id] => 2
[0] => 2
[category_id] => 221
[1] => 221
[active] => 0
[2] => 0
)
)
$result array
Array
(
[221] => Array
(
[1] => 0
[2] => 0
)
)
#EDIT
Currently, the function returns something like this
enter image description here
And based on this array, it should be something like - as you can see 1437 has => 1 so the category is not empty
enter image description here

It sounds like you are trying to isolate what is and is not empty from a scattered list (it does sound like you might be able to do a better query though). See if this iteration helps filter.
function getCategoryActivity($products)
{
$store = array();
foreach($products as $detail) {
$cid = $detail['category_id'];
$pid = $detail['product_id'];
# If the cid is not already stored, store it
if(!isset($store[$cid]))
$store[$cid] = $detail['active'];
else {
# If it's already set to active, ignore it
if(!empty($store[$cid]))
continue;
else
# Store it if not currently active
$store[$cid] = $detail['active'];
}
}
# Send back the filtered array
return $store;
}
# Fetch the filtered array
$sorted = getCategoryActivity($products);
$sorted should give you a list of categories now that have activity in them and not in them. You can iterate one more time using array_map() or another foreach() to echo what you want. I have no idea what you are trying to do with that multiplier part so I ignored it.

Related

Can array_search return the key of the inner array of a multidimensional or nested array?

I am working on a shopping cart project and have a $_SESSION['productSummary'] array that looks like this.
[productSummary] => Array
(
[0] => Array
(
[name] => Individual Coins
[code] => 8774
[IDs] => Array
(
[0] => 8774
[1] => 8775
[2] => 8778
[3] => 8765
)
[pluID] => 6105
[qty] => 4
[finalPrice] => 0.0000
[listPrice] => 0.0000
[shipping] => 0.0000
)
[1] => Array
(
[name] => Business Package - 5,000
[code] => 8770
[IDs] => Array
(
[0] => 8770
)
[pluID] => 6087
[qty] => 1
[finalPrice] => 125.0000
[listPrice] => 125.0000
[shipping] => 0.0000
)
)
When the user wants to remove an item #8778 from the cart, I need to find the value of the index key for '8778' so I can remove that value from the array of IDs.
Here is the snip of code I have so far. I am getting good values for $matchingKey but $matchingKey2 is always empty.
// Find the key for the parent array
$matchingKey = array_search(8778, array_column($_SESSION["productSummary"], 'IDs'));
// Find the key for the element in the nested IDs array
$matchingKey2 = array_search(8778, array_column($_SESSION['productSummary'][$matchingKey]['IDs']));
// If it found a match, unset that element
if(!empty($matchingKey2)) {
unset($_SESSION["productSummary"][$matchingKey]['IDs'][$matchingKey2]);
}
// Reindex the array
$_SESSION["productSummary"][$matchingKey]['IDs'] = array_values($_SESSION["productSummary"][$matchingKey]['IDs']);
I was expecting
$matchingKey2 = array_search(8778, array_column($_SESSION['productSummary'][$matchingKey]['IDs']));
to return the value of 2 in this example, but instead if comes back as NULL
UPDATE: SOLVED
Based on the answers given, I updated my code to this and it seems to be working as expected now. (or at least until I break it again.) Thanks All
// $results is pulled from query of database based on a packageID - Short version is it puts all packaged inventory items in the cart and allows all to be taken out of the cart in as a group.
foreach ($results as $cartItem) {
// set cart time in the database back to NULL so it will appear in the store again
$query = "hidden";
dbWriteQuery($query);
// Remove item from SESSION['products']
$indexA = array_search($cartItem['inventoryID'], array_column($_SESSION["products"], 'code'));
if($indexA !== false) {
unset($_SESSION["products"][$indexA]);
}
// Reindex the array
$_SESSION["products"] = array_values($_SESSION["products"]);
// Remove item (or reduce qty) from SESSION['productSummary']
foreach ($_SESSION["productSummary"] as $key => $product) {
$indexB = array_search($cartItem['inventoryID'], $product['IDs']);
//Found a matching element
if ($indexB !== false) {
// if count of $product['IDs'] > 1, reduce the qty and remove the inventoryID from ID's
if(count($product['IDs'])>1) {
//reduct the qty
$_SESSION['productSummary'][$key]['qty'] = $_SESSION['productSummary'][$key]['qty'] - 1;
// remove the inventoryID from the IDs array
array_splice($_SESSION['productSummary'][$key]['IDs'], $indexB, 1);
// set the 'code' value equal to the next element in the IDs array
$_SESSION['productSummary'][$key]['code'] = $_SESSION['productSummary'][$key]['IDs'][0];
// else unset the whole element from ProductSummary
} else {
unset($_SESSION["productSummary"][$key]);
}
break;
}
}
// Reindex the array
$_SESSION["productSummary"] = array_values($_SESSION["productSummary"]);
}
You can't use array_search() to search nested arrays. Use an ordinary foreach loop.
Note also that you can't use !empty($matchingKey2) to tell if the item was found. If the item is the first element in the array, $matchingKey2 will be 0, which is considered empty. You have to use strict comparison with false.
foreach ($_SESSION["productSummary"] as &$product) {
$index = array_search(8778, $product['IDs']);
if ($index !== false) {
array_splice($product['IDs'], $index, 1);
break;
}
}

PHP how to loop through an array and grab specific parts

Ok so im trying to grab a single part of an array, the array is the return for some stats there can be up to 8 players in the server, the data i get is like this
Array (
[0] => 1
[1] => Player1
[2] =>
[3] => 1
[4] => 0
[5] => 0
[6] => 0
[7] => 0
[8] => 1
[9] => Player2
[10] =>
[11] => 1
[12] => 0
[13] => 0
[14] => 0
[15] => 0
)
so that is the return for 2 players, as i said it can be up to 8, anyway i am trying to just grab the player names and im not sure how to go about it ( Player1 , Player2 ) is the only data i need, any help is appreciated, it always returns 8 pieces of data per player never more never less if that makes it easier
(sorry for bad english)
If you have control over the return type, I would restructure the array being returned either into an Object or an array of arrays where each sub array contains all of the information for one player.
I you don't have control over the return type and the Player's name is always in the second position within the return array you can use a while loop to iterate over the array. Use a counter starting at 1 and then increment the counter by 8 each time through the loop. For example:
$i= 1;
while ($i < count($return_var)) {
$name = $return_var[$i];
// do something w/ name
$i += 8;
}
You want to get all items that are not '' (assuming empty string), 0 or 1 (assuming integers here):
$playerNames = array_diff($array, array('', 0, 1));
If you more specifically know what the format of the array actually is, you can also create some little "parser":
$playerSize = 8;
$playerFields = array('_1', 'name', '_3', '_4', '_5', '_6', '_7', '_8');
$players = array_chunk($array, $playerSize);
foreach($players as &$player)
{
$player = (object) array_combine($playerFields, $player);
}
unset($player);
This does parse $array into another array $players that contains one object per each player. Each object has the name property now:
printf("%d Player(s):\n", count($players));
foreach($players as $i => $player)
{
printf("#%d: %s\n", $player->name);
}
if the array you pasted is called $array and the values of the places without players are always numeric (like your example), this code will work:
$players = array();
foreach($array as $player){
if(!empty($player) && !is_numeric($player){
$players[]=$player;
}
}
var_dump($players);

If value exists in one PHP array, add value to second array

I have two PHP arrays. One contains a group name and another contains a pay wage value.
$group_wages_array = Array ( [0] => 1 [1] => 4 [2] => 1 [3] => 3 );
This means there are four employees on the schedule. Two are assigned to group 1, another to group 4 and the last to group 3.
The second array is as follows:
$tot_wages_array = Array ( [0] => 500 [1] => 44 [2] => 80 [3] => 11.25 );
This is a sample array of each employee's wage. Both arrays are constructed in order as values are added in a mysql while loop as it pulls the info from the database.
Later on down the line, I combine the two arrays to get one array where the key is the group number and the value is the total wages for that group:
$combined_group_wages = array_combine($group_wages_array, $tot_wages_array);
This works like a charm EXCEPT for when more than one employee is assigned to the same group. These arrays are built in a mysql while loop as it loops through each employee's info:
array_push($tot_wages_array, $totemp_wages_sch); // Add their wage to the array
array_push($group_wages_array, $emp_data['group_id']); // Add their group to the array
Instead of just pushing the data to the array, I need to do this... I know the english but I don't know how to code it:
If $emp_data['group_id'] exists as value in $group_wages_array, add nothing to this array but get the key. Add $totemp_wages_sch to $tot_wages_array where key = group_wages_array key
I know it sounds more like an SQL query but I have to keep the keys and values in order so that they can be combined later in the page. If I can get this to work right, The arrays shown in the example would be:
$group_wages_array = Array ( [0] => 1 [1] => 4 [2] => 3 );
$tot_wages_array = Array ( [0] => 580 [1] => 44 [2] => 11.25 );
$combined_group_wages = array_combine($group_wages_array, $tot_wages_array);
$combined_group_wages = Array ( [1] => 580 [4] => 44 [3] => 11.25 );
...I've got to make this work using PHP. Any ideas?
I came up with a solution based on a combination of two of the answers submitted below. Here it is if it can help someone:
if(in_array($emp_data['group_id'], $group_wages_array)){
$key = key($group_wages_array);
$tot_wages_array[$key] += $totemp_wages_sch;
} else {
array_push($group_wages_array, $emp_data['group_id']);
array_push($tot_wages_array, $totemp_wages_sch);
}
This should do it:
$group_wages_array = array(1, 4, 1, 3);
$tot_wages_array = array(500, 44, 80, 11.25);
$combined_group_wages = array();
for ($i=0; $i<count($group_wages_array); $i++) {
$group = $group_wages_array[$i];
if (array_key_exists($group_wages_array[$group], $combined_group_wages)) {
$combined_group_wages[$group] += $tot_wages_array[$i];
} else {
$combined_group_wages[$group] = $tot_wages_array[$i];
}
}
print_r($combined_group_wages);
Yields:
Array
(
[1] => 580
[4] => 44
[3] => 11.25
)
But I recommend that you just switch to using objects to better represent your data.
If I could see the entirety of the code that would help a lot, but here's your English converted to php. Show me more code and I can perfect it, until then try this ->
if(in_array($emp_data['group_id'], $group_wages_array)){
$key = key($group_wages_array);
$tot_wages_array[$key] = $totemp_wages_sch;
} else {
array_push($group_wages_array, $emp_data['group_id']);
}

PHP Array insert into MySQL table as individual rows

I am trying to insert multiple rows in a MySQL table from PHP arrays. I managed with with help of other members to get set of values in a pair of brackets but when i try to insert this i get "Error: Column count doesn't match value count at row 1" I donot know where am i going wrong. my codes are as below: (The number of values i get vary according to user input)
$docno1=array();
$serialno = array();
$acc_name = array();
$debit = array();
$credit = array();
for ($i=1;$i<=$rowcount;$i++)
{
//echo 'Accountname'.$i.' :'.($_GET['accname'.$i]).'<br>';
$docno1 [] = ($_GET['docno']);
array_unshift($docno1,"");
unset($docno1[0]);
$serialno [] = $i;
array_unshift($serialno,"");
unset($serialno[0]);
$acc_name[] = ($_GET['accname'.$i]);
array_unshift($acc_name,"");
unset($acc_name[0]);
$debit[] = ($_GET['DrAmount'.$i]);
array_unshift($debit,"");
unset($debit[0]);
$credit[] = ($_GET['CrAmount'.$i]);
array_unshift($credit,"");
unset($credit[0]);
}
$sum_dr = array_sum ($debit);
$sum_cr = array_sum ($credit);
echo ' values of $multi<br>';
$multi = array(
($docno1),
($serialno), //Array for a row of fields
($acc_name),
($debit),
($credit),
($docno1)
);
print_r($multi);
$new = array();
foreach($multi as $key=>$value) {
$new[] = "'".implode("','", $value)."'";
}
echo '<br>Values of $new <br>';
print_r($new);
$query = "(".implode("), (",$new).")";
echo $query.'<br>';
mysql_query("INSERT INTO docitems (`docno`,`itemno`,`accountname`,`debit`,`credit`, `picrefno`) VALUES ".$query.";") or die('Error: ' . mysql_error());
echo "Inserted successfully";
die;
The results i get are :
values of $multi
Array
(
[0] => Array
(
[1] => 3434
[2] => 3434
)
[1] => Array
(
[1] => 1
[2] => 2
)
[2] => Array
(
[1] => Lemon
[2] => Kidney Beans
)
[3] => Array
(
[1] => 20
[2] => 10
)
[4] => Array
(
[1] => 0
[2] => 0
)
[5] => Array
(
[1] => 3434
[2] => 3434
)
)
Values of $new
Array
(
[0] => '3434','3434'
[1] => '1','2'
[2] => 'Lemon','Kidney Beans'
[3] => '20','10'
[4] => '0','0'
[5] => '3434','3434'
)
('3434','3434'), ('1','2'), ('Lemon','Kidney Beans'), ('20','10'), ('0','0'), ('3434','3434')
Error: Column count doesn't match value count at row 1
mysql_query("INSERT INTO docitems (`docno`,`itemno`,`accountname`,`debit`,`credit`, `picrefno`) VALUES ".$query.";") or die('Error: ' . mysql_error());
You are trying to insert something into 6 fields, so that $query string must have 6 values in it, or you get this error.
You have a lot of $query's that are 2 values. And that's not 6
It looks to me as if you are mapping your array the wrong way round. You're trying to add two records with six fields each, but what you're actually putting into the SQL statement are six records with two fields each.
This is why MySQL is complaining -- because you've told it you want to update six fields, but in each of the records you've given it, you've only specified two fields.
You need to build your array differently.
I assume that $docno1, $serialno, $acc_name, $debit and $credit will always all have the same number of array elements (it appears from your code that you are assuming this, so I'll follow you in your assumption).
In that case, you need to build your array something like this:
$multi = array();
foreach($docno1 as $key=>value) {
$multi[] = array(
$docno1[$key],
$serialno[$key], //Array for a row of fields
$acc_name[$key],
$debit[$key],
$credit[$key],
$docno1[$key])
}
Replace the block in your code where you set $multi with this, and your program should work.
Look at what print_r($multi) looks like now, and you'll see the difference.
(note, there are more efficient ways of writing your whole program than this, but I've focused on giving you a drop-in replacement for this specific bit, to help show you where you were going wrong, rather than simply rewriting the whole program for you)
Hope this helps.
If the error is occurring when trying to insert a row to your table, try specifying the list of fields, in the insert query -- this way, the number of data in the values clause will match the number of expected columns.
Else, MySQL expects six columns : it expects the specific inserts -- for which you didn't specify a value.

Getting all possible combinations of N items in X Groups

I have a list of Groups that can vary in number, with Items in these groups that also vary in number. I've been racking my head over a way to get all possible combinations of 1 Item from every Group.
Bonus: I also need all combinations of not having every items from a group.
I've seen and done what was mentioned before, but that requires knowing the number of groups to begin with.
To be more specific about what I'm doing, I would like to generate products with exact pricing based off product options. Here's an example list:
So it would generate products like:
UV Coating, Qty 500, Color 4:0
UV Coating, Qty 500, Color 4:1
etc...
Each of these Groups has an ID, and each item has a Group_Item_ID. So I can put them in an array such as:
$selections[1][...] // 1 = Coating
$selections[2][...] // 2 = Quantity
// ... = all selected Items in group
Hope I explained it well enough. I'm just not able to wrap my head around how to do this when the number of Groups are variable also.
Here's an example array for the groups and their items:
Array
(
[0] => Array
(
[0] => 2
[1] => 3
)
[1] => Array
(
[0] => 10
[1] => 11
[2] => 12
)
[2] => Array
(
[0] => 16
[1] => 17
)
[3] => Array
(
[0] => 19
[1] => 20
)
)
Try this:
function c($groups, $prefix='')
{
$result = array();
$group = array_shift($groups);
foreach($group as $selected) {
if($groups) {
$result = array_merge($result, c($groups, $prefix . $selected. ' '));
} else {
$result[] = $prefix . $selected;
}
}
return $result;
}

Categories