I have an array:
Array
(
[0] => dir0|file0.txt
[1] => dir0|file1.txt
[2] => dir1|file2.txt
[3] => dir1|filea.txt
[4] => dir2|fileb.txt
)
I would like it to be displayed as a tree, such as:
dir0
file0.txt
file1.txt
dir1
file2.txt
filea.txt
dir2
fileb.txt
Can any one explain how I can do that?
Edit: Updated for multidimentional array:
$paths[0][0] = 'dir0|file0.txt';
$paths[0][1] = 400;
$paths[1][0] = 'dir0|filea.txt';
$paths[1][1] = 500;
$paths[2][0] = 'dir1|file1.txt';
$paths[2][1] = 600;
$paths[3][0] = 'dir1|fileb.txt';
$paths[3][1] = 700;
$paths[4][0] = 'dir2|filec.txt';
$paths[4][1] = 700;
I would like the output to be:
dir0 (900)
file0.txt (400)
filea.txt (500)
dir1 (1300)
file1.txt(600)
fileb.txt (700)
dir2 (700)
filec.txt (700)
The values need to be added and displayed in root.
The best way would be to reformat the array so the keys were the directories, and the array values were arrays containing file names, like so:
$array = array( ..);
$reformatted = array();
foreach( $array as $k => $v) {
list( $key, $value) = explode( '|', $v);
if( !isset( $reformatted[$key]))
$reformatted[$key] = array();
$reformatted[$key][] = $value;
}
Then you just have to iterate over the new array, like so:
foreach( $reformatted as $dir => $files) {
echo $dir . "
";
foreach( $files as $file)
echo "\t" . $file . "
";
}
This outputs:
dir0
file0.txt
file1.txt
dir1
file2.txt
filea.txt
dir2
fileb.txt
Note that this will only work for plain text environment (such as <pre></pre>
, like in the demo). Otherwise, you'll need to use <br />
instead of for line breaks, or use an ordered or unordered list.
For HTML output, use this, whose output can be seen here
echo '<ul>';
foreach( $reformatted as $dir => $files) {
echo "<li>$dir</li>";
echo '<ul>';
foreach( $files as $file)
echo "<li>$file</li>";
echo '</ul>';
}
echo '</ul>';
Generates:
For your updated array, here is the solution:
$reformatted = array(); $weights = array();
foreach( $paths as $k => $v) {
list( $key, $value) = explode( '|', $v[0]);
if( !isset( $reformatted[$key]))
$reformatted[$key] = array();
if( !isset( $weights[$key]))
$weights[$key] = 0;
$reformatted[$key][] = array( $value, $v[1]);
$weights[$key] += $v[1];
}
foreach( $reformatted as $dir => $files) {
echo $dir . ' (' . $weights[$dir] . ")
";
foreach( $files as $file)
echo "\t" . $file[0] . ' (' . $file[1] . ")
";
}
This outputs:
dir0 (900)
file0.txt (400)
filea.txt (500)
dir1 (1300)
file1.txt (600)
fileb.txt (700)
dir2 (700)
filec.txt (700)
I'll leave it up to you to translate that into HTML if necessary.
You want to use a loop and do this.
<?php
$directories = array();
foreach($arr as $val)
{
$pair = explode('|', $val);
if(!isset($directories[$pair[0]])) { $directories[$pair[0]] = array(); }
$directories[$pair[0]][] = $pair[1];
}
print_r($directories);
That will reorganize your array and then print_r it, showing you the new structure. Then you can do this:
<?php
foreach($directories as $directory => $files)
{
echo "$directory<br><ul>";
foreach($files as $file)
{
echo "<li>$file</li>";
}
echo "</ul>";
}