get max an min values from php array [duplicate] - php

This question already has answers here:
Get min and max value in PHP Array
(9 answers)
Closed 4 months ago.
I have the following array $data. n and 0 are identical, it's just the way the data is returned. I need to determine the max and min values for the id value, it looks like the id values are stored as strings, how is this achieved?
Array
(
[0] => stdClass Object
(
[n] => artefact[10.3]{"id": "1", "name": "001", "type": "Artefact"}
[0] => artefact[10.3]{"id": "1", "name": "001", "type": "Artefact"}
)
[1] => stdClass Object
(
[n] => artefact[10.4]{"id": "2", "name": "002", "type": "Artefact"}
[0] => artefact[10.4]{"id": "2", "name": "002", "type": "Artefact"}
)
[2] => stdClass Object
(
[n] => artefact[10.5]{"id": "3", "name": "003", "type": "Artefact"}
[0] => artefact[10.5]{"id": "3", "name": "003", "type": "Artefact"}
)
)

It seems that {"id":....} is a JSON value, and we need to parse the value and collect IDs. Before we need to clean artefact string with preg_replace function. In this case, we can determine max and min values:
<?php
$data = [
[
'0'=>'artefact[10.3]{"id": "1", "name": "001", "type": "Artefact"}',
'n'=>'artefact[10.3]{"id": "1", "name": "001", "type": "Artefact"}',
],
[
'0'=>'artefact[10.4]{"id": "1", "name": "001", "type": "Artefact"}',
'n'=>'artefact[10.4]{"id": "3", "name": "001", "type": "Artefact"}',
],
];
$ids = [];
foreach ($data as $datum) {
foreach ($datum as $item) {
$parsedItem = preg_replace("/artefact\[(.+?)\]/",'',$item);
$jsonDecoded = json_decode($parsedItem);
$ids[] = $jsonDecoded->id;
}
}
$maxId = $ids ? max($ids):0;
$minId = $ids ? min($ids):0;
echo "Max id: $maxId <br> Min id $minId ";

Related

PHP - Slice nested array

I have two nested arrays with different length. I want to make length of second array as per first array, see below examples to get idea. Just remove all those items which don't exist in first array. Sometime second array has more values then first array, in this case my tree structure breaks.
These arrays are nested array so simple array_slice not working.
Here are the structure of array.
First Array
"1": {
"id": "1",
"username": "username",
"children": [
{
"id": "-1",
"username": "NULL",
"children": [
{
"id": "-1",
"username": "NULL",
"children": [
{
"id": "-1",
"username": "NULL",
"children": []
}
]
}
]
}
]
}
Second Array
"157": {
"id": "157",
"username": "test1",
"children": [
{
"id": "158",
"username": "test1",
"children": [
{
"id": "159",
"username": "test2",
"children": [
{
"id": "160",
"username": "test3",
"children": []
},
{
"id": "160",
"username": "KICK ME BECAUSE I M NOT EXIST IN FIRST ARRAY",
"children": []
}
]
}
]
},
{
"id": "160",
"username": "KICK ME BECAUSE I M NOT EXIST IN FIRST ARRAY",
"children": [
{
"id": "159",,
"username": "KICK ME BECAUSE I M NOT EXIST IN FIRST ARRAY",
"children": [
{
"id": "161",
"username": "KICK ME BECAUSE I M NOT EXIST IN FIRST ARRAY",
"children": []
}
]
}
]
}
]
}
Expected Output
"157": {
"id": "157",
"username": "test1",
"children": [
{
"id": "158",
"username": "test1",
"children": [
{
"id": "159",
"username": "test2",
"children": [
{
"id": "160",
"username": "test3",
"children": []
},
]
}
]
},
]
}
I am trying this method, but it is not working.
$firstCount = (array_map('count', $actualTree));
$secondCount = (array_map('count', $emptyTree));
$chunk = array_slice($actualTree, 0 , $second[$this->userId], true);
Use Case
The thing which I want to do is that remove those array childrens completely which are not exists in first array. I am building a binary tree upto three levels. First array already has a binary tree with empty values. The second array is data that is coming from the database, and I am simply replacing empty data with the actual data using array_replace. This is working good until second array has more values then first array. So to make it working I have to remove those extra elements.
Could anyone please help me to make there length same. Any help will be appreciated.
Thanks in advance.
A Stack Overflow miracle has occurred... I got a recursive snippet to work on the first pass! Usually it takes me a good hour or two to write something that works.
I don't know if I can make it any tighter/better OR if it will fail on any fringe cases, but:
it works for your sample input
it is midnight for me, I'm tired, and I have to work in the morning
Effectively, it synchronously & recursively iterates each array and stores each level of the entry array to the output array so long as the same level keys exists in the structure array.
Code: (Demo)
function truncateRecursive($structure, $entry) {
$output = [];
while (($structureKey = key($structure)) !== null && ($entryKey = key($entry)) !== null) {
$output[$entryKey] = !is_array($entry[$entryKey])
? $entry[$entryKey]
: truncateRecursive($structure[$structureKey], $entry[$entryKey]);
unset($structure[$structureKey], $entry[$entryKey]);
}
return $output;
}
var_export(truncateRecursive($structure, $entry));
Output:
array (
157 =>
array (
'id' => '157',
'username' => 'test1',
'children' =>
array (
0 =>
array (
'id' => '158',
'username' => 'test1',
'children' =>
array (
0 =>
array (
'id' => '159',
'username' => 'test2',
'children' =>
array (
0 =>
array (
'id' => '160',
'username' => 'test3',
'children' =>
array (
),
),
),
),
),
),
),
),
)

accessing the data inside array-key-array-objects

This is the data inside a variable named $data and i printed it using print_r().
Array
(
[user_id] => 6
[car_id] => 9
[pickup_name] => only me
[snooze] => 15
[pickup_loc] => pickup location
[drop_loc] => drop location
[note] => see you soon
[schedule] => [ {
"id": "1",
"car_name": "Mercedes-Benz C-Class",
"price": "200",
"status": "0",
"cr_dt": "2019-07-25 18:29:42",
"up_dt": "2019-07-26 11:20:36"
},
{
"id": "2",
"car_name": "Mercedes-Benz C-Class",
"price": "300",
"status": "0",
"cr_dt": "2019-07-25 18:29:42",
"up_dt": "2019-07-26 11:20:36"
} ]
[id] => 16
)
I want to access the data inside ['schedule'] in my foreach loop.
Thanks in advance.
You can use json_decode( $data['schedule]) directly. Otherwise you can use a variable like:
$jsarray = json_decode( $data['schedule])
Then you can access the data.

How to get the only first images in array inside array

Here i have one array(first array) inside i have one more array(second array), now i want to display only first image from second array(galleryImages) , how can do this. i tried but i am not able to get the results
print_r($response);
Array
(
[0] => stdClass Object
(
[gallery_id] => 2
[title] => Annual Day 2017
[description] =>
[galleryImages] => ["1.jpg","2.jpg","3.jpg","4.jpg"]
[reg_on] => 2017-05-17 01:55:12
[created_by] => rajeshdash123#gmail.com
[school_id] => 2
[status] => 0
)
[1] => stdClass Object
(
[gallery_id] => 3
[title] => Sports Day
[description] =>
[galleryImages] => ["1.jpg","2.jpg","3.jpg"]
[reg_on] => 2017-05-17 01:55:36
[created_by] => rajeshdash123#gmail.com
[school_id] => 2
[status] => 0
)
)
Expected Results
{
"status": "Success",
"data": [
{
"gallery_id": "2",
"title": "Annual Day 2017",
"description": "",
"galleryImagesCount": 4,
"gallery":"1.jpg"
},
{
"gallery_id": "3",
"title": "Sports Day 2017",
"description": "",
"galleryImagesCount": 4,
"gallery":"1.jpg"
}
],
}
I tried like this but is i am not getting the exact results
$images = array();
foreach ($response as $key => $value)
{
$img['gallery_id'] = $value->gallery_id;
$img['title'] = $value->title;
$img['description'] = $value->description;
$img['galleryImagesCount'] = count(json_decode($value->galleryImages,true));
$img['gallery'] = json_decode($value->galleryImages,true);
array_push($images,$img);
}
$return=array('status'=>"Success",'Images'=>$images);
echo json_encode($return);
Getting Results
{
"status": "Success",
"Images": [
{
"gallery_id": "2",
"title": "Annual Day 2017",
"description": "",
"galleryImagesCount": 4,
"gallery": [
"d17ac9d0aeb6435eaa294e0d69d4cc8f.jpg",
"a91945e0cf55379f51cf5faef10d7a4a.jpg",
"2d1501045ddbb3ccc238e70f9af05027.jpg",
"071c3b5f969bed1d1e2ee4b6531e4444.jpg"
]
},
{
"gallery_id": "3",
"title": "Sports Day",
"description": "",
"galleryImagesCount": 4,
"gallery": [
"f0ba574fd46a01ff5a41855a97c710ca.jpg",
"1d10802f1b74e660117f36bd6dd0aa26.jpg",
"e705fb66f767a1b914200ca8d3cae700.jpg",
"3d5d8828331e13d3decc94021a64e5ca.jpg"
]
}
]
}
Here what happening means gallery is coming an array , for me don't want array i need first image only, please check my expected results, update the answer
Updated expected results
{
"status": "Success",
"Images": [
{
"gallery_id": "2",
"title": "Annual Day 2017",
"description": "",
"galleryImagesCount": 4,
"gallery": [
{
"galleryimage": "1.jpg"
},
{
"galleryimage": "2.jpg"
}
]
},
{
"gallery_id": "3",
"title": "Sports Day",
"description": "",
"galleryImagesCount": 4,
"gallery": [
{
"galleryimage": "1.jpg"
},
{
"galleryimage": "2.jpg"
}
]
}
]
}
Instead of [galleryImages] => ["1.jpg","2.jpg","3.jpg"], use for loop to iterate through galleryImages.
Create an associative array with key =>value pair like [galleryImages] => ["galleryimage1" => "1.jpg", "galleryimage2" => "2.jpg", "galleryimage3" => "3.jpg"].
While json_decode you will get intended output.
My changes and explanations are in the code block:
Code: (Demo)
// assumed that previous line was something like $response=json_decode($json);
$response=[
(object)[
'gallery_id'=>2,
'title'=>'Annual Day 2017',
'description'=>'',
'galleryImages'=>["1.jpg","2.jpg","3.jpg","4.jpg"],
'reg_on'=>'2017-05-17 01:55:12',
'created_by'=>'rajeshdash123#gmail.com',
'school_id'=>2,
'status'=>0
],
(object)[
'gallery_id'=>3,
'title'=>'Sports Day',
'description'=>'',
'galleryImages'=>["1.jpg","2.jpg","3.jpg"],
'reg_on'=>'2017-05-17 01:55:36',
'created_by'=>'rajeshdash123#gmail.com',
'school_id'=>2,
'status'=>0
]
];
foreach ($response as $value){ // removed $key=> because it was unnecessary
$img['gallery_id'] = $value->gallery_id;
$img['title'] = $value->title;
$img['description'] = $value->description;
$img['galleryImagesCount'] = count($value->galleryImages); // removed json_decode()
$img['gallery'] = $value->galleryImages[0]; // removed json_decode and added [0] to access first
$images[]=$img; // swapped push() call with identical function-less "push"
}
if(isset($images)){ // added this condition to ensure there was something to return
$return=array('status'=>"Success",'Images'=>$images);
//var_export($return);
echo json_encode($return);
}else{
// enter some sort of error message / default behavior
}
Output:
{"status":"Success","Images":[{"gallery_id":2,"title":"Annual Day 2017","description":"","galleryImagesCount":4,"gallery":"1.jpg"},{"gallery_id":3,"title":"Sports Day","description":"","galleryImagesCount":3,"gallery":"1.jpg"}]}

Add new key/value pair into JSON in PHP

I have a result from my MySQL DB that I'm json encoding in PHP, the result looks like
:
[
{
"id": "8488",
"name": "Tenby",
"area": "Area1"
},
{
"id": "8489",
"name": "Harbour",
"area": "Area1"
},
{
"id": "8490",
"name": "Mobius",
"area": "Area1"
}
]
What I would like to do is to add a new key/value pair to that JSON so that it will be :
[
{
"id": "8488",
"name": "Tenby",
"area": "Area1",
"image": "1278.jpg"
},
{
"id": "8489",
"name": "Harbour",
"area": "Area1",
"image": "1279.jpg"
},
{
"id": "8490",
"name": "Mobius",
"area": "Area1",
"image": "1280.jpg"
}
]
So how can I do that in PHP?
<?php
$data[0]['id']="8488";
$data[0]['name']="Tenby";
$data[0]['area']="Area1";
$data[1]['id']="8489";
$data[1]['name']="Harbour";
$data[1]['area']="Area1";
$data[2]['id']="8490";
$data[2]['name']="Mobius";
$data[2]['area']="Area1";
echo json_encode($data)."<br/>";
/*Add Image element (or whatever) into the array according to your needs*/
$data[0]['image']="1278.jpg";
$data[1]['image']="1279.jpg";
$data[2]['image']="1280.jpg";
echo json_encode($data);
?>
PHP is not very good with JSON. Its best to convert from JSON to Array to do this - what #egig has also recommended.
Example code:
$temp = json_decode($json);
$temp[] = new data, whatever you want to add...;
$json = json_encode($temp);
Hope this helps.
hu?
the result of the db query will be an array or an object...
add the additional entry to that data, only encode after every necessary data manipulation is done
alternatives, but clumsy (horrible):
json_decode, add stuff, json_encode
build your additional data as a string, str_replace for example "area": "Area1" in your json string with "area": "Area1", "image": "1278.jpg"
but really:
output formatting like json_encode should only be done once you are sure that you have the whole output together and it is send out
Maybe things have changed since then, but I know this will work at this current stage:-
So here is the JSON string:-
$strJSON = '[
{
"id": "8488",
"name": "Tenby",
"area": "Area1"
},
{
"id": "8489",
"name": "Harbour",
"area": "Area1"
},
{
"id": "8490",
"name": "Mobius",
"area": "Area1"
}
]';
If this is still a string, then I would convert it into an object like this:-
$json = json_decode( $strJSON );
Now that it is in object format, to add my "image" keys with their values, I would then add them like it is shown below:-
$json[0]->image = "1278.jpg";
$json[1]->image = "1279.jpg";
$json[2]->image = "1280.jpg";
So then if I add the code below after the above code:-
echo "<pre>";
print_r( $json );
echo "</pre>";
We should then see it outputting on the page like so:-
Array
(
[0] => stdClass Object
(
[id] => 8488
[name] => Tenby
[area] => Area1
[image] => 1278.jpg
)
[1] => stdClass Object
(
[id] => 8489
[name] => Harbour
[area] => Area1
[image] => 1279.jpg
)
[2] => stdClass Object
(
[id] => 8490
[name] => Mobius
[area] => Area1
[image] => 1280.jpg
)
)
//$index = some value in array;
for($i=0;$i<count($index);$i++){
$data[$i]->key = $index[$i];
}
print $data;

PHP array to Json tree format

I want to tranform an php array into an json string to use with JavaScript InfoVis Toolkit formart.
the objective:
InfoVis Demo Tree
Json specification format:
InfoVis-loading and serving JSON data
I have this php array: $my_array :
Array
(
[item_1] => Array
(
[id] => item_1_ID
[name] => item_1_NAME
[data] => item_1_DATA
[children] => Array
(
[door] => Array
(
[id] => door_ID
[name] => door_NAME
[data] => door_DATA
[children] => Array
(
[mozart] => Array
(
[id] => mozart_ID
[name] => mozart_NAME
[data] => mozart_DATA
[children] => Array
(
[grass] => Array
(
[id] => grass_ID
[name] => grass_NAME
[data] => yes
)
[green] => Array
(
[id] => green_ID
[name] => green_NAME
[data] => no
)
[human] => Array
(
[id] => human_ID
[name] => human_NAME
[data] => human_DATA
[children] => Array
(
[blue] => Array
(
[id] => blue_ID
[name] => blue_NAME
[data] => blue_DATA
[children] => Array
(
[movie] => Array
(
[id] => movie_ID
[name] => movie_NAME
[data] => yes
)
)
)
)
)
)
)
)
)
[beat] => Array
(
[id] => beat_ID
[name] => beat_NAME
[data] => yes
)
[music] => Array
(
[id] => music_ID
[name] => music_NAME
[data] => no
)
)
)
)
now if I json_encode($my_array);
{
"item_1": {
"id": "item_1_ID",
"name": "item_1_NAME",
"data": "item_1_DATA",
"children": {
"door": {
"id": "door_ID",
"name": "door_NAME",
"data": "door_DATA",
"children": {
"mozart": {
"id": "mozart_ID",
"name": "mozart_NAME",
"data": "mozart_DATA",
"children": {
"grass": {
"id": "grass_ID",
"name": "grass_NAME",
"data": "yes"
},
"green": {
"id": "green_ID",
"name": "green_NAME",
"data": "no"
},
"human": {
"id": "human_ID",
"name": "human_NAME",
"data": "human_DATA",
"children": {
"blue": {
"id": "blue_ID",
"name": "blue_NAME",
"data": "blue_DATA",
"children": {
"movie": {
"id": "movie_ID",
"name": "movie_NAME",
"data": "yes"
}
}
}
}
}
}
}
}
},
"beat": {
"id": "beat_ID",
"name": "beat_NAME",
"data": "yes"
},
"music": {
"id": "music_ID",
"name": "music_NAME",
"data": "no"
}
}
}
}
But to InfoVis the current json output (json_encode($my_array)) has 3 problems:
is not using [ ]
the 'children' arrays have the key names
arrays items is with their key names -> example: "item_1": { ....
let me point the problem so maybe you can help with an function to transform this json string:
see this slice of json_encode($my_array) output:
{
"item_1": {
"id": "item_1_ID",
"name": "item_1_NAME",
"data": "item_1_DATA",
"children": {
"door": {
"id": "door_ID",
1. problem 1:
{
"item_1": {
we have to remove those keys like: "item_1":
2. problem 2:
"children": {
"door": {
"id": "door_ID",
the correct code for this should be:
"children": [
{
"id": "door_ID",......
"door": was removed... because it`s a key
"children": { => becomes" "children": [
An working example of 'children':
"children": [
{
"id": "grass_ID",
"name": "grass_NAME",
"data": "yes"
},
{
"id": "green_ID",
"name": "green_NAME",
"data": "no"
}
]
to clarify an complete example of WORKING Json InfoVis format:
json = {
id: "node02",
name: "0.2",
children: [{
id: "node13",
name: "1.3",
children: [{
id: "node24",
name: "2.4"
}, {
id: "node222",
name: "2.22"
}]
}, {
id: "node125",
name: "1.25",
children: [{
id: "node226",
name: "2.26"
}, {
id: "node237",
name: "2.37"
}, {
id: "node258",
name: "2.58"
}]
}, {
id: "node165",
name: "1.65",
children: [{
id: "node266",
name: "2.66"
}, {
id: "node283",
name: "2.83"
}, {
id: "node2104",
name: "2.104"
}, {
id: "node2109",
name: "2.109"
}, {
id: "node2125",
name: "2.125"
}]
}, {
id: "node1130",
name: "1.130",
children: [{
id: "node2131",
name: "2.131"
}, {
id: "node2138",
name: "2.138"
}]
}]
};
is it clear to understand?
Hope anyone can help me.. I'm working on this for days!
thank you.
Try this quickie conversion function
function fixit($yourArray) {
$myArray = array();
foreach ($yourArray as $itemKey => $itemObj) {
$item = array();
foreach ($itemObj as $key => $value) {
if (strtolower($key) == 'children') {
$item[$key] = fixit($value);
} else {
$item[$key] = $value;
}
}
$myArray[] = $item;
}
return $myArray;
}
$fixed = fixit($my_array);
$json = json_encode($fixed);
PHP doesn't differentiate between arrays (numeric keys) and associative arrays (string keys). They're all just Arrays. Javascript DOES differentiate. Since you're using string keys, they HAVE to be done as objects ({}) in JS.
You can't tell json_encode to ignore the keys in an array (e.g. your 'children' sub-arrays). That'd mean the produced JSON is NOT the same as the original PHP structure - you've now changed key names.
You'd have to process your array and convert all those children sub-array keys to numbers:
grass -> 0
green -> 1
etc...
so that json-encode could see that it's a numerically keyed PHP array, meaning it'll produce an actual javavscript array ([]), and not an object ({}).
The alternative is writing your own JSON-encoder to do this on-the-fly for you.
This is documented behaviour. An associative array will produce an object literal when JSON stringified with json_encode. Update your original array structure to represent the outcome you want, instead of mangling the produced JSON representation, or wrap your own solution around json_encode for each object.
Edit: attempting a cleanup operation
The code
$original = <your original data-array>; // assumed, I reversed your encoded JSON as test data
// Start by stripping out the associative keys for level 1
$clean = array_values($original);
// Then recursively descend array, and do the same for every children-property encountered
function &recursiveChildKeysCleaner(&$arr) {
// If $arr contains 'children'...
if (array_key_exists('children', $arr)) {
/// ...strip out associative keys
$arr['children'] = array_values($arr['children']);
// ...and descend each child
foreach ($arr['children'] as &$child) {
recursiveChildKeysCleaner($child);
}
}
return $arr;
}
foreach ($clean as &$item) {
recursiveChildKeysCleaner($item);
}
unset($item);
echo json_encode($clean);
Output
[{
"id": "item_1_ID",
"name": "item_1_NAME",
"data": "item_1_DATA",
"children": [{
"id": "door_ID",
"name": "door_NAME",
"data": "door_DATA",
"children": [{
"id": "mozart_ID",
"name": "mozart_NAME",
"data": "mozart_DATA",
"children": [{
"id": "grass_ID",
"name": "grass_NAME",
"data": "yes"
},
{
"id": "green_ID",
"name": "green_NAME",
"data": "no"
},
{
"id": "human_ID",
"name": "human_NAME",
"data": "human_DATA",
"children": [{
"id": "blue_ID",
"name": "blue_NAME",
"data": "blue_DATA",
"children": [{
"id": "movie_ID",
"name": "movie_NAME",
"data": "yes"
}]
}]
}]
}]
},
{
"id": "beat_ID",
"name": "beat_NAME",
"data": "yes"
},
{
"id": "music_ID",
"name": "music_NAME",
"data": "no"
}]
}]

Categories