You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

CodeIgniter3查询构造器实现排除另一表数据的查询问题

解决CodeIgniter3中排除未归还品牌的下拉选项问题

嘿,我知道你现在卡在这个查询上了,咱们一步步来搞定它!

首先,你的现有代码失效主要有两个核心原因:

  • 逻辑搞反了:你要排除的是未归还的品牌(也就是datereturned为NULL或者等于'0000 00 00'的记录),但原来的条件是排除date_returned != '0000 00 00'的品牌,完全搞反了方向。
  • NOT IN的隐形坑:如果子查询返回的brand里存在NULL值,NOT IN会直接返回空结果——因为SQL里任何值和NULL比较的结果都是UNKNOWN,不会匹配任何行。

推荐方案:用NOT EXISTS(更可靠,处理NULL无压力)

NOT EXISTS是处理这类排除查询的最佳选择,它不会因为NULL值出问题,逻辑也更直观。下面是适配CodeIgniter3的写法:

$data = $this->db
    ->select('*')
    ->from('inventory')
    // 核心逻辑:排除那些在交易表中存在未归还记录的品牌
    ->where_not_exists("
        SELECT 1 
        FROM inven_trans 
        WHERE inven_trans.brand = inventory.brand 
        AND (inven_trans.datereturned IS NULL OR inven_trans.datereturned = '0000 00 00')
    ")
    ->get()
    ->result_array();

注意:如果你的交易表实际名称是ha_inventory_trans(和你代码里写的一致),记得把上面的inven_trans改成对应的表名。

备选方案:修正后的NOT IN(需规避NULL问题)

如果你坚持要用NOT IN,必须确保子查询不会返回NULL的brand,同时修正逻辑:

$data = $this->db
    ->select('*')
    ->from('inventory')
    ->where("
        brand NOT IN (
            SELECT DISTINCT brand 
            FROM ha_inventory_trans 
            WHERE (datereturned IS NULL OR datereturned = '0000 00 00') 
            AND brand IS NOT NULL
        )", 
        NULL, 
        FALSE
    )
    ->get()
    ->result_array();

这里加了DISTINCT来减少重复的品牌值,同时用brand IS NOT NULL避免子查询返回NULL,彻底解决NOT IN的失效问题。

额外提醒

  • 检查日期格式:如果你的数据库日期字段是标准的YYYY-MM-DD格式,记得把'0000 00 00'改成'0000-00-00'。
  • 性能优化:如果数据量较大,给inven_trans表的brand和datereturned字段加索引,能显著提升查询速度。

内容的提问来源于stack exchange,提问作者goaty

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.27 08:52:29