Creating 2-D matrix in php - php

The thing is I have to create a 2D matrix in php where each row and column must have a key. I tried to do this but what happens is that a 2-D array is created which does not resemble a matrix. I used the following code:
$x=$row['start_id'];
$y=$row['dest_id'];
$d=$row['distance'];
$this->map[$x][$y]=$d;
Here map is the intended matrix. The intention of this code is to create an adjacency matrix and then fill the unset cells with maximum distance. $x, $y and $d in above code are derived from result of a mysql query.
Sample Output:
Array (
[10010012] => Array (
[10010013] => 2
[10010016] => 8
)
[10010016] => Array (
[10010015] => 5
)
[10010013] => Array (
[10010014] => 7
[10010016] => 3
)
[10010014] => Array (
[10010015] => 2
)
)
Now the problem is that I am not able to fill the empty cells
e.g. row key =>[10010012] and column key=>[10010015] (Not able to set value)
Any help is appreciated. If possible also mention how to traverse through such matrices.
I am a relative beginner and have tried my best to explain my problem. However if you find any shortcomings please point them out.
Edit: The matrix is not a square one.

That would be
$this->map[10010012][10010015]= MAX_DISTANCE;
On the other hand, why do you want to set all empty/non-existing cell to MAX_DISTANCE? You can leave the map incomplete and whenever a cell does not exist you assume MAX_DISTANCE as its value.
edit: simple example
define('MAX_DISTANCE', PHP_INT_MAX);
$map = array(
10010012 => array ( 10010013 => 2, 10010016 => 8),
10010016 => array ( 10010015 => 5 ),
10010013 => array ( 10010014 => 7, 10010016 => 3),
10010014 => array ( 10010015 => 2 )
);
function getValue(&$map, $x, $y) {
return isset($map[$x][$y]) ? $map[$x][$y] : MAX_DISTANCE;
}
function setValue(&$map, $x, $y, $value) {
if ( !isset($map[$x]) ) {
$map[$x] = array($y => $value);
}
else {
$map[$x][$y] = $value;
}
}
// get an "existing" value from $map
echo getValue($map, 10010012, 10010016), "\n";
// get a "non-existing" value from $map
echo getValue($map, 10010014, 10010016), "\n";
// set a "new" value
setValue($map, 10010014, 10010016, 5);
// $map has been altered
var_dump($map[10010014]);
prints
8
2147483647
array(2) {
[10010015]=>
int(2)
[10010016]=>
int(5)
}

Related

Get highest value in multi multidimensional array [duplicate]

This question already has answers here:
Find highest value in multidimensional array [duplicate]
(9 answers)
Closed 5 years ago.
i need to get the the max or highest value in a multi dimensional array.
here is my array $array:
[pay] => Array
(
[0] => Array
(
[title] => Array
(
[name] => 'hi'
)
[payment] => Array
(
[amount] => 35
[currency] => USD
)
)
[1] => Array
(
[title] => Array
(
[name] => 'lol'
)
[payment] => Array
(
[amount] => 50
[currency] => USD
)
)
[2] => Array
(
[title] => Array
(
[name] => 'ok'
)
[payment] => Array
(
[amount] => 30
[currency] => USD
)
)
)
i need to get the max value for amount which is 50. how can i do that?
here is what i tried but it did not work:
$max = -9999999; //will hold max val
$found_item = null; //will hold item with max val;
foreach($array as $k=>$v)
{
if($v['Total']>$max)
{
$max = $v['Total'];
$found_item = $v;
}
}
Simple as this one-liner. Get the payment column data, then pull the amount data from that generated array, then get the max value. Done and done. (Sorry it took me so long -- I had to convert your posted array to a usable php array.)
Input:
$array=["pay" => [
["title"=>["name"=>'hi'],"payment"=>["amount"=>35,"currency"=>"USD"]],
["title"=>["name"=>'lol'],"payment"=>["amount"=>50,"currency"=>"USD"]],
["title"=>["name"=>'ok'],"payment"=>["amount"=>30,"currency"=>"USD"]]
]
];
Method #1 (Demo):
echo max(array_column(array_column($array["pay"],"payment"),"amount"));
Method #2 (Demo):
$max=0;
foreach($array["pay"] as $subarray){
if($max<$subarray["payment"]["amount"]){
$max=$subarray["payment"]["amount"];
}
}
echo $max;
Method #3 (Demo):
$payments=array_column($array["pay"],"payment"); // declare payments array
rsort($payments); // sort by amount DESC
echo $payments[0]["amount"]; // access the first amount value
Output:
50
The benefits to method #1 are: code brevity, no condition statements, no global variable declarations/overwriting, just straight to the max value. What's not to love!
If method #1 is too scary, you can go with my method #2 (which was first posted by aendeerei). I don't prefer it because it requires the extra steps of initializing the $max variable, performing a conditional check on each iteration, and overwriting the $max variable when appropriate. Actual performance on the foreach loop is going to depend on the size of your array, but the difference between the two methods is going to be unnoticable to humans.
Method 3 might be my new favorite because there are no conditionals and just two functions before it is accessed purely by keys. However, it does require the declaration of a partial copy of the input array which must be sorted. Anyhow, take your pick -- it's all the same outcome.
Use Usort and get the 1st index
$arr= array
(
array
(
'payment' => array
(
'amount' => 35,
'currency' => 'USD'
)
),
array
(
'payment' => array
(
'amount' => 50,
'currency' => 'USD'
)
),
array
(
'payment' => array
(
'amount' => 80,
'currency' => 'USD'
)
)
);
function sortAmount($x, $y) {
return $y['payment']['amount'] - $x['payment']['amount'];
}
usort($arr, 'sortAmount');
echo "<pre>";
$highest=$arr[0];
print_r($highest)
//for value only
$highest=$arr[0]['payment']['amount'];
Working fiddle
http://phpfiddle.org/main/code/p5hw-ivei
$max = 0;
foreach ($array['pay'] as $key => $item) {
$amount = $item['payment']['amount'];
if ($amount > $max) {
$max = $amount;
}
}
echo $max;
Shorthand:
$result = array_reduce($array['pay'], function($a, $b){
return $a ? ($a['payment']['amount'] > $b['payment']['amount'] ? $a : $b) : $b;
});
var_dump($result['payment']['amount']);
Try this hope this will be helpful. Here we are just using simple foreach to get it done.
Solution 1:
try this code snippet here
$max=0;
foreach($yourArray["pay"] as $value)
{
if($max<$value["payment"]["amount"])
{
$max=$value["payment"]["amount"];
}
}
echo $max;
Solution 2:
Just for testing purpose i have converted you array to json. Here we are using array_column two times to get the columns
Try this code snippet here
$internals=array_column($yourArray["pay"],"payment");//retrieving payments
$amounts=array_column($internals, "amount");//retrieving amounts
arsort($amounts);
print_r(array_values($amounts)[0]);
Consider this example with an array named pay. You can adapt this method for your own array. This code will work for an array of n elements. Here I consider 3 as the number of elements in the array named $pay. You can replace the max elements in the array in the place of 3 for controlling the loop control variable 'i'.
$big=$pay[0];
for($i=1; $i<3; $i++){
if($pay[i]>$big)
$big=$pay[i];
}
echo $big;
I hope this is what you are looking for. Ask for any clarification.

PHP multidimensional associative array [duplicate]

This question already has answers here:
Transposing multidimensional arrays in PHP
(12 answers)
Closed 3 months ago.
I am new to php & I'm not sure that this can be done, but I am hoping that someone knows how to. I've collected all the data that I need to submit but now I need to reformat it before I can json_encode to send to the database.
Basically, I have 1 parent array($data) containing 3 sub-arrays ($hours, $WId, $Pid). I need to create associative arrays for each index position & join them together.
Here is my parent array:
$data = array(
'hours' => array(),
'wId' => array(),
'phaseId' => array(),
);
Here is what currently returns when I print_r each of these arrays:
Array ( [hours] => Array ( [0] => 0.5 [1] => 1 [2] => 2 ) )
Array ( [wId] => Array ( [0] => 10, [1] => 9, [2] => 8, ) )
Array ( [phaseId] => Array ( [0] => 20, [1] => 20, [2] => 19, ) )
I need to take these "vertical" arrays & turn them in to "horizontal" arrays per index, using thearray name as the $key & the value for that index as $value. Here is what I need to return.... (Syntax is probably wrong but you can get the idea.)
Array[1] ("hours" => 0.5, "wId" => 10, "phaseId" => 20)
Array[2] ("hours" => 1, "wId" => 9, "phaseId" => 20)
Array[3] ("hours" => 2, "wId" => 8, "phaseId" => 19)
Is there a function that will allow me to do this easily? I saw how to join & merge them together but not sure how to set the array name (hours, etc) as the $key & the value for each index as $value. I need to loop it too because the length of the arrays will vary. (But they will always the same length as each other, so index should still work as what needs to be collected.)
Any suggestions would be greatly appreciated :)
<?php
// set up your output array
$result = array();
// loop through $data, exposing $name for later use
foreach ($data as $name => $array) {
// loop through each named array and set the desired value
// using the current $key and $name
foreach ($array as $key => $value) {
$result[$key][$name] = $value;
}
}
// tada!
print_r($result);
NOTE: In your desired results in your question, you had the parent Array keys starting at 1. This answer assumes that's a typo and you actually wanted them to match the input. If you indeed wanted it to start at one, just change this line in my answer:
$result[$key+1][$name] = $value;

foreach not looping correctly for a webservice

I have and array that is being produced from a webservice.
Array (
[TPA_Extensions] => Array (
[TPARoomDetail] => Array (
[GuestCounts] => Array (
[GuestCount] => Array (
[!AgeQualifyingCode] => 10
[!Count] => 1
)
)
[!Occupancy] => Single
[!OccupancyCode] => SGL
)
)
[!IsRoom] => true
[!Quantity] => 1
[!RoomType] => Palace Gold Club Room
[!RoomTypeCode] => PGC
)
My foreach loop is as below
foreach ($roomType["TPA_Extensions"]["TPARoomDetail"]["GuestCounts"]["GuestCount"] as $guestcount) {
echo "guest count1->";print_r($guestcount);
echo "guest count2->"; print_r($roomType["TPA_Extensions"]["TPARoomDetail"]["GuestCounts"]["GuestCount"]);
}
The output i get is
guest
count1->10 guest count2->Array ( [!AgeQualifyingCode] => 10 [!Count] => 1 )
guest count1 should have been an array
Array ( [!AgeQualifyingCode] => 10 [!Count] => 1 ) but it comes as an int 10 ..
why is that so ..?
Your output is correct, $guestcount holds the number '10',
where $roomType["TPA_Extensions"]["TPARoomDetail"]["GuestCounts"]["GuestCount"]
hold an array.
this is your loop:
foreach ($roomType["TPA_Extensions"]["TPARoomDetail"]["GuestCounts"]["GuestCount"] as $guestcount) {
echo "guest count1->";print_r($guestcount);
echo "guest count2->"; print_r($roomType["TPA_Extensions"]["TPARoomDetail"]["GuestCounts"]["GuestCount"]);
}
ths loop will run 2 times, because that's the number of childs in GuestCount array.
it will be '10', then '1', exactly reflecting the structure of your array:
[!AgeQualifyingCode] => 10
[!Count] => 1
Theres nothing wrong in the code as 1st index holds integer value and 2nd index holds array. However your method of accessing array value are very complicated and doesn't looks good. You an access the array values and keys in more effective manner as follows.
1)Create a method that takes path of the array you want to access
For example According to your code if I want to access AgeQualifyingCode key than I have to write $roomType["TPA_Extensions"]["TPARoomDetail"]["GuestCounts"]["GuestCount"]["AgeQualifyingCode"].
This doesn't looks good, wouldn't it be great if you just have to pass the path of key you want to access the value to.
For example: /TPA_Extensions/TPARoomDetail/GuestCounts/GuestCount/AgeQualifyingCode
You just have to define a function that takes the path of the key, and will return value for that key
<?php
function path($path=null){
if($path){
$array = $theNameOfOriginalArray
$path = explode('/',$path);
foreach($path as $sub){
if(isset($array[$sub])){
$array = $array[$sub];
}
}
return $array;
}
}
$value = path('TPA_Extensions/TPARoomDetail/GuestCounts/GuestCount/AgeQualifyingCode');
//will return 10
?>

I need to compare specific elements of a multi-dim PHP array with certain other elements in the same array

I have an array that contains certain words from a MySQL database, which are matched with words in a line of text. The text is, say, 20 lines long.
The array also stores the position of each word in the database, and some of these words are "related" to other words in the database, which are also stored in the array. It looks a bit like this:
$words = array(
["Line0"] => array (
["Word0"] => array(
["Name"] => "RandomWord",
["DatabasePos"] => 15,
["RelationsInDatabase"] => array (
89, //So this is clearly the same database pos as Word1 on Line0.
27, //let's assume there's a word on line15 that has this database pos
)
),
["Word1"] => array (
["Name"] => "SomeOtherRandomWord",
["DatabasePos"] => 89,
["RelationsInDatabase"] => array (
NULL
)
)
),
["Line1"] => array (
["Word0"] => .... ,
..
...
...
)
);
etc.
I want to iterate through this array, and find the words that are related to by other words. Then, append to the same array which lines and which words they are related to. For example:
$words = array(
["Line0"] => array (
["Word0"] => array(
["Name"] => "RandomWord",
["DatabasePos"] => 15,
["RelationsInDatabase"] => array (
89, //So this is clearly the same database pos as Word1 on Line0.
27, //let's assume there's a word on line15 that has this database pos
),
["RelationsInLinesOfText"] => array ( //I want to loop through and add this element to the array.
[0] => array("Line0", "Word1"),
[1] => array("Line15", "Word3")
)
),
["Word1"] => array (
["Name"] => "SomeOtherRandomWord",
["DatabasePos"] => 89,
["RelationsInDatabase"] => array (
NULL
)
)
),
["Line1"] => array (
["Word0"] => .... ,
..
...
...
)
);
My problem is that I end up with a very messy, 4/5 level deep "foreach" loop and end up making a bunch of mistakes that are hard to debug due to the messy code. Is there a clean way of doing this, maybe using something like a RecursiveArrayIterator? I don't have much experience with PHP iterator objects.
Thanks for the help
It is an ugly solution, but I think in any case you'll need to iterate through entire array twice-nested:
function searchLink($iLink, &$rgData)
{
$rgResult = [];
foreach($rgData as $sLine=>$rgLines)
{
foreach($rgLines as $sWord=>$rgWord)
{
if($rgWord['DatabasePos']==$iLink)
{
$rgResult[]=['line'=>$sLine, 'word'=>$sWord];
}
}
}
return $rgResult;
}
//$rgData is a data array
foreach($rgData as $sLine => $rgLines)
{
foreach($rgLines as $sWord=>$rgWord)
{
foreach($rgWord['RelationsInDatabase'] as $iPosition)
{
$rgData[$sLine][$sWord]['RelationsInLinesOfText'][]=searchLink($iPosition, $rgData);
}
}
}
also, since you've not mentioned if position is unique, an array ['line'=>$sLine, 'word'=>$sWord] will be written to each entry.

Fetching a multidimensional array

I am trying to edit a plugin that is fetching a multidimensional array, then breaking it out into a foreach statement and doing stuff with the resulting data.
What I am trying to do is edit the array before it gets to the foreach statement. I want to look and see if there is a key/value combination that exists, and if it does remove that entire subarray, then reform the array and pass it to a new variable.
The current variable
$arrayslides
returns several subarrays that look like something like this (I remove unimportant variables for the sake of briefness):
Array (
[0] => Array (
[slide_active] => 1
)
[1] => Array (
[slide_active] => 0
)
)
What I want to do is look and see if one of these subarrays contains the key slide_active with a value of 0. If it contains a value of zero, I want to dump the whole subarray altogether, then reform the multidimensional array back into the variable
$arrayslides
I have tried a few array functions but have not had any luck. Any suggestions?
$arrayslides = array(0 => array ( 'slide_active' => 1, 'other_data' => "Mark" ),
1 => array ( 'slide_active' => 0, 'other_data' => "ABCDE" ),
2 => array ( 'slide_active' => 1, 'other_data' => "Baker" ),
3 => array ( 'slide_active' => 0, 'other_data' => "FGHIJ" ),
);
$matches = array_filter($arrayslides, function($item) { return $item['slide_active'] == 1; } );
var_dump($matches);
PHP >= 5.3.0
I know its not so efficient but still
foreach ($arraySlides as $key => $value)
{
if(in_array('0', array_values($value))
unset($arraySlides[$key]);
}

Categories