如何在Codeigniter中用GROUP BY统计category_post类型分类的文章数
问题解决
错误原因分析
- ORA-00979: 最初的GROUP BY问题是因为Oracle要求SELECT中的所有非聚合字段必须出现在GROUP BY子句中,虽你的代码已包含相关字段,但
LEFT JOIN搭配WHERE CATEGORY.CATEGORY_TYPE='TYPE_POST'会自动转为INNER JOIN,逻辑上需调整写法避免歧义。 - ORA-00936: 多是修改代码时出现语法错误,比如漏写字段、括号不匹配等;另外原百分比计算逻辑有误——
COUNT(*)是当前分组的行数,不是符合条件的总文章数,导致结果不符合预期。 - 视图展示错误: 视图错误引用
$row1->ID,实际应调用total_posts,且未输出百分比数据。
修正后的代码
Model代码
class My_model extends CI_Model { function get_post_by_category() { // 获取符合条件的总文章数,用于计算百分比 $total_posts = $this->db->select('COUNT(*) as total') ->from('POST') ->join('CATEGORY', 'POST.CATEGORY_ID = CATEGORY.ID') ->where('CATEGORY.CATEGORY_TYPE', 'TYPE_POST') ->get()->row()->total; $q = $this->db->select('POST.CATEGORY_ID, CATEGORY.CATEGORY_NAME, COUNT(POST.ID) as total_posts, (COUNT(POST.ID)/' . $total_posts . ') * 100 as percentage') ->from('POST') ->join('CATEGORY', 'POST.CATEGORY_ID = CATEGORY.ID') // 用INNER JOIN即可,仅需关联TYPE_POST的分类 ->where('CATEGORY.CATEGORY_TYPE', 'TYPE_POST') ->group_by('POST.CATEGORY_ID, CATEGORY.CATEGORY_NAME') ->order_by('POST.CATEGORY_ID', 'ASC') ->get(); return $q->result(); } }
View代码
<table border="1"> <tbody> <tr> <td>分类名称</td> <td>文章总数</td> <td>占比%</td> </tr> <?php foreach ($countdata as $row1): ?> <tr> <td><?php echo $row1->CATEGORY_NAME; ?></td> <td><?php echo $row1->total_posts; ?></td> <td><?php echo number_format($row1->percentage, 2); ?>%</td> </tr> <?php endforeach; ?> </tbody> </table>
Controller代码(优化冗余加载)
public function __construct() { parent::__construct(); $this->load->model('My_model'); } function index() { $data['countdata'] = $this->My_model->get_post_by_category(); $this->load->view('data/my_view', $data); }
关键调整点
- 将
LEFT JOIN改为INNER JOIN,因仅需关联类型为TYPE_POST的分类,LEFT JOIN无实际意义。 - 单独查询符合条件的总文章数,确保百分比为该分类文章数占总符合条件文章数的比例。
- 视图中修正字段引用,添加百分比格式化输出。
- 去除Controller中重复的模型加载代码。
内容的提问来源于stack exchange,提问作者CodingStudent
相关产品推荐
相关产品推荐

