Array for each array row PHP - php

I have an array with name $items like this:
array(2) {
[0]=> array(8) { ["item_regel"]=> int(0) ["item_id"]=> string(2) "82" ["item_naam"]=> string(21) "Bureauschermen staand" ["item_uitvoering"]=> string(12) "100 x 200 cm" ["item_afmeting"]=> NULL ["item_kleur"]=> string(11) "Transparant" ["item_aantal"]=> string(1) "2" ["item_opmerking"]=> string(18) "Ik wil mijn logo 2" }
[1]=> array(8) { ["item_regel"]=> int(1) ["item_id"]=> string(3) "226" ["item_naam"]=> string(33) "Instructieborden Dibond aluminium" ["item_uitvoering"]=> string(10) "50 x 50 cm" ["item_afmeting"]=> NULL ["item_kleur"]=> string(5) "Blauw" ["item_aantal"]=> string(1) "2" ["item_opmerking"]=> string(4) "test" }
}
I found this code to prefill a gravity form list field:
add_filter( 'gform_field_value_list_one', 'itsg_prefill_list_one' );
function itsg_prefill_list_one( $value ) {
$list_array = array(
//List row
array(
"Product" => "Product",
"Afmeting" => "Good",
"Uitvoering" => "Product",
"Kleur" => "Product",
"Aantal" => "Product",
"Opmerking" => "Product",
),
//List row
array(
"Product" => "Product",
"Afmeting" => "Good",
"Uitvoering" => "Product",
"Kleur" => "Product",
"Aantal" => "Product",
"Opmerking" => "Product",
),
);
return $list_array;
}
Now this function is filled with fixed values. I want to do a 'List row' foreach row inside the array above.
I tried this but it won't work:
add_filter( 'gform_field_value_list_one', 'itsg_prefill_list_one' );
function itsg_prefill_list_one( $value ) {
$items = $_SESSION["wishlist"];
$list_array = array(
foreach ($items as $keys => $values) {
array(
"Product" => $values["item_naam"],
"Afmeting" => $values["item_afmeting"],
"Uitvoering" => $values["item_uitvoering"],
"Kleur" => $values["item_kleur"],
"Aantal" => $values["item_aantal"],
"Opmerking" => $values["item_opmerking"],
),
}
);
return $list_array;
}

Inside the loop add items to the array from the looped array
add_filter( 'gform_field_value_list_one', 'itsg_prefill_list_one' );
function itsg_prefill_list_one( $value ) {
foreach ($_SESSION["wishlist"] as $keys => $values) {
$list_array[] = [
"Product" => $values["item_naam"],
"Afmeting" => $values["item_afmeting"],
"Uitvoering" => $values["item_uitvoering"],
"Kleur" => $values["item_kleur"],
"Aantal" => $values["item_aantal"],
"Opmerking" => $values["item_opmerking"],
];
}
return $list_array;
}

Related

Sorting a Multi-Dimensional Array by sum of object values in PHP

I have the below multi dimensional array of products. Each array is a pair of products that make a product set, I need to order the multi dimensional array by the total price of each product set.
array(4) {
[0]=>
array(2) {
["product1"]=>
object(stdClass)#5075 (2) {
["product_id"]=>
string(4) "9416"
["price"]=>
string(6) "110.00"
}
["product2"]=>
object(stdClass)#5077 (2) {
["product_id"]=>
string(4) "9431"
["price"]=>
string(6) "100.00"
}
}
[1]=>
array(2) {
["product1"]=>
object(stdClass)#5065 (2) {
["product_id"]=>
string(4) "1254"
["price"]=>
string(6) "75.00"
}
["product2"]=>
object(stdClass)#5067 (2) {
["product_id"]=>
string(4) "9431"
["price"]=>
string(6) "62.00"
}
}
[2]=>
array(2) {
["product1"]=>
object(stdClass)#5055 (2) {
["product_id"]=>
string(4) "9416"
["price"]=>
string(6) "45.00"
}
["product2"]=>
object(stdClass)#5057 (2) {
["product_id"]=>
string(4) "9431"
["price"]=>
string(6) "50.00"
}
}
[3]=>
array(2) {
["product1"]=>
object(stdClass)#5045 (2) {
["product_id"]=>
string(4) "9416"
["price"]=>
string(6) "60.00"
}
["product2"]=>
object(stdClass)#5047 (2) {
["product_id"]=>
string(4) "9431"
["price"]=>
string(6) "25.00"
}
}
}
I need to sort the multi-dimensional array by the total sum of product1 + product2 in each array in ascending order. For example [1] should be above [0] as 75+62 is less than 110 +100.
If anyone can help me with this it would be greatly appreciated.
You can use usort() for this purpose:-
function comparePrice($a,$b)
{
$a_price = $a['product1']->price + $a['product2']->price;
$b_price = $b['product1']->price + $b['product2']->price;
if ($a_price ==$b_price) return 0;
return ($a_price<$b_price)? -1:1;
}
usort($array,'comparePrice');
A hardcoded working example:- https://3v4l.org/mTfu6
You need to use user-defined sorting
http://php.net/manual/en/function.usort.php
usort($products, function($a, $b) {
$prodA = $a['product1']['price'] + $a['product2']['price'];
$prodB = $b['product1']['price'] + $b['product2']['price'];
if($prodA == $prodB) return 0;
return ($prodA < $prodB) ? -1 : 1;
});
The php7+ "spaceship operator" (aka three-way-comparison operator) makes the syntax with usort() as clean and brief as possible.
Code: (Demo)
$array = [
[
"product1" => (object) ["product_id" => "9416", "price"=>"110.00"],
"product2" => (object) ["product_id"=>"9431", "price"=>"100.00"]
],
[
"product1" => (object) ["product_id" => "1254", "price"=>"75.00"],
"product2" => (object) ["product_id"=>"9431", "price"=>"62.00"]
],
[
"product1" => (object) ["product_id" => "9416", "price"=>"45.00"],
"product2" => (object) ["product_id"=>"9431", "price"=>"50.00"]
],
[
"product1" => (object) ["product_id" => "9416", "price"=>"60.00"],
"product2" => (object) ["product_id"=>"9431", "price"=>"25.00"]
]
];
usort($array, function($a, $b) {
return $a['product1']->price + $a['product2']->price <=> $b['product1']->price + $b['product2']->price;
});
var_export($array);
Output:
array (
0 => // sum = 85.00
array (
'product1' =>
(object) array(
'product_id' => '9416',
'price' => '60.00',
),
'product2' =>
(object) array(
'product_id' => '9431',
'price' => '25.00',
),
),
1 => // sum = 95.00
array (
'product1' =>
(object) array(
'product_id' => '9416',
'price' => '45.00',
),
'product2' =>
(object) array(
'product_id' => '9431',
'price' => '50.00',
),
),
2 => // sum = 137.00
array (
'product1' =>
(object) array(
'product_id' => '1254',
'price' => '75.00',
),
'product2' =>
(object) array(
'product_id' => '9431',
'price' => '62.00',
),
),
3 => // sum = 210.00
array (
'product1' =>
(object) array(
'product_id' => '9416',
'price' => '110.00',
),
'product2' =>
(object) array(
'product_id' => '9431',
'price' => '100.00',
),
),
)

How to compare two multidimensional arrays by certain keys in each?

I have two multidimensional arrays of the same structure.
Like this:
array(2) {
[0] =>
array(9) {
'id' =>
string(5) "44994"
'ersatzteil_id' =>
string(3) "120"
'lang' =>
string(6) "name2_tag2"
'title' =>
string(12) "Seitentüren"
'alias' =>
string(12) "seitentueren"
'content' =>
string(1610) "LOREM ISPUM BLALABLBL"
'on_main' =>
string(1) "0"
'disabled' =>
string(1) "1"
'short_text' =>
NULL
}
[1] =>
array(9) {
'id' =>
string(5) "44996"
'ersatzteil_id' =>
string(3) "122"
'lang' =>
string(6) "name1_tag1"
'title' =>
string(7) "Spoiler"
'alias' =>
string(7) "spoiler"
'content' =>
string(1513) "SOME OTHER RANDOM TEXT"
'on_main' =>
string(1) "0"
'disabled' =>
string(1) "0"
'short_text' =>
NULL
}
}
What I need to do is I need to compare first array with the second one.
I have to compare them by keys ersatzteil_id and content , and I find that they have same content I need to store element from first array in another new array, that wasn't existing before.
For example I need something like this, but more efficient:
if(array1[20]['ersatzteil_id'] == array2[145]['ersatzteil_id']
&& array1[20]['content'] == array2[145]['content']){
array3 = array1[20];
}
Try this code:-
$result = [];
foreach($array1 as $arr1){
foreach($array2 as $arr2){
if(($arr1['id'] == $arr2['id']) && ($arr1['ersatzteil_id'] == $arr2['ersatzteil_id'])){
$result[] = $arr1;
}
}
}
echo '<pre>'; print_r($result);

Converting an array to a new array to meet template

I have an old file. I would like to integrate it into a new template I bought.
I have a list of links. I store them in a Session array.
The array has a title and a url for each
<?php session_start();
//in my old file i write this
foreach ($_SESSION[links] as $value){
?>
<a href="<?php print $value[linkurl]?>"><?php print $value[linktitle]?></a ><?php
}
// array style i need to match in the new file
// "name" => array(
// "title" => "Display Title",
// "url" => "http://yoururl.com"
// )
// what i tried
// foreach ($_SESSION[links] as $value){
// "$value[linktitle]" => array(
// "title" => "$value[linktitle]",
// "url" => "$value[linkurl]"
// )
// }
//obviously doesn't work
?>
Here is the full template. I'm trying to replace the Smart UI sub (carousel, tab...)
<?php
//CONFIGURATION for SmartAdmin UI
//ribbon breadcrumbs config
//array("Display Name" => "URL");
$breadcrumbs = array(
"Home" => APP_URL
);
/*navigation array config
ex:
"dashboard" => array(
"title" => "Display Title",
"url" => "http://yoururl.com",
"url_target" => "_self",
"icon" => "fa-home",
"label_htm" => "<span>Add your custom label/badge html here</span>",
"sub" => array() //contains array of sub items with the same format as the parent
)
*/
$page_nav = array(
"dashboard" => array(
"title" => "Dashboard",
"url" => APP_URL,
),
"smartui" => array(
"title" => "Smart UI",
"icon" => "fa-code",
"sub" => array(
"carousel" => array(
"title" => "Carousel",
"url" => APP_URL.'/smartui-carousel.php'
),
"tab" => array(
"title" => "Tab",
"url" => APP_URL.'/smartui-tab.php'
),
"accordion" => array(
"title" => "Accordion",
"url" => APP_URL.'/smartui-accordion.php'
),
"widget" => array(
'title' => "Widget",
'url' => APP_URL."/smartui-widget.php"
),
"datatable" => array(
"title" => "DataTable",
"url" => APP_URL."/smartui-datatable.php"
),
"button" => array(
"title" => "Button",
"url" => APP_URL."/smartui-button.php"
),
'smartform' => array(
'title' => 'Smart Form',
'url' => APP_URL.'/smartui-form.php'
)
)
)
);
//configuration variables
$page_title = "";
$page_css = array();
$no_main_header = false; //set true for lock.php and login.php
$page_body_prop = array(); //optional properties for <body>
$page_html_prop = array(); //optional properties for <html>
?>
var_dump:
array(6) {
[0]=> array(4) { ["linktitle"]=> string(13) "Claims Center" ["linkurl"]=> string(79) "Claims.php" ["Sectionlinktitle"]=> string(12) "Applications" ["linkdes"]=> string(11) "Application" }
[1]=> array(4) { ["linktitle"]=> string(16) "Expense Allocate" ["linkurl"]=> string(81) "Expense.php" ["Sectionlinktitle"]=> string(12) "Applications" ["linkdes"]=> string(11) "Application" }
[2]=> array(4) { ["linktitle"]=> string(13) "Freight Rater" ["linkurl"]=> string(105) "User.php" ["Sectionlinktitle"]=> string(12) "Applications" ["linkdes"]=> string(11) "Application" }
[3]=> array(4) { ["linktitle"]=> string(14) "Invoice Center" ["linkurl"]=> string(71) "Online.php" ["Sectionlinktitle"]=> string(12) "Applications" ["linkdes"]=> string(11) "Application" }
[4]=> array(4) { ["linktitle"]=> string(4) "KPIs" ["linkurl"]=> string(4) "KPIs" ["Sectionlinktitle"]=> string(10) "Dashboards" ["linkdes"]=> string(9) "Dashboard" }
[5]=> array(4) { ["linktitle"]=> string(16) "Multi-Mode Rater" ["linkurl"]=> string(0) "M" ["Sectionlinktitle"]=> string(12) "Applications" ["linkdes"]=> string(16) "Multi-Mode Rater" }
}
You want to add the navigation in $_SESSION['links'] to the new template!
Comment out the $page_nav variable (/* $page_nav = array( ... ); */) in the template. This will generate the code to insert in the template (cut and paste):
$a = $_SESSION['links'];
echo '<pre>$page_nav = array(' . "\n";
foreach( $a as $k=>$v ) {
echo "\t'" . strtolower(str_replace(' ','',$v['linktitle'])) . "' => array(\n"
. "\t\t'title' => '" . $v['linktitle'] . "',\n"
. "\t\t'url' => '" . $v['linkurl'] . "'\n"
. "\t),\n";
}
echo ');</pre>';
If you want to keep the code in the $_SESSION variable (really not a good idea) you put this piece of code in its place:
$page_nav = array();
foreach ( $_SESSION['links'] as $k=>$v ) {
$page_nav[strtolower(str_replace(' ','',$v['linktitle']))] = array(
'title' => $v['linktitle'],
'url' => $v['linkurl']
);
}
I think this should work! I have not considered any submenus, since none were in your var_dump!
You need to create a new array:
$page_nav = array();
foreach ($_SESSION[links] as $value) {
$page_nav[][$value['linktitle']] = array(
'title' => $value['linktitle'],
'url' => $value['linkurl']
)
}
Now you should have everything in the new array $var;

Merging arrays with specific output format

I am currently learning how to manage and work with arrays. But I am a bit lost with combining two arrays. Both arrays have the same number of values in it. The array_merge( $thumbnails, $urls ); does what it says but it is not what I am looking for. How can i merge the array as shown below?
$thumbnails = array(
array( "thumbnail" => "https://example1.png" ) ,
array( "thumbnail" => "https://example2.png" ) ,
array( "thumbnail" => "https://example3.png" ) ,
);
$urls = array(
array( "url" => "http://www.example.com/1" ) ,
array( "url" => "http://www.example.com/2" ) ,
array( "url" => "http://www.example.com/3" ) ,
);
Current Result
[0]=>
array(1) {
["thumbnail"]=> "https://example1.png"
}
[1]=>
array(1) {
["thumbnail"]=> "https://example2.png"
}
[2]=>
array(1) {
["thumbnail"]=> "https://example3.png"
}
[3]=>
array(1) {
["url"]=> "http://www.example.com/1"
}
[4]=>
array(1) {
["url"]=> "http://www.example.com/2"
}
[5]=>
array(1) {
["url"]=> "http://www.example.com/3"
}
Desired Result
[0]=>
array(2) {
["thumbnail"]=> "https://example1.png"
["url"]=> "http://www.example.com/1"
}
[1]=>
array(2) {
["thumbnail"]=> "https://example2.png"
["url"]=> "http://www.example.com/2"
}
[2]=>
array(2) {
["thumbnail"]=> "https://example2.png"
["url"]=> "http://www.example.com/2"
}
[3]=>
array(2) {
["thumbnail"]=> "https://example3.png"
["url"]=> "http://www.example.com/3"
}
I would just loop over them:
foreach ($thumbnails as $k => $src) {
if (isset($urls[$k]) {
$urls[$k]['thumbnail'] = $src;
}
}
The function array_merge won't help you out here, because it's "Array in Array". But you can loop over them, so you have only one array-item. The following function returns an array just as you desire:
function array_merge_keys($a, $b) {
$retArr = array();
// Lets use min(countA, countB) so there will be no errors on
// unbalanced array item counts.
for($i = 0; $i < min(count($a), count($b)); $i++) {
$retArr[$i] = array_merge($a[$i], $b[$i]);
} // for end
return $retArr;
}
$a = array(array("url" => "1.jpg"), array("url" => "2.jpg"));
$b = array(array("thumb" => "1.thumb.jpg"), array("thumb" => "2.thumb.jpg"));
print_r(array_merge_keys($a, $b));
This gives you:
Array
(
[0] => Array
(
[url] => 1.jpg
[thumb] => 1.thumb.jpg
)
[1] => Array
(
[url] => 2.jpg
[thumb] => 2.thumb.jpg
)
)
$thumbnails = array(
array( "thumbnail" => "https://example1.png" ) ,
array( "thumbnail" => "https://example2.png" ) ,
array( "thumbnail" => "https://example3.png" ) ,
);
$urls = array(
array( "url" => "http://www.example.com/1" ) ,
array( "url" => "http://www.example.com/2" ) ,
array( "url" => "http://www.example.com/3" ) ,
);
$thumbnails = array_combine(array_map(function($key){return 'key'.$key;},array_keys($thumbnails)),$thumbnails);
$urls = array_combine(array_map(function($key){return 'key'.$key;},array_keys($urls)),$urls);
var_dump(array_values(array_merge_recursive($thumbnails,$urls)));
do you mean this ?

Multi-dimensional array / creating a survey

I have an array like this:
$survey = array(
'Category1' => array(
'Question1' => array(
'Option1', 'Option2', 'Option3'
),
'Question2' => array(
'Option1', 'Option2', 'Option3'
)
),
'Category2' => array(
'Question1' => array(
'Option1', 'Option2', 'Option3'
),
'Question2' => array(
'Option1', 'Option2', 'Option3'
)
)
);
This array is in practice much larger. The requirement is 3 questions per page. My thought was to store which category and question I'm currently on. For example category 0, question 2. Then check to see if array_key_exists and if so, display, if not, increment and try again. As you might have guessed, categories and questions don't have keys (at least not numeric ones for me to loop through). So using an index is, as far as I know, is out of the question. How can I dynamically display 3 questions per page and automatically get the next 3 questions for the next page without knowing what the value is for category2, for example. How can I traverse/target this?
Thanks,
Ryan
The data seems fairly static so i would suggest changing the data format :)
Change the array into something like:
$survey = array(
array( 'name' = > 'Category1',
'questions' => array(
array(
'name' => 'Question1',
'opts' => array(
'Option1', 'Option2', 'Option3'
)
),
array(
'name' => 'Question2',
'opts' => array(
'Option1', 'Option2', 'Option3'
)
)
),
array( 'name' = > 'Category2',
'questions' => array(
array(
'name' => 'Question1',
'opts' => array(
'Option1', 'Option2', 'Option3'
)
),
array(
'name' => 'Question2',
'opts' => array(
'Option1', 'Option2', 'Option3'
)
)
)
);
And you can use integer indexes then. Just remember 2 number (the category index and the question index inside the category. And just increment until end of array in each case.
Php is not my strongest language so the code above might look strange to a native php programmer. However the root cause of OP's difficulties is the inability to easily create an interator type object. This is because of the fact that the key based array have a "strange" order given by their hash map nature. Change the nature and allow yourself to build an interator like object (aka an array index).
Since you're using an associative array (aka hash), there is no order to it. Each question and each category need to have the next question/category key with them. After that, see link-list algorithms.
My be array_keys() function will help you? You will iterate keys array (to get next keys).
<?php
$survey = array(
'Category1' => array(
'Question1' => array(
'Option1', 'Option2', 'Option3'
),
'Question2' => array(
'Option1', 'Option2', 'Option3'
),
'Question3' => array(
'Option1', 'Option2', 'Option3'
),
'Question4' => array(
'Option1', 'Option2', 'Option3'
)
),
'Category 2' => array(
'Question1' => array(
'Option1', 'Option2', 'Option3'
),
'Question2' => array(
'Option1', 'Option2', 'Option3'
)
),
'Category 3' => array(
'Question1' => array(
'Option1', 'Option2', 'Option3'
),
'Question2' => array(
'Option1', 'Option2', 'Option3'
),
'Question3' => array(
'Option1', 'Option2', 'Option3'
),
)
);
function fetchQuestions($survey, $page, $perPage = 3)
{
$results = Array();
$nCount = 0; $nRead = 0; $nIndex = $page * $perPage;
foreach ($survey as $CategoryName => $Questions)
{
foreach ($Questions as $Question => $Options)
{
if ($nCount >= $nIndex && $nRead < $perPage)
{
if (!isset($results[$CategoryName]))
$results[$CategoryName] = Array();
$results[$CategoryName][$Question] = $Options;
$nRead++;
}
$nCount++;
}
}
return $results;
}
echo '<html><body><pre>';
var_dump(fetchQuestions($survey,0));
var_dump(fetchQuestions($survey,1));
var_dump(fetchQuestions($survey,2));
echo '</pre></body></html>';
?>
And the output:
array(1) {
["Category1"]=>
array(3) {
["Question1"]=>
array(3) {
[0]=>
string(7) "Option1"
[1]=>
string(7) "Option2"
[2]=>
string(7) "Option3"
}
["Question2"]=>
array(3) {
[0]=>
string(7) "Option1"
[1]=>
string(7) "Option2"
[2]=>
string(7) "Option3"
}
["Question3"]=>
array(3) {
[0]=>
string(7) "Option1"
[1]=>
string(7) "Option2"
[2]=>
string(7) "Option3"
}
}
}
array(2) {
["Category1"]=>
array(1) {
["Question4"]=>
array(3) {
[0]=>
string(7) "Option1"
[1]=>
string(7) "Option2"
[2]=>
string(7) "Option3"
}
}
["Category 2"]=>
array(2) {
["Question1"]=>
array(3) {
[0]=>
string(7) "Option1"
[1]=>
string(7) "Option2"
[2]=>
string(7) "Option3"
}
["Question2"]=>
array(3) {
[0]=>
string(7) "Option1"
[1]=>
string(7) "Option2"
[2]=>
string(7) "Option3"
}
}
}
array(1) {
["Category 3"]=>
array(3) {
["Question1"]=>
array(3) {
[0]=>
string(7) "Option1"
[1]=>
string(7) "Option2"
[2]=>
string(7) "Option3"
}
["Question2"]=>
array(3) {
[0]=>
string(7) "Option1"
[1]=>
string(7) "Option2"
[2]=>
string(7) "Option3"
}
["Question3"]=>
array(3) {
[0]=>
string(7) "Option1"
[1]=>
string(7) "Option2"
[2]=>
string(7) "Option3"
}
}
}
There's my bid. Returns an array similar to your original array with the questions that should be displayed on that specific page.
If you want a more visual representation:
echo '<html><body>';
$page = 0;
while (count($matches = fetchQuestions($survey,$page++)) > 0)
{
echo '<div style="background-color:#CCC;">';
echo '<h2>Page '.$page.'</h2>';
echo '<ul>';
foreach ($matches as $Category => $Questions)
{
echo '<li><strong>'.$Category.'</strong>:<ul>';
foreach ($Questions as $Question => $Options)
{
echo '<li><u>'.$Question.'</u><ul>';
foreach ($Options as $Option)
echo '<li>'.$Option.'</li>';
echo '</ul>';
}
echo '</ul></li>';
}
echo '</ul>';
echo '</div>';
}
echo '</body></html>';

Categories