免费注册 查看新帖 |

Chinaunix

  平台 论坛 博客 文库
最近访问板块 发新帖
查看: 5984 | 回复: 9
打印 上一主题 下一主题

mysql关于where子句对列计算时 索引无效的问题,请进 [复制链接]

论坛徽章:
0
跳转到指定楼层
1 [收藏(0)] [报告]
发表于 2011-03-08 15:42 |只看该作者 |倒序浏览
这样的 例如:我有一个50万行的表
CREATE TABLE t1(
   name varchar(32),
   code int,
   key (code)
);
现在 我有这样一个sql:
SELECT * FROM t1 WHERE code&14=14;
此时 code的索引是无效的,从explain可以看出
mysql仍然会扫描所有50万行数据。
请问这样我要怎样才能提高查询效率呢?

论坛徽章:
0
2 [报告]
发表于 2011-03-08 16:06 |只看该作者
SELECT * FROM t1 WHERE code&14=14;

很明显这句话是用不到索引的。
MYSQL不支持函数索引,索引只能进行简单判断,而不能经过运算后进行比较。

SELECT * FROM t1 WHERE code+14=14;
这样用不到索引。

SELECT * FROM t1 WHERE code=14-14;
这样可以用到索引。

论坛徽章:
0
3 [报告]
发表于 2011-03-08 16:10 |只看该作者
回复 2# 909413335


    是啊 , 这可难死我了,按位与这种操作貌似又不能像四则运算一样改到等号的另一边
我那code是按位存放的特征,要按特征检索的。麻烦了

论坛徽章:
0
4 [报告]
发表于 2011-03-08 16:34 |只看该作者
哈哈,
你可以在表里添加一列,就是按位与操作的结果,用触发器来维护这个值,然后在查询的时候就可以直接用这个字段来做索引了。

论坛徽章:
0
5 [报告]
发表于 2011-03-08 16:42 |只看该作者
哎 这个 要与的操作数是临时的

论坛徽章:
0
6 [报告]
发表于 2011-03-08 16:49 |只看该作者
其实我就是要code里面某几位为1的列...

论坛徽章:
0
7 [报告]
发表于 2011-03-08 16:51 |只看该作者
换个思路看看。

其实我就是要code里面某几位为1的列...


举个例子出来。

论坛徽章:
0
8 [报告]
发表于 2011-03-08 17:00 |只看该作者
是这样的,产品有一些特征。用户检索的时候需要根据综合特征来进行检索
如果我把这些特征都弄成列的话,到是方便索引
但第一,索引占用空间很大
第二,维护变的很麻烦

所以我就想给特征进行编码,例如
可加速=1
可变形=2
高熔点=4
可浸泡=8
以此类推,那么更新一个产品的时候,只要把这个产品的所有特点相加,就成为这个产品的特征码

当用户检索一个可浸泡可加速的产品的时候,特征码是9

我只要用库存产品的特征码按位与检索特征码==检索特征码这样的方法来判断,就能检索出用户想要的产品

但是因为索引无效,当表行大了之后,就会形成性能瓶颈

让我很无奈

论坛徽章:
0
9 [报告]
发表于 2011-03-08 17:15 |只看该作者
呵呵,这样啊。
你干脆多搞几个字段,P1-P20
假定有20个特征,每个产品有N个特征,就对应在P1-P20字段里面有值,其他默认NULL,

查询的时候就很方便了,也不需要总去改变表结构。

论坛徽章:
0
10 [报告]
发表于 2011-03-08 17:24 |只看该作者
嗯 看来只好这么办了 20中特征就加20列,联合索引一下...
您需要登录后才可以回帖 登录 | 注册

本版积分规则 发表回复

  

北京盛拓优讯信息技术有限公司. 版权所有 京ICP备16024965号-6 北京市公安局海淀分局网监中心备案编号:11010802020122 niuxiaotong@pcpop.com 17352615567
未成年举报专区
中国互联网协会会员  联系我们:huangweiwei@itpub.net
感谢所有关心和支持过ChinaUnix的朋友们 转载本站内容请注明原作者名及出处

清除 Cookies - ChinaUnix - Archiver - WAP - TOP