2012-09-05 7 views
5

を作成し、いくつかは子供である:私はカテゴリの束を持つデータベースを持って再帰カテゴリツリー機能

Array 
(
    [0] => Array 
     (
      [id] => 1 
      [name] => Home Improvement 
      [slug] => Home-Improvement 
      [parent] => 
      [user_id] => 1 
      [order] => 1 
     ) 

    [1] => Array 
     (
      [id] => 2 
      [name] => Asbestos Abatement & Removal 
      [slug] => Asbestos-Abatement-Removal 
      [parent] => 1 
      [user_id] => 1 
      [order] => 8 
     ) 

    [2] => Array 
     (
      [id] => 3 
      [name] => Asphalt & Asphalt Products 
      [slug] => Asphalt-Asphalt-Products 
      [parent] => 1 
      [user_id] => 1 
      [order] => 9 
     ) 

    [3] => Array 
     (
      [id] => 4 
      [name] => Bathroom 
      [slug] => Bathroom 
      [parent] => 1 
      [user_id] => 1 
      [order] => 10 
     ) 

    [4] => Array 
     (
      [id] => 5 
      [name] => Kitchen Cabinets 
      [slug] => Kitchen-Cabinets 
      [parent] => 1 
      [user_id] => 1 
      [order] => 11 
     ) 

    [5] => Array 
     (
      [id] => 6 
      [name] => Ceilings 
      [slug] => Ceilings 
      [parent] => 1 
      [user_id] => 1 
      [order] => 12 
     ) 

    [6] => Array 
     (
      [id] => 7 
      [name] => Cleaning 
      [slug] => Cleaning 
      [parent] => 1 
      [user_id] => 1 
      [order] => 13 
     ) 

    [7] => Array 
     (
      [id] => 8 
      [name] => Closet Organizers & Accessories 
      [slug] => Closet-Organizers-Accessories 
      [parent] => 1 
      [user_id] => 1 
      [order] => 14 
     ) 

    [8] => Array 
     (
      [id] => 9 
      [name] => Concrete 
      [slug] => Concrete 
      [parent] => 1 
      [user_id] => 1 
      [order] => 15 
     ) 

    [9] => Array 
     (
      [id] => 10 
      [name] => Contractors & Service Providers 
      [slug] => Contractors-Service-Providers 
      [parent] => 1 
      [user_id] => 1 
      [order] => 16 
     ) 

私は何を出力しようとしていることは、このようなものです:

<ul> 
    <li>Parent 
     <ul> 
      <li>Child</li> 
     </ul> 
    </li> 
    <li>Parent with no Children</li> 
</ul> 

I PHPで再帰的なツリースクリプトを作成しようとしていますが、私は固執しています。ここに私がこれまで持っているものがあります。私はelseとendifの間で何をすべきかに固執しています。 foreachで。 (そして私はここで簡単に読むためにその構文を使用しています)。

public function makeTree($parent, $array) 
{ 
    if (!is_array($array)) return FALSE; 

    $output = '<ul>'; 

    foreach($array as $key => $value): 
    if ($value['parent'] == $parent): 
     $output .= '<li>'; 

     if ($value['parent'] == NULL): 
      $output .= $value['name']; 

      $subcategories = ci()->db->get_where('categories', array('parent' => $value['id'])); 

      if ($subcategories->num_rows() > 0): 
       $output .= $this->makeTree($value['id'], $subcategories->result_array()); 
      endif; 
     else: 
      $output .= $value['name']; 
      $output .= '</li>'; 
     endif; 
    endif; 

    endforeach; 

    $output .= '</ul>'; 
    return $output; 
} 

:私はおそらく最高のアイデアではありませんforeachループでのデータベース呼び出しを、持っているが

echo $this->categories->makeTree(0, $this->db->get('categories')->result_array()); 

public static function makeTree($parent, $array) 
{ 
    if (!is_array($array)) return ''; 

    $output = '<ul>'; 

    foreach($array as $key => $value): 
    if ($value['parent'] == $parent): 
     $output .= '<li>'; 

     if ($value['parent'] == NULL): 
      $output .= $value['name']; 
     else: 

     endif; 
    endif; 

    $output .= '</li>'; 
    endforeach; 

    $output .= '</ul>'; 
    return $output; 
} 

EDIT 1

私は、この作業を取得することができましたEDIT 2

ここで私の最終的な解決策は、DB qu ERY:

public function makeTree($parent, $array) 
{ 
    if (!is_array($array) OR empty($array)) return FALSE; 

    $output = '<ul>'; 

    foreach($array as $key => $value): 
    if ($value['parent'] == $parent): 
     $output .= '<li>'; 

     if ($value['parent'] == NULL): 
      $output .= $value['name']; 

      $matches = array(); 

      foreach($array as $subkey => $subvalue): 
       if ($subvalue['parent'] == $value['id']): 
        $matches[$subkey] = $subvalue; 
       endif; 
      endforeach; 

      $output .= $this->makeTree($value['id'], $matches); 

     else: 
      $output .= $value['name']; 
      $output .= '</li>'; 
     endif; 
    endif; 

    endforeach; 

    $output .= '</ul>'; 

    return $output; 
} 
+0

現在、2つのレベルをトラバースしています。それをnレベルまでトラバースできますか? –

答えて

7

この回答は思われますが、hereです。表示された機能を使用すると、フラットデータを1回の繰り返しでネストしたデータに変換できます。そのネストされたデータからULリストを作成するのは非常に簡単です。たとえば:

function nested2ul($data) { 
    $result = array(); 

    if (sizeof($data) > 0) { 
    $result[] = '<ul>'; 
    foreach ($data as $entry) { 
     $result[] = sprintf(
     '<li>%s %s</li>', 
     $entry['name'], 
     nested2ul($entry['children']) 
    ); 
    } 
    $result[] = '</ul>'; 
    } 

    return implode($result); 
} 

echo nested2ul(array(flat2nested($yourFlatData)); 

このアプローチの良いところは、あなただけの子要素を見つけるために、入力データの上に何度も何度も再反復する必要がないことです。

+0

私はそれが好きですが、返す$ m [$ r] [0]で "未定義オフセット:0"を取得し続けます。 'makeRecursive関数の中で。私の配列は 'Array([0] => Array([id] => 1、parent)であるのに対し、この関数は' array( 'id' => 5273、 'parent' => 0) ] => 0)) '。どのように私はこれを修正することができます上の任意の提案? – dallen

+0

@dallen投稿した2つのスニペットは実際には同じです。私は、あなたのルートの親の値が空の文字列であることが問題だと思います。ヘルパー関数は '0'を使います(' $ r'パラメータ参照)。配列キーとしての空の文字列は少し問題があるので、入力データでその文字列を変更できれば、残りはうまくいくはずです。 – Yoshi

0

これを試してみてください。私はusualyこのようなものを使用

$cats = $this->db->get('categories')->result_array(); 

echo $this->categories->makeTree(0, $cats); 

public static function makeTree($parent, $array) 
{ 
    if (!is_array($array)) return ''; 

    $output = '<ul>'; 

    foreach($array as $key => $value): 
    if ($value['parent'] == $parent): 
     $output .= '<li>'; 

     if ($value['parent'] == NULL): 
      $output .= $value['name']; 
     else: 

     endif; 
    endif; 

    $output .= '</li>'; 

    $output .= $this->categories->makeTree($value['parent'], $cats); 

    endforeach; 

    $output .= '</ul>'; 
    return $output; 
} 
+0

動作しません。私はちょうど500エラーで破損したページを取得します。 – dallen

1

、コードのこの作品は廃止mysql_を使用している

は、第一に注意してください*

第二あなたはlevelという名前のデータベースフィールドを1つ持つ必要があります。NULLの場合はメインカテゴリ、数値の場合はnのカテゴリのサブカテゴリですumber as id

function getFamilies($level = 0) { 
    $level++; 
    $sql = "SELECT id from families WHERE level IS NULL"; 
    if (mysql_num_rows($result) > 0) { 
     echo "<ul>"; 
      while($row = mysql_fetch_assoc($result)) { 
       echo "<li>".$row['id']; 
        getSubFamilies($level, $row['id']); 
       echo "</li>"; 
      } 
     echo "</ul>"; 
    } 
} 

function getSubFamilies($level, $id) { 
    $level++; 
    $sqlSubFamilies = "SELECT id FROM families WHERE level = ".$id.""; 
    $resultSubFamilies = mysql_query($sqlSubFamilies); 
    if (mysql_num_rows($resultSubFamilies) > 0) { 
     echo = "<ul>"; 
      while($rowSubFamilies = mysql_fetch_assoc($resultSubFamilies)) { 
       echo "<li>".$rowSubFamilies['id']; 
        getSubFamilies($level, $rowSubFamilies['id']); 
       echo "</li>"; 
      } 
     echo "</ul>"; 
    } 
} 

getFamilies($level = 0); 
+0

あなたのケースでは、レベルは親ですので、 "親がnullのカテゴリからのIDを選択してください" – Pluda

2

ここで私の最終的な解決策は、DBクエリを実行する代わりに配列を再利用することです。あなたがより良い解決策を持っているなら、投稿してください!

public function makeTree($parent, $array) 
{ 
    if (!is_array($array) OR empty($array)) return FALSE; 

    $output = '<ul>'; 

    foreach($array as $key => $value): 
    if ($value['parent'] == $parent): 
     $output .= '<li>'; 

     if ($value['parent'] == NULL): 
      $output .= $value['name']; 

      $matches = array(); 

      foreach($array as $subkey => $subvalue): 
       if ($subvalue['parent'] == $value['id']): 
        $matches[$subkey] = $subvalue; 
       endif; 
      endforeach; 

      $output .= $this->makeTree($value['id'], $matches); 

     else: 
      $output .= $value['name']; 
      $output .= '</li>'; 
     endif; 
    endif; 

    endforeach; 

    $output .= '</ul>'; 

    return $output; 
} 
0

匿名機能を使用するこの方法は非常に簡単だと思います。

//--------------------------- PRINT NESTED CATEGORIES 
$cats_childs = array(); 

$q = $db->query("SELECT id, parent, name FROM categories"); 

while ($r = $db->row($q)) 
{ 
    $cats_childs[$r['parent']][$r['id']] = $r; 
} 

$nested2ul = function($data) use (&$nested2ul, &$cats_childs) { 
    if (!empty($data)) { 
     echo '<ul>'; 
     foreach ($data as $r) { 
      echo '<li>'; 
      echo $r['name']; 
      $flat2ul($cats_childs[$r['id']]); 
      echo '</li>'; 
     } 
     echo '</ul>'; 
    } 
}; 

echo $nested2ul($cats_childs[0]); 
関連する問題