• ADADADADAD

    说Mysql的distinct语句和group by,order by[ mysql数据库 ]

    mysql数据库 时间:2024-12-24 19:09:59

    作者:文/会员上传

    简介:

    最近,在做一个项目的时候,发现得出的数据于预料的相差很多,仔细的研究了一下,发现问题出在 distinct语句和groupy by,order by
    首先,distinct语句,获得非重复的(唯一)行记.
    grouy by

    以下为本文的正文内容,内容仅供参考!本站为公益性网站,复制本文以及下载DOC文档全部免费。

    最近,在做一个项目的时候,发现得出的数据于预料的相差很多,仔细的研究了一下,发现问题出在 distinct语句和groupy by,order by
    首先,distinct语句,获得非重复的(唯一)行记.
    grouy by是分组,order by 是排序。

    直接看我的例子。

    假定我有一个表f_job,有字段:

    select job_id, com_id,job_time from f_job order by job_time desc limit 10; T e:webwebphpfhrtee.txt
    +--------+--------+---------------------+
    | job_id | com_id | job_time |
    +--------+--------+---------------------+
    | 5060 | 2205 | 2006-09-29 16:30:11 |
    | 4707 | 19084 | 2006-09-29 16:27:55 |
    | 4708 | 19084 | 2006-09-29 16:27:55 |
    | 4709 | 19084 | 2006-09-29 16:27:55 |
    | 4710 | 19084 | 2006-09-29 16:27:55 |
    | 4711 | 19084 | 2006-09-29 16:27:55 |
    | 4859 | 19084 | 2006-09-29 16:27:55 |
    | 4918 | 19084 | 2006-09-29 16:27:55 |
    | 5059 | 2205 | 2006-09-29 16:27:22 |
    | 4078 | 2715 | 2006-09-29 16:18:36 |
    +--------+--------+---------------------+
    10 rows in set (0.03 sec)

    还有其他字段,不可能影响结果.此处不列出。

    job_id是primary key。 com_id是外键,我需要按照时间来排序。所以必须使用order by!

    你看到了com_id在得出的结果中不唯一,对,我需要的结果就是提取com_id唯一的最近10条com_id的记录,而已。

    我就以以前的MSSQL的经验写如下的语句执行:

    mysql> select distinct( com_id) from f_job order by job_time desc limit 10; T e:webwebphpfhrtee.txt
    +--------+
    | com_id |
    +--------+
    | 19084 |
    | 2197 |
    | 19917 |
    | 19580 |
    | 19520 |
    | 19664 |
    | 19397 |
    | 19900 |
    | 1176 |
    | 19449 |
    +--------+

    对,这次得出的结果是唯一,但是,这不对呀,很明显,把com_id记录号码是2005的记录给没了,这结果肯定错。马上分析一下所有的的结果,发现忽略的com_id并没有消失,只是被排到后面去了。

    我按照时间排序,应该出现的结果第一个就是2205呀,为什么能排到后面?从两条可疑记录看出了结果:

    原记录:
    | 5058 | 19580 | 2006-09-29 15:23:58 |
    | 5057 | 19917 | 2006-09-29 15:14:16 |
    | 4973 | 19580 | 2006-09-29 15:13:49 |
    | 5011 | 19580 | 2006-09-29 15:13:49 |
    distinct后的次序:


    | 19917 |
    | 19580 |

    这说明,对于不是在一起的隔行记录,如果恰巧隔一行,还可以被order by 比较出来,否则比较出来的不再真实,这是因为,被缓存的上次的order by 的临时值在客观上不再有用!还有一种情况,如果记录连着,也可以被比较出来。

    先是明白了MySql的弱智了。

    马上又执行了一下操作,结果如下: mysql> select distinct(com_id),job_time from f_job order by job_time desc limit 10;
    +--------+---------------------+
    | com_id | job_time |
    +--------+---------------------+
    | 2205 | 2006-09-29 16:30:11 |
    | 19084 | 2006-09-29 16:27:55 |
    | 2205 | 2006-09-29 16:27:22 |
    | 2715 | 2006-09-29 16:18:36 |
    | 2197 | 2006-09-29 16:03:16 |
    | 19580 | 2006-09-29 15:23:58 |
    | 19917 | 2006-09-29 15:14:16 |
    | 19580 | 2006-09-29 15:13:49 |
    | 19520 | 2006-09-29 10:29:41 |
    | 19900 | 2006-09-29 10:16:48 |
    +--------+---------------------+
    10 rows in set (0.10 sec)

    先和这个比较一下:
    mysql> select com_id,job_time from f_job order by job_time desc limit 10; T e:webwebphpfhrtee.txt
    +--------+---------------------+
    | com_id | job_time |
    +--------+---------------------+
    | 2205 | 2006-09-29 16:30:11 |
    | 19084 | 2006-09-29 16:27:55 |
    | 19084 | 2006-09-29 16:27:55 |
    | 19084 | 2006-09-29 16:27:55 |
    | 19084 | 2006-09-29 16:27:55 |
    | 19084 | 2006-09-29 16:27:55 |
    | 19084 | 2006-09-29 16:27:55 |
    | 19084 | 2006-09-29 16:27:55 |
    | 2205 | 2006-09-29 16:27:22 |
    | 2715 | 2006-09-29 16:18:36 |
    +--------+---------------------+
    10 rows in set (0.06 sec)
    发现,distinct恰巧和前面第一次测试的结果相反处理我们的信息,他把隔行的看作不同的结果输出,这就导致了2205的记录又出现了。

    然后我就用了group by语句,应该可以吧,结果也让我。。。:
    mysql> select com_id from f_job group by com_id order by job_time desc limit 10;
    +--------+
    | com_id |
    +--------+
    | 19084 |
    | 2197 |
    | 19917 |
    | 19580 |
    | 19520 |
    | 19664 |
    | 19397 |
    | 19900 |
    | 1176 |
    | 19449 |
    +--------+
    10 rows in set (0.03 sec)

    这和distinct的结果一样,这倒不出乎意料,然后我又加入分组job_time,看看:
    mysql> select com_id from f_job group by com_id,job_time order by job_time desc limit 10;
    +--------+
    | com_id |
    +--------+
    | 2205 |
    | 19084 |
    | 2205 |
    | 2715 |
    | 2197 |
    | 19580 |
    | 19917 |
    | 19580 |
    | 19520 |
    | 19900 |
    +--------+
    10 rows in set (0.03 sec)

    这结果差一点点了,然后我再distinct(com_id)一下,应该可以了吧!看看:
    mysql> select distinct(com_id) from f_job group by com_id,job_time order by job_time desc limit 10; T e:webwebphpfhrtee.txt
    +--------+
    | com_id |
    +--------+
    | 19084 |
    | 2197 |
    | 19917 |
    | 19580 |
    | 19520 |
    | 19664 |
    | 19397 |
    | 19900 |
    | 1176 |
    | 19449 |
    +--------+
    10 rows in set (0.04 sec)

    汗,这和没加group by 的一点区别都没,怎么这样弱呀!没办法,这怎么办,犹豫中。。。

    上面的问题彻底的说明了这样一个事实:distinct只能返回它的目标字段,而无法返回其它字段。。。

    汗,这和没加group by 的一点区别都没,怎么这样弱呀!没办法,这怎么办,犹豫中。。。

    ------------------------------------
    想起了一个很能骚的一个人--phzzy,这jh,qq说了句话,果然在,他玩php,马上求助,经过1个多小时的艰苦YY,终于这鸟人先大爷我一步给出语句:

    select (`com_id`),max(`job_time`) from `f_job` GROUP BY `com_id` order by max(`job_time`) limit 10;

    mdgb,终于明白了,刚拿到这语句就明白了。

    我tmd知道这是2次排序,md,group by是一次,然后无论怎么样,都不可能2次排序,因为第二次必须借助内部的集聚函数。。。。。。我怎么没想到max,气死我了[@more@]
    说Mysql的distinct语句和group by,order by.docx

    将本文的Word文档下载到电脑

    推荐度:

    下载
    热门标签: grct