I have this array in php returned from db
Array
(
[inv_templates] => Array
(
[0] => Array
(
[inven_subgroup_template_id] => 1
[inven_group] => Wires
[inven_subgroup] => CopperWires
[inven_template_id] => 1
[inven_template_name] => CopperWires6G
[constrained] => 0
[value_constraints] =>
[accept_range] => 2 - 16
[information] => Measured Manual
)
[1] => Array
(
[inven_subgroup_template_id] => 1
[inven_group] => Wires
[inven_subgroup] => CopperWires
[inven_template_id] => 2
[inven_template_name] => CopperWires2G
[constrained] => 0
[value_constraints] =>
[accept_range] => 1 - 7
[information] => Measured by Automated Calipers
)
)
)
I need to output this kind of multidimensional stuff
Array
(
[Wires] => Array
(
[inv_group_name] => Wires
[inv_subgroups] => Array
(
[CopperWires] => Array
(
[inv_subgroup_id] => 1
[inv_subgroup_name] => CopperWires
[inv_templates] => Array
(
[CopperWires6G] => Array
(
[inv_name] => CopperWires6G
[inv_id] => 1
)
[CopperWires2G] => Array
(
[inv_name] => CopperWires2G
[inv_id] => 2
)
)
)
)
)
)
I currently do this stuff
foreach ($data['inv_templates'] as $key => $value) {
$processeddata[$value['inven_group']]['inv_group_name'] = $value['inven_group'];
$processeddata[$value['inven_group']]['inv_subgroups'][$value['inven_subgroup']]['inv_subgroup_id'] = $value['inven_subgroup_template_id'];
$processeddata[$value['inven_group']]['inv_subgroups'][$value['inven_subgroup']]['inv_subgroup_name'] = $value['inven_subgroup'];
$processeddata[$value['inven_group']]['inv_subgroups'][$value['inven_subgroup']]['inv_templates'][$value['inven_template_name']]['inv_name'] = $value['inven_template_name'];
$processeddata[$value['inven_group']]['inv_subgroups'][$value['inven_subgroup']]['inv_templates'][$value['inven_template_name']]['inv_id'] = $value['inven_template_id'];
}
return $processeddata;
EDIT : A var_export
array (
'inv_templates' =>
array (
0 =>
array (
'inven_subgroup_template_id' => '1',
'inven_group' => 'Wires',
'inven_subgroup' => 'CopperWires',
'inven_template_id' => '1',
'inven_template_name' => 'CopperWires6G',
'constrained' => '0',
'value_constraints' => '',
'accept_range' => '2 - 16',
'information' => 'Measured Manual',
),
1 =>
array (
'inven_subgroup_template_id' => '1',
'inven_group' => 'Wires',
'inven_subgroup' => 'CopperWires',
'inven_template_id' => '2',
'inven_template_name' => 'CopperWires6G',
'constrained' => '0',
'value_constraints' => '',
'accept_range' => '1 - 7',
'information' => 'Measured by Automated Calipers',
),
),
)
The foreach is almost unreadable. There must be a simpler way
$processeddata = array();
foreach($data['inv_templates'] as $key => $value) {
$group = $value['inven_group'];
$processeddata[$group]['inv_group_name'] = $group;
$subgroup = &$processeddata[$group]['inv_subgroups'][$value['inven_subgroup']];
$subgroup['inv_subgroup_id'] = $value['inven_subgroup_template_id'];
$subgroup['inv_subgroup_name'] = $value['inven_subgroup'];
$template = $value['inven_template_name'];
$subgroup['inv_templates'][$template]['inv_name'] = $template;
$subgroup['inv_templates'][$template]['inv_id'] = $value['inven_template_id'];
}
return $processeddata;
Untested code. This structures the array in a multidimensional way, and then uses array_merge_recursive to merge them with the already processed data.
if (!isset($processeddata[$value['inven_group']]))
$processeddata[$value['inven_group']] = array();
$processeddata[$value['inven_group']] = array_merge_recursive(
$processeddata[$value['inven_group']],
array(
'inv_group_name' => $value['inven_group'],
'inv_subgroups' => array(
$value['inven_subgroup'] => array(
'inv_subgroup_id' => $value['inven_subgroup_template_id'],
'inv_subgroup_name' => $value['inven_subgroup'],
'inv_templates' => array(
$value['inven_template_name'] => array(
'inv_name' => $value['inven_template_name'],
'inv_id' => $value['inven_template_id'],
),
),
),
),
)
);
I find this format usually works for me. You could do it more efficient, I've just never cared :D
I started traversing at $yourArray['inv_templates'] though.
function groupToStructure(array $rows, array $keys) {
$tree = array();
$keys = array_reverse($keys);
foreach ($rows as $row) {
$subTree = array($row);
foreach ($keys as $key) {
$subTree = array($row[$key] => $subTree);
}
$tree = array_merge_recursive($tree, $subTree);
}
return $tree;
}
print_r(groupToStructure($rows, array('inven_group', 'inven_subgroup', 'inven_template_name')));
Related
I have a multidimensional array with key and value and some key is empty also. Then I want to set a value for internal not empty array.
$oldArray = array("Lexus LS600" => array(),
"Toyota Alphard" => array(),
"Benz S550" => array(0 => array(
"card_no" => "G2FPCBS3",
"travel_date" => "2020-09-10"
"travel_time" => "16:15:00",
"car_id" => 12,
"return_time" => "17:25")),
"BMW X6" => array());
I had this array but I want to set return_time 00:00 all over array. I tried foreach loop but foreach is remove empty array but I want empty array also.
I want this type array:-
$newArray = array("Lexus LS600" => array(),
"Toyota Alphard" => array(),
"Benz S550" => array(0 => array(
"card_no" => "G2FPCBS3",
"travel_date" => "2020-09-10"
"travel_time" => "16:15:00",
"car_id" => 12,
"return_time" => "00:00")),
"BMW X6" => array());
Try this foreach again, I think it will solve your problem if I understood you correctly.
foreach ($arrays as $key => $values) {
if (is_array($values)) {
if (count($values)) {
foreach ($values as $index => $data) {
$arrays[$key][$index]['return_time'] = "00:00";
}
} else {
$arrays[$key] = $values;
}
}
}
It will change return_time to "00:00" and also retain the empty index to your array.
array_walk_recursive() is very suitable for this.
$oldArray = array("Lexus LS600" => array(),
"Toyota Alphard" => array(),
"Benz S550" => array(0 => array(
"card_no" => "G2FPCBS3",
"travel_date" => "2020-09-10",
"travel_time" => "16:15:00",
"car_id" => 12,
"return_time" => "17:25")),
"BMW X6" => array());
$keySearch = "return_time";
$replaceWith = "00:00";
array_walk_recursive(
$oldArray,
function(&$val,$key) use($keySearch,$replaceWith){
if($key == $keySearch) $val = $replaceWith;
}
);
var_export($oldArray);
Output:
array (
'Lexus LS600' =>
array (
),
'Toyota Alphard' =>
array (
),
'Benz S550' =>
array (
0 =>
array (
'card_no' => 'G2FPCBS3',
'travel_date' => '2020-09-10',
'travel_time' => '16:15:00',
'car_id' => 12,
'return_time' => '00:00',
),
),
'BMW X6' =>
array (
),
)
Use two foreach loops to traverse the limited-depth array and make all values modifiable by reference (& before the variable). In doing so, you don't need to create a separate array, just update the input array. It is SUPER easy to read and maintain.
Code: (Demo)
foreach ($array as &$cars) {
foreach ($cars as &$entry) {
if ($entry) {
$entry["return_time"] = "00:00";
}
}
}
var_export($array);
Output:
array (
'Lexus LS600' =>
array (
),
'Toyota Alphard' =>
array (
),
'Benz S550' =>
array (
0 =>
array (
'card_no' => 'G2FPCBS3',
'travel_date' => '2020-09-10',
'travel_time' => '16:15:00',
'car_id' => 12,
'return_time' => '00:00',
),
),
'BMW X6' =>
array (
),
)
I have an array with some repeating string values. How to replace these string values (as a whole, because some words are repeated in others strings) with corresponding specific numeric values, as bellow?
deloc = 1
foarte puţin = 2
mediu = 3
mult = 4
foarte mult = 5
This is the array (example):
array = (
"tensionat" => "mediu",
"trist" => "mult",
"melancolic" => "deloc",
"fara_speranta" => "foarte puțin",
"nefolositor"] => "deloc",
"ingrijorat" => "foarte mult",
"amarat" => "deloc",
"anxios" => "mediu"
);
How can this
Try this
$data = array (
"tensionat" => "mediu",
"trist" => "mult",
"melancolic" => "deloc",
"fara_speranta" => "foarte puțin",
"nefolositor" => "deloc",
"ingrijorat" => "foarte mult",
"amarat" => "deloc",
"anxios" => "mediu"
);
$repl = array (
'deloc' => 1,
'foarte puţin' => 2,
'mediu' => 3,
'mult' => 4,
'foarte mult' => 5,
);
$result = array ();
foreach ($data as $key => $value) {
$result[$key] = !empty($repl[$value]) ? $repl[$value] : $value;
}
print_r($result);
Output:
Array
(
[tensionat] => 3
[trist] => 4
[melancolic] => 1
[fara_speranta] => foarte puțin
[nefolositor] => 1
[ingrijorat] => 5
[amarat] => 1
[anxios] => 3
)
I have data like this :
[1] => Array
(
[COMPANY_SERVICE_ID] => CS01
[COMPANY_NAME] => HANOMAN SAKTI PRATAMA, PT - JAKARTA
[TARIFF_CURRENCY] => IDR
[SELLING_SERVICE_ID] => SS01
[CONTAINER_TYPE_ID] => DC
[SERVICE_NAME] => CONTAINER TRUCKING SERVICE
[FROM_QTY] => 1
[TO_QTY] => 100
[FROM_NAME] => TANJUNG PRIOK
[FROM_LOCATION_ID] => L096
[TO_NAME] => BALARAJA
[TO_LOCATION_ID] => L002
[RESULT_LOCATION] => Array
(
[L001] => Array
(
[TARIF_20] => 1.500.000,00
[TARIF_40] => 1.750.000,00
[TARIF_45] => 5.500.000,00
[TARIF_4H] => 3.500.000,00
)
[L002] => Array
(
[TARIF_20] => 500.000,00
)
)
)
i wanna unset value of RESULT_LOCATION if value in RESULT_LOCATION different with value of TO_LOCATION_ID.
What should i do?
i try to remove with code like this :
foreach ($hasil_jakarta as $key => $value) {
foreach ($value['RESULT_LOCATION'] as $key1 => $value1) {
if ($value['TO_LOCATION_ID'] != $value['RESULT_LOCATION'][$key1]) {
unset($hasil_jakarta[$key]['RESULT_LOCATION'][$key1]);
}
}
}
but all value of RESULT_LOCATION deleted. Whats wrong with my code?
You don't have to test the value but the key. Then, unset() arrays with different keys.
Here is an example :
<?php
$a = array(
'COMPANY_SERVICE_ID' => 'CS01',
'COMPANY_NAME' => 'HANOMAN SAKTI PRATAMA, PT - JAKARTA',
'TARIFF_CURRENCY' => 'IDR',
'SELLING_SERVICE_ID' => 'SS01',
'CONTAINER_TYPE_ID' => 'DC',
'SERVICE_NAME' => 'CONTAINER TRUCKING SERVICE',
'FROM_QTY' => 1,
'TO_QTY' => 100,
'FROM_NAME' => 'TANJUNG PRIOK',
'FROM_LOCATION_ID' => 'L096',
'TO_NAME' => 'BALARAJA',
'TO_LOCATION_ID' => 'L002',
'RESULT_LOCATION' => array(
'L001' => array(
'TARIF_20' => '1.500.000,00',
'TARIF_40' => '1.750.000,00',
'TARIF_45' => '5.500.000,00',
'TARIF_4H' => '3.500.000,00'
),
'L002' => array(
'TARIF_20' => '500.000,00'
)
)
);
foreach ($a['RESULT_LOCATION'] as $key => $value) {
if ($key != $a['TO_LOCATION_ID']) {
unset($a['RESULT_LOCATION'][$key]);
}
}
The result will be :
php > print_r($a);
Array
(
[COMPANY_SERVICE_ID] => CS01
[COMPANY_NAME] => HANOMAN SAKTI PRATAMA, PT - JAKARTA
[TARIFF_CURRENCY] => IDR
[SELLING_SERVICE_ID] => SS01
[CONTAINER_TYPE_ID] => DC
[SERVICE_NAME] => CONTAINER TRUCKING SERVICE
[FROM_QTY] => 1
[TO_QTY] => 100
[FROM_NAME] => TANJUNG PRIOK
[FROM_LOCATION_ID] => L096
[TO_NAME] => BALARAJA
[TO_LOCATION_ID] => L002
[RESULT_LOCATION] => Array
(
[L002] => Array
(
[TARIF_20] => 500.000,00
)
)
)
Hope it helps.
EDIT
I saw your snippet and adapt the loop for your needs :
foreach ($hasil_jakarta as $h_j_key => $h_j_value) {
foreach ($h_j_value['RESULT_LOCATION'] as $key => $value) {
if ($key != $h_j_value['TO_LOCATION_ID']) {
unset($hasil_jakarta[$h_j_key]['RESULT_LOCATION'][$key]);
}
}
}
Your code was almost good but the unset line was not. In that case, you need to unset a variable from the $hasil_jakarta array.
Good luck !
I have an array with same customerid. I want to merge all same customerid arrays in to one with few amends to the array.
Array
(
[0] => Array
(
[customerid] => 13
[customer_fullname] => Chris
[profession_id] => 8
[profession_name] => Producer
)
[1] => Array
(
[customerid] => 1
[customer_fullname] => John
[profession_id] => 8
[profession_name] => Producer
)
[2] => Array
(
[customerid] => 13
[customer_fullname] => Chris
[profession_id] => 7
[profession_name] => Camera
)
)
So now I want a new array to be created like this:
Array(
[customerid] => 13
[customer_fullname] => Chris
[new_array] => array(
[0]=>[profession_id] => 8, [profession_name] => Producer,
[1]=>[profession_id] => 7, [profession_name] => Camera
)
)
Spent some time on it but wasn't able to get it right
There are better approaches if you're merging lots of records, but if you want a way to just merge two records as stated, I'd just do this:
$array1 = array(
'customerid' => 13
'customer_fullname' => 'John',
'profession_id' => 8,
'profession_name' => 'Producer'
);
$array2 = array(
'customerid' => 13
'customer_fullname' => 'John',
'profession_id' => 7,
'profession_name' => 'Director'
);
function merge_customers($customerA, $customerB)
{
$newCustomer = array();
if ($customerA['customerid'] == $customerB['customerid'])
{
$newCustomer['customerid'] = $customerA['customerid'];
$newCustomer['customer_fullname'] = $customerA['customer_fullname'];
$newCustomer['new_array'] = array(
array(
'profession_id' => $customerA['profession_id'],
'profession_name' => $customerA['profession_name']
),
array(
'profession_id' => $customerB['profession_id'],
'profession_name' => $customerB['profession_name']
)
);
return $newCustomer;
}
/* We can't merge these if they're different customers. */
return NULL;
}
The extended solution which is also well-suited for finding and "merging" multiple groups of entries which has same customerid. Used functions: array_filter, array_count_values, array_keys, array_walk, array_chunk and array_values:
// supposing $arr is your initial array
// finds which 'customerid' has multiple entries
$dupIds = array_filter(array_count_values(array_column($arr, "customerid")), function($v) {
return $v > 1;
});
$dupIds = array_keys($dupIds);
$result = [];
array_walk($arr, function($v) use(&$result, $dupIds) {
if (in_array($v['customerid'], $dupIds)) {
$parts = array_chunk($v, 2, true);
if (!isset($result[$v['customerid']])) {
$result[$v['customerid']] = $parts[0] + ['new_array' => [$parts[1]]];
} else {
$result[$v['customerid']]['new_array'][] = $parts[1];
}
}
});
print_r(array_values($result));
The output:
Array
(
[0] => Array
(
[customerid] => 13
[customer_fullname] => Chris
[new_array] => Array
(
[0] => Array
(
[profession_id] => 8
[profession_name] => Producer
)
[1] => Array
(
[profession_id] => 7
[profession_name] => Camera
)
)
)
)
Quick hack, maybe there is a nicer solution.
Note: The second "for each" loop is only needed if there is the possibility that the arrays don't have the same fields.
function merge($array1, $array2){
$result = array();
foreach($array1 as $key => $value){
if(isset($array2[$key]) && $array2[$key]!=$array1[$key]){
$result[$key][]=$value;
$result[$key][]=$array2[$key];
}else{
$result[$key]=$value;
}
}
foreach($array2 as $key => $value){
if(!isset($result[$key])){
$result[$key] = $value;
}
}
return $result;
}
print_r(merge($array1, $array2));
I have nested structure very similar to folder structure, like:
Array
(
[level_one_1] => Array
(
[level_two_1] => value1
[level_two_2] => valuetwo
[level_two_3] => value_three
)
[level_one_2] => Array
(
[level_two_4] => value1
[level_two_5] => valuetwo
[level_two_6] => value_three
)
[level_one_3] => Array
(
[level_two_2] => valuetwo
[level_two_3] => value_three
)
)
Is it a quick way to covert it to something like this:
Array
(
[level_one_1/level_two_1] => value1
[level_one_1/level_two_2] => valuetwo
[level_one_1/level_two_3] => value_three
[level_one_2/level_two_4] => value1
[level_one_2/level_two_5] => valuetwo
[level_one_2/level_two_6] => value_three)
[level_one_3/level_two_2] => valuetwo
[level_one_3/level_two_3] => value_three
)
Slash between levels would be separator - it could anything. Also it would be dynamic numbers of levels.
Is it a way to do so by using predefined array* functions ? with recursion ?
Something like this. Untested, but should help you get started in the right direction:
$myArray = array(
'level_one_1' => array(
'level_two_1' => 'value1',
'level_two_2' => 'valuetwo',
'level_two_3' => 'value_three'
),
'level_one_2' => array(
'level_two_4' => 'value1',
'level_two_5' => 'valuetwo',
'level_two_6' => 'value_three'
),
'level_one_3' => array(
'level_two_2' => 'valuetwo',
'level_two_3' => 'value_three'
));
$ritit = new RecursiveIteratorIterator(new RecursiveArrayIterator($myArray));
$result = array();
foreach ($ritit as $leafValue) {
$keys = array();
foreach (range(0, $ritit->getDepth()) as $depth) {
$keys[] = $ritit->getSubIterator($depth)->key();
}
$result[ join('/', $keys) ] = $leafValue;
}