I got the following array:
"task" : {
"author_id" : 150,
"created_at" : somedate,
"status_id" : 2,
"assignee_id" : 100,
"updated_at" : somedate_too
and I got 2 more associative arrays where I store names for IDs in the following way:
"100" => Mike,
"150" => Bob //etc..., the same for statuses
I need to check for the IDs in the first array and replace numbers with names for the corresponding arrays in the most effective way. I tried the following:
if(isset(task['status_id'])){$row = array_merge($row, [$status_ids[
task['status_id']]]);}else{$row = array_merge($row, '');}
if(isset(task['author_id'])){row = array_merge($row, [$users[// note the different array here
task['author_id']]]);}else{$row = array_merge($row, '');}
if(isset(task['assignee_id'])){$row = array_merge($row, [$users[
task['assignee_id']]]);}else{$row = array_merge($row, '');}
In my resulting array ($row) I cannot miss the index and replace it with another value. If there is no value in the first array, I need to insert an empty string to get the following, for example:
['in progress', '', 'Mike']
if there is no author_id in the first array. I believe there should be a better way to do it with foreach loop, but I cant find out how because for different fields I get the data from different arrays. I dont think a separate if clause for every field is the most suitable here.
Any help would be welcome. Thank You.
You could map your special keys to their array counterparts using references and use that mapping when populating $row, like this:
$users = [
"100" => "Mike",
"150" => "Bob",
];
$status_ids = [
1 => "Foo",
2 => "Bar",
];
// Define output format and array mapping
$mapping = [
"author_id" => &$users, // Mapped to $users array
"created_at" => null, // Not mapped, keep $task value
"status_id" => &$status_ids,
"assignee_id" => &$users,
"updated_at" => null,
];
$task = [
"author_id" => 150,
"created_at" => "Some date",
"status_id" => 2,
// "assignee_id" => 99999, // Oops, missing key/value => empty string in $row
"updated_at" => "Some other date",
];
foreach ($mapping as $key => $mappedArray) {
#$row[] = $mappedArray
? $mappedArray[$task[$key]] ?: ''
: $task[$key];
}
print_r($row);
Output:
Array
(
[0] => Bob
[1] => Some date
[2] => Bar
[3] =>
[4] => Some other date
)
It should work (I didn't try it, but it should give you the general idea):
<?php
$fields = array("author_id", "assignee_id", "status_id");
$aliases = array("users", "users", "status_ids");
foreach ($task as $key=>&$value) {
$alias = str_replace($fields, $aliases, ${$key});
if (is_array(${$alias}) {
$value = array_key_exists($value, ${$alias}) ? ${$alias}[$value] : "";
}
}
unset($value);
And then you can fill up your $row as you planned, directly from the $task array.
Related
I am aware that I could use a loop to answer my question, but I was hoping that maybe PHP has a function to do what I am trying to achieve and that someone might know.
Basically I am trying to identify a unique key from a series of arrays and then extract the value of the correlated key in the array.
So basically, from this array:
$myarray = array(array("id" => 1, "label" => "True"), array("id" => 2, "label" => "False"))
I want to be able to find the label value when the id is searched and matched, i.e. $id = 1 should return True.
Any simple functions available to do this without having to write a couple of loops?
It would be one simple loop. But if you are loopofobic, then you can rely on other functions (that acts as loop too):
function find(array $inputs, int $search): ?string
{
$result = array_filter($inputs, fn ($input) => $input['id'] === $search);
return current($result)['label'] ?? null;
}
$myarray = [["id" => 1, "label" => "True"], ["id" => 2, "label" => "False"]];
var_dump(find($myarray, 1)); // string(4) "True"
var_dump(find($myarray, 2)); // string(5) "False"
var_dump(find($myarray, 3)); // NULL
Live Example
you may use the built-in function array_column() for your aim.
$myarray = array(array("id" => 1, "label" => "True"), array("id" => 2, "label" => "False"));
/* label (value) per id (key) in 1-dimensional array.*/
print_r(array_column($myarray,'label','id'));
will return
Array
(
[1] => True
[2] => False
)
so you may adjust the code below.
$myarray = array(array("id" => 1, "label" => "True"), array("id" => 2, "label" => "False"));
$id_val = 1;
$output = isset(array_column($myarray,'label','id')[$id_val]) ? array_column($myarray,'label','id')[$id_val] : 'key not found';
var_dump($output);
I am parsing a csv file, and then looping it like so.
foreach ($this->csvData as $dataKey => &$item) {
foreach ($item as $key => $value) {
print_r($item);
}
}
Now if I output item, I can see something like the following
array:12 [
"ID" => "12345"
"CODE" => "AZ6G"
"YEAR" => "2009"
"WEEK" => "13"
"FULL_DATE" => "29/04/2014"
"SALES" => "asdas89.34"
"QUANTITY" => "3"
]
So the above example represents one row in the csv, the key is the header name and then it has a value.
The problem is this, I know which columns I need to keep based on an index value. These values are selected by the user at a previous stage. So in the above example I know I need to keep the ID, FULL_DATE and SALES, so in my database I have 0, 4, 5 which represents their indexes.
Now I need to extract these columns. If I do something like the following
foreach ($this->csvData as $dataKey => &$item) {
foreach ($item as $key => $value) {
print_r($item[4]);
}
}
I will get an undefined index problem as there is no key named 4. If I give it the name of the key, it will work, and show me the value.
So how can I get the value using the key index instead of the name?
Thanks
you could use array_keys and then loop over those keys you said you get from the Database like so:
<?php
$keys = [0, 4, 5];
$data = [
"ID" => "12345",
"CODE" => "AZ6G",
"YEAR" => "2009",
"WEEK" => "13",
"FULL_DATE" => "29/04/2014",
"SALES" => "asdas89.34",
"QUANTITY" => "3"
];
foreach($keys as $key) {
echo $data[array_keys($data)[$key]] . "\n";
}
// outputs:
// 12345
// 29/04/2014
// asdas89.34
Explanation what happens:
array_keys($data)[0]; // is "ID"
// and the "ID" can be used as "key" for the $data array with
$data[array_keys($data)[0]]; // which is $data["ID"]; => "12345"
You can play with it online here: http://sandbox.onlinephpfunctions.com/code/4d6a4d86a6cdceccf4034fca06dcef9e50a89dc8
I need some help wrapping my head around a problem. I have an array filled with other arrays. I need to:
Loop through the entire array and build a new array called finalOptions
Each iteration of the loop will take a new SearchIndex and apply the other paramenters
i.e
SearchIndex => SportingGoods
MinPercentageOff => 50
MinimumPrice => 1
ItemPage => 1
Sort => salesrank
BrowseNode => 2342470011
THEN:
Final array should contain data like this
SearchIndex => SportingGoods
MinPercentageOff => 60
MinimumPrice => 100
ItemPage => 2
Sort => salesrank
BrowseNode => 3403201
Basically, I'm creating a new array and sending it to another method that will execute a call to an API and return a result, then doing it again until my array options are complete.
This might not be the way to go and I'm looking for suggestions/pseudo code on an approach. Here is the basics of what I have so far:
Starting with this code
$allOptions = array(
"SearchIndex" => array("SportingGoods", "Tools"),
"MinPercentageOff" => array("50", "60", "70"),
"MinimumPrice" => array("1", "100", "1000"),
"ItemPage" => array("1", "2"),
"Sort" => array("salesrank")
"BrowseNode" => array(
"SportingGoods" => array("2342470011", "3403201"),
"Tools" => array("511364")
)
)
$finalOptions = array();
foreach($allOptions as $options){
foreach($options["SearchIndex"] as $searchIndex){
$finalOptions[] = "SearchIndex" => $searchIndex[]
}
$this->itemSearch($finalOptions);
}
EDIT
The arrays will contain more values. i.e "ItemPage" => array("1", "2"), will have 1 - 10. The others will have more values as well.
From the given array it will produce 54 possible combinations as you described.
Also you need to make sure you have array in $allOptions['BrowseNode'] indexed as each value of $allOptions['SearchIndex']. Otherwise it will produce error.
Cartesian function from here.
$allOptions = [
"SearchIndex" => ["SportingGoods", "Tools"],
"MinPercentageOff" => ["50", "60", "70"],
"MinimumPrice" => ["1", "100", "1000"],
"ItemPage" => ["1", "2"],
"Sort" => ["salesrank"],
"BrowseNode" => ["SportingGoods" => ["2342470011", "3403201"], "Tools" => ["511364"] ] ];
$finalOptions = $allOptions; // copy our initial $allOptions array
unset($finalOptions['BrowseNode']); // deal with BrowseNode key later with custom iterator
$cartesian_product = cartesian($finalOptions); // find cartesian except BrowseNode
foreach($cartesian_product as $cartesian) // each member of cartesian product will iterate here
{
foreach($allOptions['BrowseNode'][$cartesian['SearchIndex']] as $possible)
/*
We have unset the BrowseNode, so need to refer original $allOptions array for BrowseNode,
In every cartesian product, we will get $cartesian['SearchIndex'] and it will contain either
'SportingGoods' or 'Tools' , so in our original array, look for 'BrowseNode' value, having key
same as $cartesian['SearchIndex'].
$allOptions['BrowseNode'][$cartesian['SearchIndex']] <---- is similar to below two lines
$key = $cartesian['SearchIndex'];
$allOptions['BrowseNode'][$key];
Finally iterate through $allOptions['BrowseNode'][$cartesian['SearchIndex']] will iterate as many times,
as many values there are
*/
{
$cartesian['BrowseNode'] = $possible; // assign the long waited key here to 'BrowseNode'
var_dump($cartesian); // here you can do $this->itemSearch($cartesian);
}
}
function cartesian($input) {
$input = array_filter($input);
/*
will renove any false values in input array,
in our array's case, it will do nothing.
*/
$result = [[]];
foreach ($input as $key => $values) {
$append = [];
foreach($result as $product) {
foreach($values as $item) {
$product [$key] = $item;
$append [] = $product;
}
}
$result = $append;
}
return $result;
}
So I have two array, the first one is like:
$MyArray = [
['id' => 1, number => 32],
['id' => 2, number => 4]
];
and the other is like:
$OtherArray = [
['id' => 1, 'show' => X],
['id' => 5, 'show' => X]
];
Where is X, I want it to be equal with the 'number' value of $MyArray where key 'id' = its id.
If there is no $MyArray.id which is equal to $OtherArray.id then it should return 0.
I hope you understand what I mean. I tried everything, what I could, yet, with no success.
Have you tried using a foreach loop here?
Here is a quick example... PHPaste Snippet
<?php
$firstArray = array(
array(
"id" => 1,
"something" => "Hello, World!"
),
array(
"id" => 3, // 3 on purpose
"something" => "Hello, mom?"
)
);
$secondArray = array(
array(
"id" => 1,
"thing" => null
),
array(
"id" => 2,
"thing" => null
)
);
foreach ($firstArray as $key => $value) {
foreach ($secondArray as $k => $v) {
if ($value['id'] == $v['id']) {
echo "Found one!\n------\n" . print_r($value, true) . "\ncontains the same ID as\n\n" . print_r($v, true) . "\n------\n";
// you may also do this if you want
// $secondArray[$k]['thing'] = $value['id'];
// this would set "thing" (in the second array) to the value of "id" (in the first array)
}
}
}
EDIT Here is a second example, displaying how you could use it as a function... PHPaste Snippet.
Note: I used the OLD array syntax because it's easier for new programmers to understand.
So, essentially what you are doing is iterating through each item in $firstArray, comparing it to each item in $secondArray, by doing a nested foreach within side the first foreach if that makes sense...?
Here is what I just said in simple form:
go through each item in array 1
--> compare it to each item in array 2
You may also notice my use of PHP's lovely function, print_r(). This displays objects and arrays in a slightly, clearer, form.
You can also see that I am getting the values from within the arrays by using $value['id'] and $v['id']. These were defined in my foreach declaration, foreach ($firstArray as $key => $value); $value is an associative array, so you can simply get a value by key just as you would if you created an array like this:
$myArray = [
"id" => 1
];
and grabbed values like this:
echo $myArray['id']; // 1
Hopefully this helped.
I have a variable number of multidimensional arrays but all with the same 4 possible values for each item.
For example:
Array
(
[companyid] => 1
[employeeid] => 1
[role] => "Something"
[name] => "Something"
)
but every array may have a different ammount of items inside it.
I want to turn all the arrays into one single table with lots of rows. I tried array_merge() but I end up with a table with 8, 12, 16... columns instead of more rows.
So... any ideas?
Thanks
Didn't test it, but you could try the following:
$table = array();
$columns = array('companyid' => '', 'employeeid' => '', 'role' => '', 'name' => '');
foreach($array as $item) {
$table[] = array_merge($columns, $item);
}
This should work since the documentation about array_merge say:
If the input arrays have the same string keys, then the later value
for that key will overwrite the previous one.
So you either get the value of the current item or a default value that you can specify in the $columns array.
$array1=Array
(
"companyid" => 1,
"employeeid" => 4,
"role" => "Something",
"name" => "Something",
);
$array2=Array
(
"companyid" => array(2,2,2),
"employeeid" => 5,
"role" => "Something2",
"name" => "Something2"
);
$array3=Array
(
"companyid" => 3,
"employeeid" => 6,
"role" => "Something3",
"name" => "Something3"
);
//Using array_merge
$main_array["companyid"]=array_merge((array)$array1["companyid"],(array)$array2["companyid"],(array)$array3["companyid"]);
$main_array["employeeid"]=array_merge((array)$array1["employeeid"],(array)$array2["employeeid"],(array)$array3["employeeid"]);
for($i=0;$i<count($main_array["companyid"]);$i++)
echo $main_array["companyid"][$i] + "<br />";
for($i=0;$i<count($main_array["employeeid"]);$i++)
echo $main_array["employeeid"][$i] + "<br />";
I've tested the code above and seems right.
You coult also improve this code into a DRY function.