Let say I have the datas in JSON,
3 people have different datas such as New only / New and Old / Old and New.
I tried using isset($_GET['NoID']); which is
http://localhost/test.php?NoID=31331 // Stan Lee
http://localhost/test.php?NoID=31332 // Mary Jane
http://localhost/test.php?NoID=31335 // John Doe
And the result are:
// Stan Lee
{
- Table: [
- {
Name: "Stan Lee",
NoID: "31331",
Type: "New",
- #attributes: {
id: "Table1",
rowOrder: "0",
}
},
]
}
// Mary Jane
{
- Table: [
- {
Name: "Mary Jane",
NoID: "31332",
Type: "New",
- #attributes: {
id: "Table1",
rowOrder: "0",
}
},
- {
Name: "Mary Jane",
NoID: "31333",
Type: "Old",
- #attributes: {
id: "Table2",
rowOrder: "1",
}
},
]
}
// John Doe
{
- Table: [
- {
Name: "John Doe",
NoID: "31334",
Type: "Old",
- #attributes: {
id: "Table1",
rowOrder: "0",
}
},
- {
Name: "John Doe",
NoID: "31335",
Type: "New",
- #attributes: {
id: "Table2",
rowOrder: "1",
}
},
]
}
I want to return which is condition is New only (Single row).
I tried to foreach() then strict statement for New and break, also I tried array_filter() and sort(). Those function didn't work out to return New only.
My code I tried so far:
foreach ($data['Table'] as $value) {
if (is_array($value) && $value['Type'] == "New") {
json($value);
break;
} elseif (is_string($value)) {
json($value);
break;
}
}
And the output is
Notice: Undefined index: Type
"New"
Both Mary Jane & John Doe gimme the right output, but Stan Lee didn't work.
Anyone can help me out?
Thank you!
hi bro i have checked you code and i just remove the break try this:
$data = ["Table" => [[
"Name" => "Stan Lee",
"NoID" => "31331",
"Type" => "New",
"attributes" =>[
"id"=>"Table1",
"rowOrder"=> "0"
]
],
[
"Name" => "Mary Jane",
"NoID" => "31332",
"Type" => "New",
"attributes" =>[
"id"=>"Table1",
"rowOrder" => "0"
]
],
[
"Name" => "Mary Jane",
"NoID" => "31333",
"Type" => "Old",
"attributes" =>[
"id"=>"Table2",
"rowOrder" =>"1"
]
],
[
"Name" => "John Doe",
"NoID" => "31334",
"Type" => "Old",
"attributes" =>[
"id"=>"Table1",
"rowOrder"=>"0"
]
],
[
"Name" => "John Doe",
"NoID" => "31335",
"Type" => "New",
"attributes" =>[
"id"=>"Table2",
"rowOrder" => "1"
]
],
]
];
foreach ($data['Table'] as $value) {
if (is_array($value) && $value['Type'] == "New") {
echo '<pre>';
print_r($value);
echo '</pre>';
} elseif (is_string($value)) {
echo '<pre>';
print_r($value);
echo '</pre>';
break;
}
}
and here is the output:
Array
(
[Name] => Stan Lee
[NoID] => 31331
[Type] => New
[attributes] => Array
(
[id] => Table1
[rowOrder] => 0
)
)
Array
(
[Name] => Mary Jane
[NoID] => 31332
[Type] => New
[attributes] => Array
(
[id] => Table1
[rowOrder] => 0
)
)
Array
(
[Name] => John Doe
[NoID] => 31335
[Type] => New
[attributes] => Array
(
[id] => Table2
[rowOrder] => 1
)
)
Let me know if this is what you need. feel free to ask.
Remove the break; from the foreach() loop.
break will interrupt the loop and no more array keys/values are treated anymore.
PHP break
edit
Probable you do not want to sent the json each time the condition is met.
So before the foreach() create variable $output and collect matched values to it $output[] = $value;. And finally send the whole output using json($output);
<?php
$data = [
"Table" => [
"Type" => "New"
],
[
1 => ["Type" => "New"],
2 => ["Type" => "Old"],
],
[
1 => ["Type" => "Old"],
2 => ["Type" => "New"],
]
];
foreach ($data['Table'] as $key => $value) {
If($key == 'Type' and $value == 'New'){
$output[] = $value;
}
Maybe this will help you:
$newArray = array();
foreach($data as $key => $d){
if(sizeof($d) > 1){
foreach($d as $key1 => $d1){
if(strtolower($d1['Type']) == 'new'){
$newArray[$key1]['Type'] = $d1['Type'];
}
}
}else{
if(strtolower($d['Type']) == 'new'){
$newArray[$key]['Type'] = $d['Type'];
}
}
}
print_r(json_encode($newArray));
Solution:
function arraySearch($array,$keyword="type",$value="New",$results=[]) {
foreach ( $array as $key => $val ) {
if(is_array($val)){
if(array_key_exists($keyword,$val)){
if ($val[$keyword] === $value ) {
$results[] = $key;
}
}else{
arraySearch($array,$keyword,$value,$results);
}
}
}
return json($results);
}
Call to function:
echo arraySearch($data['Table']);
Use array_filter like this, demo
array_filter($data, function($v){
return count($v) == 1 && $v['Type'] == 'New';
})
<?php
foreach ($data['Table'] as $value) {
foreach ($value as $data) {
if(in_array('New', $data)) {
//here you can code
echo "<pre>";
print_r($data);
}
}
}
Result: [{"0":"New","1":"New","4":"New"}]
<?php
$data = ["Table" => [[
"Name" => "Stan Lee",
"NoID" => "31331",
"Type" => "New",
"attributes" =>[
"id"=>"Table1",
"rowOrder"=> "0"
]
],
[
"Name" => "Mary Jane",
"NoID" => "31332",
"Type" => "New",
"attributes" =>[
"id"=>"Table1",
"rowOrder" => "0"
]
],
[
"Name" => "Mary Jane",
"NoID" => "31333",
"Type" => "Old",
"attributes" =>[
"id"=>"Table2",
"rowOrder" =>"1"
]
],
[
"Name" => "John Doe",
"NoID" => "31334",
"Type" => "Old",
"attributes" =>[
"id"=>"Table1",
"rowOrder"=>"0"
]
],
[
"Name" => "John Doe",
"NoID" => "31335",
"Type" => "New",
"attributes" =>[
"id"=>"Table2",
"rowOrder" => "1"
]
],
]
];
$build = [];
$output = [];
$i= 0;
foreach ($data as $value) {
foreach ( $value as $key => $val) {
if(!is_array($val) AND $val== "New"){
$build[$i][0] = $val;
$output = $build;
}else if(is_array($val) AND $val["Type"] === "New"){
$build[$i][$key] = "New";
$output = $build;
}
}
$i++;
}
print_r(json_encode($output));
?>
Related
I have nth level of nested array with string naming key , I want to convert that in indexing key only for array of item key.
i tried it to convert but that conversation only possible for limited level of nested array rather than nth level .
Input array:
$input_array= [
"NOCPL-All -working" => [
"name" => "NOCPL-All -working",
"item" => [
"apis for web" => [
"name" => "apis for web",
"item" => [
"0" => [
"name" => "update user branch maps"
]
]
],
"update user web" => [
"name" => "update user web",
"item" => [
"0" => [
"name" => "update user"
],
"1" => [
"name" => "add user"
]
]
]
]
]
];
I tried below code to convert indexing of 'item' nested array for limited level
function cleanArrayKeys($arr) {
foreach($arr as $k=>$arr1) {
if(isset($arr[$k]['item'])) {
$arr[$k]['item'] = array_values($arr[$k]['item']);
foreach($arr[$k]['item'] as $k1=>$arr2) {
if(isset($arr[$k]['item'][$k1]['item'])) {
$arr[$k]['item'][$k1]['item'] = array_values($arr[$k]['item'][$k1]['item']);
foreach($arr[$k]['item'][$k1]['item'] as $k3=>$arr3) {
if(isset($arr[$k]['item'][$k1]['item'][$k3]['item'])) {
$arr[$k]['item'][$k1]['item'][$k3]['item'] = array_values($arr[$k]['item'][$k1]['item'][$k3]['item']);
foreach($arr[$k]['item'][$k1]['item'][$k3]['item'] as $k4=>$arr4) {
if(isset($arr[$k]['item'][$k1]['item'][$k3]['item'][$k4]['item'])) {
$arr[$k]['item'][$k1]['item'][$k3]['item'][$k4]['item'] = array_values($arr[$k]['item'][$k1]['item'][$k3]['item'][$k4]['item']);
foreach($arr[$k]['item'][$k1]['item'][$k3]['item'][$k4]['item'] as $k5=>$arr5) {
if(isset($arr[$k]['item'][$k1]['item'][$k3]['item'][$k4]['item'][$k5]['item'])) {
$arr[$k]['item'][$k1]['item'][$k3]['item'][$k4]['item'][$k5]['item'] = array_values($arr[$k]['item'][$k1]['item'][$k3]['item'][$k4]['item'][$k5]['item']);
}
}
}
}
}
}
}
}
}
}
return $arr;
}
print_r(cleanArrayKeys($input_array));
?>
Expected Output :
[
"NOCPL-All -working" => [
"name" => "NOCPL-All -working",
"item" => [
"0" => [
"name" => "apis for web",
"item" => [
"0" => [
"name" => "update user branch maps"
],
"1" => [
"name" => "add user branch maps"
]
]
],
"1" => [
"name" => "update user web",
"item" => [
"0" => [
"name" => "update user"
]
]
]
]
]
];
Try using a recursion:
function aValues(&$arr) {
if (array_key_exists('item', $arr)) {
$arr['item'] = array_values($arr['item']);
}
foreach ($arr['item'] as &$el) {
if (array_key_exists('item', $el)) {
aValues($el);
}
}
}
aValues($input_array);
print_r($input_array);
I have an array with fields
[
"house" => "30|30|30",
"street" => "first|second|third",
...
]
I want to get array
[
[
"house" => "30",
"street" => "first",
...
],
[
"house" => "30",
"street" => "second",
...
],
[
"house" => "30",
"street" => "third",
...
]
]
I know how I can solve this using PHP and loop, but maybe this problem has more beautiful solution
use zip
$data = [
"house" => "30|30|30",
"street" => "first|second|third",
];
$house = collect(explode('|',$data['house']));
$street = collect(explode('|',$data['street']));
$out = $house->zip($street);
$out->toarray();
Here's something I managed to do with tinker.
$original = [
"house" => "30|30|30",
"street" => "first|second|third",
];
$new = []; // technically not needed. data_set will instantiate the variable if it doesn't exist.
foreach ($original as $field => $values) {
foreach (explode('|', $values) as $index => $value) {
data_set($new, "$index.$field", $value);
}
}
/* dump($new)
[
[
"house" => "30",
"street" => "first",
],
[
"house" => "30",
"street" => "second",
],
[
"house" => "30",
"street" => "third",
],
]
*/
I tried using collections, but the main problem is the original array's length is not equal to the resulting array's length, so map operations don't really work. I suppose you can still use each though.
$new = []; // Since $new is used inside a Closure, it must be declared.
collect([
"house" => "30|30|30",
"street" => "first|second|third",
...
])
->map(fn($i) => collect(explode('|', $i))
->each(function ($values, $field) use (&$new) {
$values->each(function ($value, $index) use ($field, &$new) {
data_set($new, "$index.$field", $value);
});
});
$array = ["house" => "30|30|30","street" => "first |second| third"];
foreach($array as $key=> $values){
$explodeval = explode('|',$values);
for($i=0; $i<count($explodeval); $i++){
$newarray[$i][$key]= $explodeval[$i];
}
}
output:
Array
(
[0] => Array
(
[house] => 30
[street] => first
)
[1] => Array
(
[house] => 30
[street] => second
)
[2] => Array
(
[house] => 30
[street] => third
)
)
i have 1 array like below :
0 => array:4 [
"id" => "1"
"date" => "2021-08-03"
"from_time" => "09"
"to_time" => "14"
]
1 => array:4 [
"id" => "2"
"date" => "2021-08-03"
"from_time" => "09"
"to_time" => "14"
]
now what i want to do ?? as you can see the date and from_time and to_time have the same value . i want to merge them to 1 item like below :
0 => array:4[
"date" => "2021-08-03"
"from_time" => "09"
"to_time" => "14"
"id" => ["1" , "2"]
].
so i can have the same day ids in 1 index of array and if for example the same date and time got 4 ids i get the id key with 4ids . i used array_merge_recursive but it didnt help me with the same keys of an array
this is how i am building the array :
foreach ($arrays as $key => $array) {
$options[$key]['id'] = last(str_split($array['id']));
$options[$key]['date'] = substr($array['id'],0,-2);
$options[$key]['from_time'] = Carbon::createFromTimestamp($array['pickup']['from'])->format('H');
$options[$key]['to_time'] = Carbon::createFromTimestamp($array['pickup']['to'])->format('H');
}
. thanks in advance for help
<?php
//define items
$items = [
[
"id" => "1",
"date" => "2021-08-03",
"from_time" => "09",
"to_time" => "14",
],[
"id" => "2",
"date" => "2021-08-03",
"from_time" => "09",
"to_time" => "14",
]
];
$options = [];
//loop through the items
foreach ($items as $item) {
//set up the hashing key to use to locate if we hit dup entry
$key = "{$item['date']}-{$item['from_time']}-{$item['to_time']}";
//if indexing key not in options = never looked at it before
if (!array_key_exists($key, $options)) {
//have the key points to the current entry
$options[$key] = $item; //attach the whole item to it
//we want the id to be an array to initialize it to be one
$options[$key]['id'] = [];
}
//gets here then we know options[$key] exists
//if the item id not in the id array of our dict
if (!in_array($item['id'], $options[$key]['id'])) {
//add to it
$options[$key]['id'][] = $item['id'];
}
}
//array_values to get the values and not worry about the keys
print_r(array_values($options));
You can do something like this:
$arr = [
[
"id" => "1",
"date" => "2021-08-03",
"from_time" => "09",
"to_time" => "14"
],
[
"id" => "2",
"date" => "2021-08-03",
"from_time" => "09",
"to_time" => "14"
],
[
"id" => "3",
"date" => "2021-08-03",
"from_time" => "14",
"to_time" => "16"
]
];
$res = array_reduce($arr, function($carry, $entry) use(&$arr) {
$matches = array_filter($arr, function($item) use($entry) {
return $item['from_time'] === $entry['from_time'] && $item['to_time'] && $entry['to_time'];
});
//print_r([ $entry['id'], $matches ]);
foreach($matches as $match) {
unset($arr[array_search($match['id'], array_column($matches, 'id'))]);
}
if (!count($matches)) {
return $carry;
}
$carry[] = [
'id' => array_column($matches, 'id'),
'date' => $entry['date'],
'from_time' => $entry['from_time'],
'to_time' => $entry['to_time'],
];
return $carry;
}, []);
Here is the thing I trying deal with
I have array which looks like this and have duplicates
$products = [
[
"product_name" => "Adidas1",
"address" => "street 2"
],
[
"product_name" => "Adidas2",
"address" => "street 2"
],
[
"product_name" => "Adidas3",
"address" => "street 2"
],
[
"product_name" => "Adidas4",
"address" => "street 2"
],
[
"product_name" => "Nike1",
"address" => "street name1"
],
[
"product_name" => "Nike2",
"address" => "street name1"
]];
Result that I need to get is below .
I did try different ways to do it but still can bring it to the finel result that have to come up
$final_result = [
[
"address" => "street 2",
"products" => [
"addidas1",
"addidas2",
"addidas3",
"addidas4",
]
],
[
"address" => "street name1",
"products" => [
"Nike1",
"Nike2",
]
]
any suggestion how to do it ?
here is my best solution that I tried
$stor_sorted = array();
foreach ($products as $product) {
if (array_count_values($product) > 1) {
$stor_sorted[] = ["address" => $product['address'], "items" => [$product['product_name']]];
}
}
try this code
$products = [
[
"product_name" => "Adidas1",
"address" => "street 2"
],
[
"product_name" => "Adidas2",
"address" => "street 2"
],
[
"product_name" => "Adidas3",
"address" => "street 2"
],
[
"product_name" => "Adidas4",
"address" => "street 2"
],
[
"product_name" => "Nike1",
"address" => "street name1"
],
[
"product_name" => "Nike2",
"address" => "street name1"
]];
$final_result = [];
foreach ($products as $pr){
$original_key = array_search($pr['address'], array_column($final_result, 'address'), true);
if($original_key === false){
$temp_array['address'] = $pr['address'];
$temp_array['products'] = [$pr['product_name']];
$final_result[] =$temp_array;
}else{
$final_result[$original_key]['products'][] = $pr['product_name'];
}
}
your result will be in final_result array
Use address values as temporary keys in your result array.
When an address is encountered for the first time, cast the product name as an array within the row and store the row.
On subsequent encounters, merely push the product name into the group's subarray.
When finished, re-index the result with array_values().
Code: (Demo)
$result = [];
foreach ($products as $row) {
if (!isset($result[$row['address']])) {
$row['product_name'] = (array)$row['product_name'];
$result[$row['address']] = $row;
} else {
$result[$row['address']]['product_name'][] = $row['product_name'];
}
}
var_export(array_values($result));
Same output with a body-less foreach() using array destructuring: (Demo)
$result = [];
foreach (
$products
as
[
'address' => $key,
'address' => $result[$key]['address'],
'product_name' => $result[$key]['product_name'][]
]
);
var_export(array_values($result));
Same output with functional style programming and no new globally-scoped variables: (Demo)
var_export(
array_values(
array_reduce(
$products,
function($result, $row) {
$result[$row['address']]['product_name'] = $row['product_name'];
$result[$row['address']]['address'][] = $row['address'];
return $result;
}
)
)
);
I have an array that looks like this
"name" => array:3 [
1 => "Hello"
4 => "Test"
21 => "Test2"
]
"runkm" => array:3 [
1 => "100.00"
4 => "1000.00"
21 => "2000.00"
]
"active" => array:3 [
1 => "1"
4 => "0"
21 => "0"
]
Can i somehow combine the matching keys with a PHP function so that the array would look like this instead
1 => array:3 [
name => "Hello"
runkm => "100.00"
active => "1"
]
4 => array:3 [
name => "Test"
runkm => "1000.00"
active => "0"
]
21 => array:3 [
name => "Test2"
runkm => "2000.00"
active => "0"
]
EDIT: Thanks for all the answers guys. What i was really looking for was a PHP built in function for this, which i probably should have been more clear about.
$newArr=array();
foreach($array1 as $key => $value){
$newArr[$key]=>array(
'name' =>$value[$key];
'runkm' =>$array2[$key];
'active'=>$array3[$key];
);
}
this is how you make a new array and then print the $newArr and check you get what you want or not? Good Luck!
<?php
$resultarr = array();
for($i=0;$i<count($sourcearr['name']);$i++) {
$resultarr[] = array('name'=>$sourcearr['name'][$i], 'runkm'=>$sourcearr['runkm'][$i], 'active'=>$sourcearr['active'][$i]);
}
This works well. And also, doesn't use hard coded keys.
<?php
$arr = [
"name" => [
1 => "Hello",
4 => "Test",
21 => "Test2"
],
"runkm" => [
1 => "100.00",
4 => "1000.00",
21 => "2000.00"
],
"active" => [
1 => "1",
4 => "0",
21 => "0"
]
];
// Pass the array to this function
function extractData($arr){
$newarr = array();
foreach ($arr as $key => $value) {
foreach($value as $k => $v) {
if(!isset($newarr[$k]))
$newarr[$k] = array();
$newarr[$k][$key] = $v;
}
}
return $newarr;
}
print_r(extractData($arr));
?>
I'm not sure if there's a function that does that in PHP but maybe you can try this
$arr1 = array(
"name" => array(
1 => "hello",
4 => "test",
21 => "test2",
),
"runKm" => array(
1 => "100",
4 => "200",
21 => "300",
),
"active" => array(
1 => "1",
4 => "0",
21 => "0",
),
);
// declare another that will hold the new structure of the array
$nArr = array();
foreach($arr1 as $key => $val) {
foreach($val as $sub_key => $sub_val) {
$nArr[$sub_key][$key] = $sub_val;
}
}
what this does is simply loop thru each array and its values and assign it to another array which is the $nArr. I hope it helps.