I have list with categories that sometimes appear duplicate. I want to them belonging to the same category as in groups. Current output is as follows:
Mercedes
Vito
Mercedes
A Klasse
Opel
Corsa
Mercedes
CLA
I want them to print like:
Mercedes
Vito
A Klasse
CLA
Opel
Corsa
my code:
$string = json_decode('{"cars_array":[{"brand":"Mercedes","model":"Vito"},{"brand":"Mercedes","model":"A Klasse"},{"brand":"Opel","model":"Corsa"},{"brand":"Mercedes","model":"CLA"}]}',true);
$catArray = array();
foreach ($string['cars_array'] as $k => $product) {
echo $product['brand']."\n";
echo $product['model']."\n\n";
}
What I have tried so far:
$string = json_decode('{"cars_array":[{"brand":"Mercedes","model":"Vito"},{"brand":"Mercedes","model":"A Klasse"},{"brand":"Opel","model":"Corsa"},{"brand":"Mercedes","model":"CLA"}]}',true);
$catArray = array();
foreach ($string['cars_array'] as $k => $product) {
if (array_key_exists($product['brand'], $catArray)) {
$catArray[$product['brand']] = array('model' => $product['model'] );
}else{
$catArray[$product['brand']] = $product['brand'];
$catArray[$product['brand']] = array('model' => $product['model'] );
}
}
var_dump($catArray);
You can group items by using a named array, then assign values by pushing them with [] syntax
$string = json_decode('{"cars_array":[{"brand":"Mercedes","model":"Vito"},{"brand":"Mercedes","model":"A Klasse"},{"brand":"Opel","model":"Corsa"},{"brand":"Mercedes","model":"CLA"}]}',true);
$catArray = array();
foreach ($string['cars_array'] as $k => $product) {
// create an array grouped on brand’s value
$catArray[$product['brand']][] = $product['model'];
echo $product['brand']."\n";
echo $product['model']."\n\n";
}
foreach($catArray as $brand => $modelList) {
print "$brand\n";
foreach($modelList as $model) {
print "$model\n";
}
print "\n";
}
try to use array unique in $string
$string_arr = array_unique($string);
then Implode it
$echo_arr = implode($string_arr)
echo $echo_arr;
Related
I am new to multidimensional array in php, I read this SO answer and I tried to create my bidimensional array but how do I output it?
$nPost = array("orange, table");
$count_values = array("fruit, forniture");
$final_array = array(array($count_values), array($nPost));
Output would have to be:
Fruits: orange, Forniture: table
Tried
print_r($final_array);
But i got
Array ( [0] => Array ( [0] => Array ( [0] => fruit, forniture ) ) [1] => Array ( [0] => Array ( [0] => orange, table ) ) )
0 fruit, forniture
UPDATE
Real life full code is (explanation in code comments):
<?php
$stack = array();
$userID = array();
$nPost = array();
$blogusers = get_users( 'orderby=nicename&role=author' );
foreach ( $blogusers as $user ) {
// get the language list for each user, and push to array
$descTokens = explode(',', $user->user_description);
$stack = array_merge($stack, $descTokens);
// get the ID for each user, and push to the array
// get the number of posts for each user ID and push to array
$the_user_id = $user->ID;
$numPosts = count_user_posts( $the_user_id );
array_push($userID, $the_user_id);
array_push($nPost, $numPosts);
}
// get the count for each language by counting the duplicate strings
$count_values = array();
foreach ($stack as $a) {
#$count_values[$a]++;
}
$total_duplicates = 0;
foreach ($count_values as $a) {
if($count_values[$a]<=1){
unset($count_values[$a]);
} else{
$total_duplicates += $count_values[$a];
}
}
for($i = 0; $i < count($count_values); $i++){
$final_array[$count_values[$i]] = $nPost[$i];
}
foreach($final_array as $label => $item){
echo "$label: $item, ";
}
?>
// This gives me a correct result but not the n. posts
<ul>
<?php
foreach ($count_values as $key=>$count) {
echo '<li>'.$key.' '.$count.'</li>';
}
?>
</ul>
What we're trying to achieve is:
1 French with 2 posts
3 English with 5 posts
<?php
class User {
public $id;
public $numPosts;
public $languages = array();
public function __construct($id, $numPosts, $lang = array()){
$this->id = $id;
$this->numPosts = $numPosts;
$this->languages = $lang;
}
}
$users = array();
$john = new User(1, 4, array("English", "French"));
$fred = new User(2, 3, array("English"));
$dave = new User(3, 7, array("German", "French", "Spanish"));
$users[] = $john;
$users[] = $fred;
$users[] = $dave;
$langPostCount = array();
$langUserCount = array();
foreach($users as $user){
foreach($user->languages as $lang){
$langUserCount[$lang] += 1; // this is what you already have from $count_values
//$langPostCount[$lang] += $user->numPosts; // can be done here but we'll do another loop
}
}
/*
* the following can be done in the above loop, but you already have that functionality in your code
* just need to do another loop through your languages, tallying the number of posts in that language
* keep in mind this is not entirely accurate as your users have multiple languages. they might have
* one post in english and 4 in french. A better way to do this would be to select the number of posts
* in each language directly from the posts database.
*/
foreach($langUserCount as $lang => $userCount){
foreach($users as $user){
if(in_array($lang, $user->languages)){
$langPostCount[$lang] += $user->numPosts;
}
}
}
echo "<ul>";
foreach($langUserCount as $lang => $userCount){
echo "<li>$userCount $lang with " . $langPostCount[$lang] . " posts.</li>";
}
echo "</ul>";
?>
OUTPUT
2 English with 7 posts.
2 French with 11 posts.
1 German with 7 posts.
1 Spanish with 7 posts.
As you can see, not entirely accurate. You're better off getting post count by querying your posts dataset than by working from the bottom up.
Try This
Adds a new tally to the foreach loop at the top, and changes the ul loop at the end.
$postsPerLanguage = array(); // add this
foreach ( $blogusers as $user ) {
$descTokens = explode(',', $user->user_description);
...
$numPosts = count_user_posts( $the_user_id );
...
// add this loop
foreach($descTokens as $lang){
$postsPerLanguage[$lang] += $numPosts;
}
}
...
<ul>
<?php
foreach ($count_values as $key=>$count) {
echo '<li>'.$key.' '.$count.' with '. $postsPerLanguage[$key] .' posts</li>';
}
?>
</ul>
Your output doesn't need multidimensional array you can achieve it like this:
$final_array = array('Fruits'=> 'orange', 'Furniture'=> 'table')
but for example if you have multiple fruits or furniture you can make something like this:
$final_array = array('Fruits'=> array('orange', 'apple'), 'Furniture'=> array('table', 'sofa'))
and you can access apple like this:
echo $final_array['Fruits'][1];
and for print_r($final_array) we have this:
[Fruits] => (
[0] => orange,
[1] => apple
)
[Furniture] => (
[0] => table,
[1] => sofa
)
I have this result inside my foreach loop:
Tonsilitis
Tonsilitis
Laryngitis
Rhinosinusitis Akut
Rhinosinusitis Akut
Rhinosinusitis Akut
Common Cold
Common Cold
Common Cold
Rhinitis Alergi
This is my script:
foreach ($results as $data) :
$final = $data->nama_diagnosis . '<br>';
echo $final;
endforeach;
My question is, how can i count the same word in my loop or outside the loop. Can i do that? give me the solution please. As a result i want to count them like this:
Tonsilitis = 2
Laryngitis = 1
Rhinosinusitis Akut = 3
Common Cold = 3
Rhinitis Alergi = 1
Or maybe i can filter the same word so i get only the most words, like Rhinosinusitis Akut and Common Cold. Please help me.
Thanks
You can try something like this, iterating through array with foreach loop and using a ternary operator with isset to safely assign and increment each occurrence:
$count = array();
foreach ($results as $result)
isset($count[$data]) ? $count[$data]++ : $count[$data] = 1;
Example
In foreach loop save words and their count into array, then make another loop and write the amounts.
<?php
$results = array(
array('nama_diagnosis' => 'Tonsilitis'),
array('nama_diagnosis' => 'Tonsilitis'),
array('nama_diagnosis' => 'Laryngitis'),
array('nama_diagnosis' => 'Rhinosinusitis Akut'),
array('nama_diagnosis' => 'Rhinosinusitis Akut'),
array('nama_diagnosis' => 'Rhinosinusitis Akut'),
array('nama_diagnosis' => 'Common Cold'),
array('nama_diagnosis' => 'Common Cold'),
array('nama_diagnosis' => 'Common Cold'),
array('nama_diagnosis' => 'Rhinitis Alergi')
);
$res = array();
foreach ($results as $words) { // changed $word to $words
foreach ($words as $word) { // this foreach added
if (isset($res[$word])) {
$res[$word] += 1;
} else {
$res[$word] = 1;
}
} // end of nested foreach which was added
}
foreach ($res as $word => $count) {
echo $word . ' (' . $count . ')<br>';
}
/*
output:
Tonsilitis (2)
Laryngitis (1)
Rhinosinusitis Akut (3)
Common Cold (3)
Rhinitis Alergi (1)
*/
?>
Try with -
$counts = array();
foreach ($results as $data) :
$final = $data->nama_diagnosis . '<br>';
if (array_key_exists($data->nama_diagnosis, $counts)) {
$counts[$data->nama_diagnosis] += 1;
} else {
$count[$data->nama_diagnosis] = 1;
}
endforeach;
foreach ($counts as $key => $val) {
echo $key.' = '.$val;
}
This should work for you:
<?php
$results = array("Tonsilitis", "Tonsilitis", "Laryngitis", "Rhinosinusitis Akut", "Rhinosinusitis Akut", "Rhinosinusitis Akut", "Common Cold", "Common Cold", "Common Cold", "Rhinitis Alergi");
$counter = array();
foreach ($results as $data):
if(in_array($data->nama_diagnosis, array_flip($counter)))
$counter[$data->nama_diagnosis]++;
else
$counter[$data->nama_diagnosis] = 1;
endforeach;
foreach ($counter as $key => $data)
echo $key . " = " . $data . "<br />";
?>
Output:
Tonsilitis = 2
Laryngitis = 1
Rhinosinusitis Akut = 3
Common Cold = 3
Rhinitis Alergi = 1
Is there a way to create dynamicaly multidimensional array? I have stored in database "path" for each field=>value like that:
field_name : [slideshow][slide][0][title]
field_value : my title
field_name : [slideshow][slide][0][desc]
field_value : my desc
field_name : [slideshow][slide][1][title]
field value : my other title
field_name : [slideshow][slide][1][desc]
field value : my other desc
field_name : [slideshow][settings][duration]
field value : 300
and now I'm trying to figure out how to make it an array again. Obviously there can be lots of fields and complexity so I wanted to avoid some recursions if possible, cause I'm not sure how it will impact performance.
I was playing around with variable variables and trying something like:
$array_name = 'arr';
${$array_name}[slideshow][slide][1][title] = $field->field_value;
print_r($arr);
but this works only if its literally that, and nothing like this works:
${$array_name}.$field->field_name = $field->field_value;
I basically need to store every field as individual row (e.g. for searches in those fields), values can be diffrent types (even serialized arrays), and contain html.
Any advice appreciate.
The basic idea is to split up your field_name string and loop over the parts backward to build up the array. Some recursion is used to merge the arrays, though any performance impact should be negligible.
Example:
// Set up sample data.
$field = new stdClass();
$field->field_name = '[slideshow][slide][0][title]';
$field->field_value = 'my title';
$fields[] = $field;
$field = new stdClass();
$field->field_name = '[slideshow][slide][0][desc]';
$field->field_value = 'my desc';
$fields[] = $field;
$field = new stdClass();
$field->field_name = '[slideshow][slide][1][title]';
$field->field_value = 'my other title';
$fields[] = $field;
$field = new stdClass();
$field->field_name = '[slideshow][slide][1][desc]';
$field->field_value = 'my other desc';
$fields[] = $field;
$field = new stdClass();
$field->field_name = '[slideshow][settings][duration]';
$field->field_value = '300';
$fields[] = $field;
// End sample data.
// array_merge_recursive() doesn't do what we want with numeric keys, so use this
function merge($base, $array) {
foreach ($array as $key => $value) {
if (isset($base[$key]) && is_array($base[$key]) && is_array($value)) {
$base[$key] = merge($base[$key], $value);
} else {
$base[$key] = $value;
}
}
return $base;
}
$result = [];
foreach ($fields as $field) {
$parts = array_reverse(explode('][', trim($field->field_name, '[]')));
$value = $field->field_value;
foreach ($parts as $part) {
$value = [$part => $value];
}
$result = merge($result, $value);
}
print_r($result);
Output:
Array
(
[slideshow] => Array
(
[slide] => Array
(
[0] => Array
(
[title] => my title
[desc] => my desc
)
[1] => Array
(
[title] => my other title
[desc] => my other desc
)
)
[settings] => Array
(
[duration] => 300
)
)
)
You could try something like this.
$cars = array
(
array("Volvo",22,18),
array("BMW",15,13),
array("Saab",5,2),
array("Land Rover",17,15)
);
<?php
echo $cars[0][0].": In stock: ".$cars[0][1].", sold: ".$cars[0][2].".<br>";
echo $cars[1][0].": In stock: ".$cars[1][1].", sold: ".$cars[1][2].".<br>";
echo $cars[2][0].": In stock: ".$cars[2][1].", sold: ".$cars[2][2].".<br>";
echo $cars[3][0].": In stock: ".$cars[3][1].", sold: ".$cars[3][2].".<br>";
?>
<?php
for ($row = 0; $row < 4; $row++) {
echo "<p><b>Row number $row</b></p>";
echo "<ul>";
for ($col = 0; $col < 3; $col++) {
echo "<li>".$cars[$row][$col]."</li>";
}
echo "</ul>";
}
?>
Hi All I have 2 arrays for example in PHP as seen below:
[users] => Array ( [0] => Array ( [username] => Timothy ) [1] => Array ( [username] => Frederic ) )
[users2] => Array ( [0] => Array ( [username] => Johnathon ) [1] => Array ( [username] => Frederic ) [] => Array ( [username] => Peter))
I am trying to compare the contents of each array against each other in order to put a html element, I tried using a nested foreach as seen below:
foreach($users as $user){
foreach ($users2 as $user2){
if($user['username'] == $user2['username']){
echo "<option value=' ".$user['username']."' selected = 'selected'>".$user['username']."</option>";
break;
} else{
echo "<option value=' ".$user['username']."'>".$user['username']."</option>";
}
}
}
my issue is that the items are being echoed more than once which is ruining my select element. Any ideas on how to compare the contents of each?
I want to achieve a list of each name eg:
-Timothy
-Frederic (this should be highlighted as it is in both arrays)
-Johnathon
- Peter
I would take it in a different way.
//Create user array one
$users = array();
$users[] = array('username'=>'Timothy');
$users[] = array('username'=>'Frederic');
//create user array 2
$users2 = array();
$users2[] = array('username'=>'Johnathon');
$users2[] = array('username'=>'Frederic');
$users2[] = array('username'=>'Peter');
$temp_array = array();
foreach($users as $key => $value) {
$temp_array[$value['username']] = '';
}
foreach($users2 as $key => $value) {
$temp_array[$value['username']] = array_key_exists($value['username'], $temp_array) ? 'DUPLICATE' : null;
}
echo '<select>';
foreach($temp_array as $key_value => $status) {
echo "<option value='{$key_value}' ".(($status == 'DUPLICATE') ? 'selected style="background-color: yellow;"' : '').">{$key_value}</option>";
}
echo '</select>';
I'll let the array take care of it self, if it shares the same key, it will merge, then just flag it with "duplicate".
If there is never any duplicates as you say in each array, the following works for me. This may look a bit complicated, but read through my comments.
You can copy the code and run it in it's own page to see if it works the way you want.
<?php
//Create user array one
$users = array();
$users[] = array('username'=>'Timothy');
$users[] = array('username'=>'Frederic');
//create user array 2
$users2 = array();
$users2[] = array('username'=>'Johnathon');
$users2[] = array('username'=>'Frederic');
$users2[] = array('username'=>'Peter');
//create a new array to combine all of the data, yes, there will be duplicates
$allData = array();
//add to allData array
foreach ($users as $user) {
$allData[] = $user['username'];
}
//add to allData array
foreach ($users2 as $user2) {
$allData[] = $user2['username'];
}
//create an array that will hold all of the duplicates
$dups = array();
//add any duplicates to the array
foreach(array_count_values($allData) as $val => $c) {
if($c > 1) $dups[] = $val;
}
//remove the duplicates from the allData array
$allData = array_unique($allData);
//echo out form
echo '<select>';
foreach ($allData as $user) {
if (in_array($user, $dups)) {
echo "<option value=' ".$user."' selected = 'selected'>".$user."</option>";
}
else {
echo "<option value=' ".$user."'>".$user."</option>";
}
}
echo '</select>';
?>
However, I'm not sure what your intentions are since IF you had "Peter" and "Frederic" in BOTH arrays, you are not going to get the form you want. But, this works for what you wanted.
i have this $_categories as array()
<?php print_r($_categories); ?> is this: Array ( [0] => 13 [1] => 7 )
what i need is to extract de values 13 and 7 into this format: 13,7 (without comma after the last value).
i have this code but is not there yet... the result is: 137 and not 13,7
<?php
if ( is_array($_categories) ) {
foreach ($_categories as $key => $value) {
$out = array();
array_push($out, $value);
echo implode(', ', $out);
}
}
else {
echo '<li>There are no saved values yet.</li>';
}
?>
Thanks, nelson
Directly use
echo implode(', ', $_categories);
Everytime you are implodeing just one element,and echoing just it. Try like this:
$out = array(); //putting outside of the loop
foreach ($_categories as $key => $value) {
array_push($out, $value);
}
echo implode(', ', $out); //putting outside of the loop