繁体   English   中英

按类别对mysql结果进行分组,并将它们显示在每个类别下的组中

[英]Group mysql results by category and display them into groups under each category

我正在尝试创建一个简单的css菜单,从mysql表中获取数据。

我的想法是有这样的菜单

    Category 1
    - link 1
    - link 2
    - link 3
    Category 2
    - link 1
    - link 2
    - ect...

每个链接都有一个名为“category”的字段。 所以我想在每个类别的菜单中分组和显示链接。

我有mysql分组之类的

$sql = "SELECT * FROM content group by category";
$result = mysql_query($sql); 

然后我有像这样的HTML

<ul class="menu">
    <li id="category1" class="files">
         <a href="#category1">Category 1</a>
         <ul class="sub-menu">
             <li><a href="#">link 1</li>
             <li><a href="#">link 2</li>
             <li><a href="#">link 3</li>
         </ul>
     </li>
    <li id="category2" class="files">
         <a href="#category2">Category 2</a>
         <ul class="sub-menu">
             <li><a href="#">link 1</li>
             <li><a href="#">link 2</li>
             <li><a href="#">link 3</li>
         </ul>
     </li>
 </ul>

db表看起来像这样

CREATE TABLE IF NOT EXISTS `content` (
  `id` int(11) NOT NULL AUTO_INCREMENT,
  `menu_name` text,
  `menu_name_en` text,
  `menu_url` varchar(255) NOT NULL DEFAULT '',
  `header_name` text,
  `header_name_en` enum('MEDIA','GENERAL') NOT NULL DEFAULT 'MEDIA',
  `text` longtext NOT NULL,
  `text_en` text,
  `category` enum('Category 1', 'Category 2') NOT NULL DEFAULT 'Category 1',
  `date` date NOT NULL DEFAULT '0000-00-00',
  `visible` char(1) NOT NULL DEFAULT '0',
  PRIMARY KEY (`id`)
);

INSERT INTO content (id, menu_name, menu_name_en, menu_url, header_name, header_name_en, text, text_en, category, date, visible) VALUES (26, 'test name', '', 'test_url', 'test name', '', '<p>test text</p>', '<p>text text</p>', 'MEDIA', '2014-02-23', '1');

所以,我在将结果放入循环并按类别创建html时遇到了麻烦。

我在这里阅读了许多相似内容的帖子,但无法达到我想要的结果。 任何帮助都感激不尽。 谢谢!

我会改用ORDER BY category 然后,您可以迭代结果集

$old = null;
foreach ($st as $s) {
  if $old != $s['id']
    echo 'Main category';
    $old = $s['id'];
  echo 'subcategory'

更新

到目前为止,这个问题本身存在三种可能的解决方案。

原始选项1

SELECT * FROM content group by category
foreach
  SELECT * FROM content WHERE category=$cat['category']

如果只想让每个父类别获得一次,则应该使用DISTINCT 不使用任何聚合函数就不应该使用GROUP BY GROUP BYSELECT *的组合仅限于(主要)MySQL。 在这种情况下,您无法在ASNI SQL中选择任意列。

选项1的变体

SELECT DISTINCT category FROM content ORDER BY category
foreach
  SELECT * FROM content WHERE category=$cat['category']

这是使用DISTINCT而不是GROUP BY的更正版本。

它仍然缺乏嵌套查询调用。 对于5个父类别,这将导致循环中的5个查询。 对于10个父类别,内部已有10个查询。 人们应该避免这种增长。

选项3

SELECT * FROM content ORDER BY category, menu_name

可用于上面的代码。

由于不同的原因,这比显示的其他选项更可取:

  • 您只需要一个数据库查询即可立即收集所有数据。 数据库花费(简单查询)大部分时间来解析提供的SQL语句,并且只有一小部分时间来实际收集您请求的数据。 如果您提供了大量SQL代码,则必须花费大量时间来解析它。 如果您提供的代码较少,则可以做的更少。
  • 数据库更容易获取数据一次,将其排序一次并将其返回给您一次,而不是收集零件,对零件进行排序,返回零件并重新开始。

尚未说明的选项4

存在一个直到现在未说明的进一步解决方案。 可以使用预准备语句,准备一次 SQL并使用不同的ID运行它。 这仍然会查询循环内的所有类别,但是不必每次都解析SQL代码。

实际上我不知道这比我的解决方案更好还是更坏(或者介于两者之间)。

SQL GROUP BY语句对结果进行分组,以便每个类别只返回一行。 这通常与count()之类的聚合函数结合使用,以计算每个类别中的项目数。 你需要的是GhostGambler所说的ORDER BY ,或者如下所示的每个类别的单独查询。 然而,由于您似乎只有两个类别,这种方法似乎不必要地复杂化。

 $q=$db->query("SELECT DISTINCT category FROM content ORDER BY category");
 foreach($q as $cat){
    echo '<li id="'.$cat['category'].'" class="files">';  
    echo '<a href="'.$cat['category'].'">'.$cat['category'].'</a>'; 
    echo '<ul class="sub-menu">';
    $linkq=$db->query("SELECT * FROM content WHERE category='" . $cat['category'] . "'"); 
    foreach($linkq as $link){
       echo '<li><a href="#">'.$link['menu_name'].'</a></li>';
    }
    echo '</ul></li>';
 }

你的查询错了

$sql = "SELECT * FROM content WHERE group by category";

应该

$sql = "SELECT * FROM content group by category";

此外,因为不推荐使用mysql而不使用它。 请改用mysqli或PDO

我假设您想要动态添加子菜单。 如果是,则首先为子菜单创建第二个表,并在菜单和子菜单表之间添加关系。

$select=$connection->query("select * from menus");
    while($result=$select->fetch_assoc()){
    echo "<li>";        
    echo "<a href=\"#\">".$result['MenuTitle']."</a>";
    $menuid=$result['MenuId'];
    if($result==true){
    $selectsubmenu=$connection->query("Select * from submenu where menuid='$menuid'");
        echo "<ul>";
            while($resultsubmenu=$selectsubmenu->fetch_assoc()){     
                    echo "<li><a href=\"Services.php?submenu=".$resultsubmenu['SubMenuId']."\">".$resultsubmenu['SubMenuTitle']."
                    </a></li>";
                    }
        echo "</ul>";
                }
            echo "</li>";   
}

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM