以下是查询有效MySQL:

SELECT * FROM table WHERE field & number = number; 
# to find values with superset of number's bits

SELECT * FROM table WHERE field | number = number; 
# to find values with subset of number's bits

...如果一个指数领域已经建立?

如果没有,是否有办法让它运行速度更快?

有帮助吗?

解决方案

更新:

看到这个条目的,在我的博客的性能的详细信息:


SELECT * FROM table WHERE field & number = number

SELECT * FROM table WHERE field | number = number

这个指数可以有效地在两个方面:

  1. 为了避免早期表扫描(由于价值的比较载在索引本身)
    • 限制的数值范围内审查。

既没有条件,在查询上 可优化搜索, 这是索引将不会被用于范围扫描(带条件,因为他们现在的).

然而,点 1 仍然拥有,而指标可能是有用的。

如果你的表包含的说, 100 字节每一行中的平均水平, 1,000,000 记录,然后该表格的扫描将需要扫描 100 Mb 数据。

如果你有一个指数(一个 4字节的关键, 6-byte行指针和一些内部开销),查询将需要只扫描 10 Mb 数据加上额外的数据表如果该过滤器成功。

  • 该表格的扫描是更有效的如果你的状况不是选择性的(你已经高probablility到匹配的条件)。
  • 索引扫描效率更高,如果你的条件是选择性的(你已经低probablility到匹配的条件)。

这些查询将需要扫描整个索引。

但是,通过改写的 AND 查询可以得益于范围上的索引。

这个条件:

field & number = number

只能相匹配的领域,如果最高位 number 设置 field 太。

你应该只是提供这种额外的条件来查询:

SELECT  *
FROM    table
WHERE   field & number = number
        AND field >= 0xFFFFFFFF & ~((2 << FLOOR(LOG(2, 0xFFFFFFFF & ~number))) - 1)

这将使用范围粗筛选和条件的细筛选。

越位 number 是取消在结束时,将更好。

其他提示

我怀疑优化器将可以认识到这一个...

也许你可以调用EXPLAIN这些查询并确认我的悲观猜测。 (当然记住这么多的查询计划决定是基于给定数据库的特定实例,即数据的不同量和/矿石仅仅数据具有不同统计分布可以产生不同的计划)。

假设表具有行的显著量,并且“bitwised”标准仍然足够选择性的)避免按位操作时在每个单列,通过用IN构造重写查询的可能的优化得以实现(或者用JOIN)

类似的东西(概念,即未测试)

CREATE TEMPORARY TABLE tblFieldValues
  (Field INT);

INSERT INTO tblFieldValues
   SELECT DISTINCT Field
   FROM table;

-- SELECT * FROM table WHERE field | number = number; 
-- now becomes
SELECT * 
FROM table t
WHERE field IN 
    (SELECT Field 
     FROM tblFieldValues 
     WHERE field | number = number); 
(所有这些具有相当大的数目在表的行中,因为否则直接“WHERE字段|数=数”的方法是足够有效的)

这样需要的方法的全部好处与不同的使用情况进行评价,但我怀疑这可能是显著更快。进一步走高可能,如果“tblFieldValues”不需要每次都重新来实现。高效地创建该表当然的意味着原始表上的字段的索引。

我这个尝试我自己,和位运算不足以防止Mysql的从“田”列使用索引。它是可能的,虽然,该指数的完全扫描正在发生。

许可以下: CC-BY-SA归因
不隶属于 StackOverflow
scroll top