How to extract particular fields from an array [duplicate] - php

This question already has answers here:
Is there a function to extract a 'column' from an array in PHP?
(15 answers)
Closed 9 months ago.
I have an array that looks
$articles = array([0] => array('title' => 'When ....',
'description' => '....',
'created' => '2011-02-21'
),
[1] => array('title' => 'Something ....',
'description' => 'When ....',
'created' => '2011-02-21'
),
);
I want to extract only the titles. Is there anyway to retrieve the titles without using for and foreach loops. I dont mind the title becomes a single string. I was thinking implode the array but that adds description and created.

considering its CakePHP, $titles = Set::extract('/title', $articles);
edit:
http://book.cakephp.org/view/1487/Set
Update:
With CakePHP 2.x Hash has replaced Set.
$titles = Hash::extract($articles, '{n}.title');

You can use for example array_map, but why do you not want to use Loops? In fact every method, that is able to modify the array in the way you want it, will iterate over it.
function reduce_to_title ($item) {
return $item['title'];
};
$titles = array_map('reduce_to_title', $articles);
Or since PHP>=5.3
$titles = array_map(function ($item) {
return $item['title'];
}, $articles);

you can use this
print_r(array_map('array_shift', $articles));
EDIT :
Assumption : if title is the first element of array.

since 5.5, array_column does exactly what you explained.
$titles = array_column($articles, "title"); // [0=>"When",1=>"Something"]
For more examples check the PHP manual

What about while loops?
reset($articles); while($a = each($articles)){echo $a['value']['title'];}

an improved version of KingCrunch's answer:
function get_column(&$array,$column) {
foreach ($array as $value) {
$ret[]=$value[$column];
}
return $ret;
}
this is pretty universal function and can be put into some library, and then called with just single line, which is shorter than in every other answer:
$titles = get_column($articles, 'title');
Update
However, it seems that cake already have such a function, so, the only proper answer is
How to extract particular fields from an array

Hey, since you're using CakePHP, why don't you just add title to the fields array in your find()? For example, the following,
$this->Article-find('all', array('fields'=>'Article.title'));
will pull only the titles of all matching Articles in the database.

Related

How do I work with an array object in PHP?

I have a Laravel site I am modifying, but there are some parts of the PHP code I don't quite understand, which are "array objects" or "object arrays". You see, I don't even know what to call them and so can't find a tutorial or basic data on it. Below is the code that I am dealing with:
private function parseMetric($result, $view)
{
$data = collect([]);
$result->each(function($item) use ($data, $view) {
if (isset($item->metric->{$view})) {
$data->push((object)[
'label' => $item->metric->{$view},
'value' => $item->metric->count
]);
}
});
...
From what I can tell, this creates an object out of $result. If I json_encode this and echo it out I get this:
[{"label":"1k-25k","value":14229},
{"label":"1mm+","value":1281},
{"label":"25k-50k","value":398},
{"label":"50k-75k","value":493},
{"label":"75k-100k","value":3848},
{"label":"100k-150k","value":9921},
{"label":"150k-200k","value":4949},
{"label":"200k-250k","value":3883},
{"label":"250k-300k","value":2685},
{"label":"300k-350k","value":2744},
{"label":"350k-500k","value":4526},
{"label":"500k-1mm","value":8690}]
Now this is obviously an array of arrays... or is it? Is it an array of objects? Or is it an object containing arrays? But the most important question is, how do I access and move or change the individual objects/arrays in this object? For example, I want to take the second object/array, which is:
{"label":"1mm+","value":1281}
and move it to the end. How do I do that? How do I find it? I used the following piece of code to find it which is pretty clunky:
$pos = strpos(json_encode($result), '1mm+');
if($pos){
Log::debug('Enrich 73, I found it!!!!!!!!!!!!!!!!!!!!!!!!!!!');
}
And once I find it, how do I move that array/object to the end of the whole object?
And finally, where can I find some kind of tutorial, or documentation, that describes this construct and how to work with it?
There is no need to json_encode the data. Since the data is an instance of Laravel Collection, you can manipulate it like so
$item = $data->firstWhere('label', '1mm+'); // get the item
$data = $data->filter(fn($value, $key) => $value->label !== '1mm+') // remove $item from $data
->push($item); // move $item to the end of data
Acording to Laravel documnentation for Collections, you can try something like this :
To find index of element with name = "1mm+" :
$index = $datas->search(function ($item, $key) {
return $item['name'] == "1mm+";
});
to get an element at a given index :
$element = $datas->get($index);
to Move element at index 3 to the end :
$index = 3
$elementToMove = $data->splice($index, 1);
$datas->push($elementToMove);
Here is a link to the document used : https://laravel.com/docs/8.x/collections

Get all values for specific key in an array of associative array [duplicate]

This question already has answers here:
Is there a function to extract a 'column' from an array in PHP?
(15 answers)
Closed 10 months ago.
Let's assume I have the following multidimensional array (retrieved from MySQL or a service):
array(
array(
[id] => xxx,
[name] => blah
),
array(
[id] => yyy,
[name] => blahblah
),
array(
[id] => zzz,
[name] => blahblahblah
),
)
Can we get an array of ids in one "built-in" php function call? or one line of code?
I am aware of the traditional looping and getting the value but I don't need this:
foreach($users as $user) {
$ids[] = $user['id'];
}
print_r($ids);
Maybe some array_map() and call_user_func_array() can do the magic.
Since PHP 5.5, you can use array_column:
$ids = array_column($users, 'id');
This is the preferred option on any modern project. However, if you must support PHP<5.5, the following alternatives exist:
Since PHP 5.3, you can use array_map with an anonymous function, like this:
$ids = array_map(function ($ar) {return $ar['id'];}, $users);
Before (Technically PHP 4.0.6+), you must create an anonymous function with create_function instead:
$ids = array_map(create_function('$ar', 'return $ar["id"];'), $users);
PHP 5.5+
Starting PHP5.5+ you have array_column() available to you, which makes all of the below obsolete.
PHP 5.3+
$ids = array_map(function ($ar) {return $ar['id'];}, $users);
Solution by #phihag will work flawlessly in PHP starting from PHP 5.3.0, if you
need support before that, you will need to copy that wp_list_pluck.
PHP < 5.3
Wordpress 3.1+
In Wordpress there is a function called wp_list_pluck
If you're using Wordpress that solves your problem.
PHP < 5.3
If you're not using Wordpress, since the code is open source you can copy paste the code in your project (and rename the function to something you prefer, like array_pick). View source here
If id is the first key in the array, this'll do:
$ids = array_map('current', $users);
You should not necessarily rely on this though. :)
You can also use array_reduce() if you prefer a more functional approach
For instance:
$userNames = array_reduce($users, function ($carry, $user) {
array_push($carry, $user['name']);
return $carry;
}, []);
Or if you like to be fancy,
$userNames = [];
array_map(function ($user) use (&$userNames){
$userNames[]=$user['name'];
}, $users);
This and all the methods above do loop behind the scenes though ;)

Remove certain keys and values from associative array

I have a array that looks like this:
[['title'= >'my title','time'=>'14:00','date'=>'feb 2'],['title'= >'another','time'=>'14:00','date'=>'feb 2']]
Now I wish to remove all time and date keys from the arrays and also rename the title to text so it looks like this:
[['text'= >'my title'],['text'= >'another title']]
I have tried to use
$tags = array_map(function($tag) {
return array(
'text' => $tag['title'],
);
}, $tags);
But I cant get it to work
Laravel solution:
collect($array)->transform(function($i) { return ['text' => $i['title']]; })->toArray();
You can transform your collections,
$mycollection = $myModel->get();
return $mycollection->map(function($row){
return [
'text' => $row->title,
];
});
Or you can use Fractal: http://fractal.thephpleague.com/transformers/
$newTags = [];
foreach($tags as $tag) {
$newTags[] = [['text'] => $tag['title']];
}
$tags = $newTags;
This question isn't specific to Laravel, but since you mention it:
Use the collect() helper and it's methods for convenience. You'll want to look at pull, map, and maybe transform in particular.
If you don't use it then unset will delete the index you want from the array.
Alternatively, just create a new array:
$a = []
foreach($tags as $tag) {
$a[] = ['text' => $tag['title']];
}
edit: fix

How to merge multiple arrays that are depending on a function in PHP?

I am seeking for someone's knowledge out here.
Right now, I would need to merge several arrays into a bigger one, but all of those arrays depend on a function.
This function returns a numeric array containing different quantities of numbers between 1 and 7 :
function Possible($i, $j, $grid)
$possible = Possible($i, $j, $grid)
I'm working with a grid, and the function returns a different array for every case of the grid. What I would like to do is to merge those 7 arrays into another one. Some numbers may be present more than once in this big array, but I want it this way.
I tried using for loops, while loops and some other techniques, but nothing worked. In this case, it is not possible to manually define every array, since they change depending of what is contained in the grid and there are too many. It has to be done automatically, and this is where I get stuck.
for ($jj=0; $j<7; $j++){
$possRow = array_merge( ###what do I add here or what do I change in this code to make everything work###
Thank you if someone can help me out!
Etpi
hope this help:
$biggerOneArray = array();
for($k=0;$k<7;$k++) {
$biggerOneArray[] = Possible($i,$j,$grid);
}
Then you can check your bigger array, may contains all arrays of the iterations of the loop (7 arrays merged).
var_dump($biggerOneArray);
The output should be this:
array(
(int) 0 => array(
'key' => 'value',
'key2' => 'value2'
),
(int) 1 => array(
'key3' => 'value3',
'key4' => 'value4'
)
)
etc...
I'm sorry but your description isn't very clear. But just to get you started you might look at this solution.
function Possible($i, $j, $grid) {
// some code ... e.g. $array[] = "some data";
return $array;
}
By creating a small array for each grid and returning it using return $array you get a few little arrays which you can inturn place into a for loop to merge it into one larger array. However i believe the var $jj must have some meaning in the function it self as well.
for($jj=0;$jj<7;$jj++) {
$merged_array[$jj] = Possible($i,$j,$grid);
}
Maybe if you descripe your problem a little more and post an exmple of the array's your working with i can give you a better answer.

How to get an array of specific "key" in multidimensional array without looping [duplicate]

This question already has answers here:
Is there a function to extract a 'column' from an array in PHP?
(15 answers)
Closed 10 months ago.
Let's assume I have the following multidimensional array (retrieved from MySQL or a service):
array(
array(
[id] => xxx,
[name] => blah
),
array(
[id] => yyy,
[name] => blahblah
),
array(
[id] => zzz,
[name] => blahblahblah
),
)
Can we get an array of ids in one "built-in" php function call? or one line of code?
I am aware of the traditional looping and getting the value but I don't need this:
foreach($users as $user) {
$ids[] = $user['id'];
}
print_r($ids);
Maybe some array_map() and call_user_func_array() can do the magic.
Since PHP 5.5, you can use array_column:
$ids = array_column($users, 'id');
This is the preferred option on any modern project. However, if you must support PHP<5.5, the following alternatives exist:
Since PHP 5.3, you can use array_map with an anonymous function, like this:
$ids = array_map(function ($ar) {return $ar['id'];}, $users);
Before (Technically PHP 4.0.6+), you must create an anonymous function with create_function instead:
$ids = array_map(create_function('$ar', 'return $ar["id"];'), $users);
PHP 5.5+
Starting PHP5.5+ you have array_column() available to you, which makes all of the below obsolete.
PHP 5.3+
$ids = array_map(function ($ar) {return $ar['id'];}, $users);
Solution by #phihag will work flawlessly in PHP starting from PHP 5.3.0, if you
need support before that, you will need to copy that wp_list_pluck.
PHP < 5.3
Wordpress 3.1+
In Wordpress there is a function called wp_list_pluck
If you're using Wordpress that solves your problem.
PHP < 5.3
If you're not using Wordpress, since the code is open source you can copy paste the code in your project (and rename the function to something you prefer, like array_pick). View source here
If id is the first key in the array, this'll do:
$ids = array_map('current', $users);
You should not necessarily rely on this though. :)
You can also use array_reduce() if you prefer a more functional approach
For instance:
$userNames = array_reduce($users, function ($carry, $user) {
array_push($carry, $user['name']);
return $carry;
}, []);
Or if you like to be fancy,
$userNames = [];
array_map(function ($user) use (&$userNames){
$userNames[]=$user['name'];
}, $users);
This and all the methods above do loop behind the scenes though ;)

Categories