广告
返回顶部
首页 > 资讯 > 数据库 >如何设计数据库索引
  • 418
分享到

如何设计数据库索引

2024-04-02 19:04:59 418人浏览 独家记忆
摘要

本篇内容主要讲解“如何设计数据库索引”,感兴趣的朋友不妨来看看。本文介绍的方法操作简单快捷,实用性强。下面就让小编来带大家学习“如何设计数据库索引”吧!MySQL中的索引Mysql中的InnoDB引擎使用B

本篇内容主要讲解“如何设计数据库索引”,感兴趣的朋友不妨来看看。本文介绍的方法操作简单快捷,实用性强。下面就让小编来带大家学习“如何设计数据库索引”吧!

MySQL中的索引

Mysql中的InnoDB引擎使用B+Tree结构来存储索引,可以尽量减少数据查询时磁盘io次数,同时树的高度直接影响了查询的性能,一般树的高度维持在  3~4 层。

B+Tree由三部分组成:根root、枝branch以及Leaf叶子,其中root和branch不存储数据,只存储指针地址,数据全部存储在Leaf  node,同时Leaf Node之间用双向链表链接,结构如下:

如何设计数据库索引

从上面可以看到,每个Leaf  Node是三部分组成的,即前驱指针p_prev,数据data以及后继指针p_next,同时数据data是有序的,默认是升序ASC,分布在B+tree右边的键值总是大于左边的,同时从root到每个Leaf的距离是相等的,也就是访问任何一个Leaf  Node需要的IO是一样的,即索引树的高度Level + 1次IO操作。

我们可以将mysql中的索引可以看成一张小表,占用磁盘空间,创建索引的过程其实就是按照索引列排序的过程,先在sort_buffer_size进行排序,如果排序的数据量大,sort_buffer_size容量不下,就需要通过临时文件来排序,最重要的是通过索引可以避免排序操作(distinct,group  by,order by)。

聚集索引

Mysql中的表是IOT(Index Organization  Table,索引组织表),数据按照主键id顺序存储(逻辑上是连续,物理上不连续),而且主键id是聚集索引(clustered  index),存储着整行数据,如果没有显示的指定主键,MySQL会将所有的列组合起来构造一个row_id作为primary key,例如表users(id,  user_id, user_name, phone, primary key(id)),id是聚集索引,存储了id, user_id, user_name,  phone整行的数据。

辅助索引

如何设计数据库索引

辅助索引也称为二级索引,索引中除了存储索引列外,还存储了主键id,对于user_name的索引idx_user_name(user_name)而言,其实等价于idx_user_name(user_name,  id),MySQL会自动在辅助索引的最后添加上主键id,熟悉oracle数据库的都知道,索引里除了索引列还存储了row_id(代表数据的物理位置,由四部分组成:对象编号+数据文件号+数据块号+数据行号),我们在创建辅助索引也可以显示添加主键id。

-- 创建user_name列上的索引 mysql> create index idx_user_name on users(user_name); -- 显示添加主键id创建索引 mysql> create index idx_user_name_id on users(user_name,id); -- 对比两个索引的统计数据 mysql> select a.space as tbl_spaceid, a.table_id, a.name as table_name, row_fORMat, space_type,  b.index_id , b.name as index_name, n_fields, page_no, b.type as index_type  from information_schema.INNODB_TABLES a left join information_schema.INNODB_INDEXES b  on a.table_id =b.table_id where a.name = 'test/users'; +-------------+----------+------------+------------+------------+----------+------------------+----------+------ | tbl_spaceid | table_id | table_name | row_format | space_type | index_id | index_name       | n_fields | page_no | index_type | +-------------+----------+------------+------------+------------+----------+------------------+----------+------ |         518 |     1586 | test/users | Dynamic    | Single     |     1254 | PRIMARY          |        9 |       4 |          3 | |         518 |     1586 | test/users | Dynamic    | Single     |     4003 | idx_user_name    |        2 |       5 |          0 | |         518 |     1586 | test/users | Dynamic    | Single     |     4004 | idx_user_name_id |        2 |      45 |          0 | mysql> select index_name, last_update, stat_name, stat_value, stat_description from mysql.innodb_index_stats where index_name in ('idx_user_name','idx_user_name_id'); +------------------+---------------------+--------------+------------+-----------------------------------+ | index_name       | last_update         | stat_name    | stat_value | stat_description                  | +------------------+---------------------+--------------+------------+-----------------------------------+    | idx_user_name    | 2021-01-02 17:14:48 | n_leaf_pages |       1358 | Number of leaf pages in the index | | idx_user_name    | 2021-01-02 17:14:48 | size         |       1572 | Number of pages in the index      | | idx_user_name_id | 2021-01-02 17:14:48 | n_leaf_pages |       1358 | Number of leaf pages in the index | | idx_user_name_id | 2021-01-02 17:14:48 | size         |       1572 | Number of pages in the index      |

对比一下两个索引的结果,n_fields表示索引中的列数,n_leaf_pages表示索引中的叶子页数,size表示索引中的总页数,通过数据比对就可以看到,辅助索引中确实包含了主键id,也说明了这两个索引时完全一致。

如何设计数据库索引

索引回表

上面证明了辅助索引包含主键id,如果通过辅助索引列去过滤数据有可能需要回表,举个例子:业务需要通过用户名user_name去查询用户表users的信息,业务接口对应的SQL:

select  user_id, user_name, phone from users where user_name = 'Laaa';

我们知道,对于索引idx_user_name而言,其实就是一个小表idx_user_name(user_name,  id),如果只查询索引中的列,只需要扫描索引就能获取到所需数据,是不需要回表的,如下SQL语句:

SQL 1: select id, user_name from users where user_name = 'Laaa';

SQL 2: select id from users where user_name = 'Laaa';

mysql> explain select id, name from users where name = 'Laaa'; +----+-------------+-------+------------+------+---------------+---------------+---------+-------+------+------- | id | select_type | table | partitions | type | possible_keys | key           | key_len | ref   | rows | filtered | Extra       | +----+-------------+-------+------------+------+---------------+---------------+---------+-------+------+------- |  1 | SIMPLE      | users | NULL       | ref  | idx_user_name | idx_user_name | 82      | const |    1 |   100.00 | Using index | mysql> explain select id from users where name = 'Laaa'; +----+-------------+-------+------------+------+---------------+---------------+---------+-------+------+------- | id | select_type | table | partitions | type | possible_keys | key           | key_len | ref   | rows | filtered | Extra       | +----+-------------+-------+------------+------+---------------+---------------+---------+-------+------+------- |  1 | SIMPLE      | users | NULL       | ref  | idx_user_name | idx_user_name | 82      | const |    1 |   100.00 | Using index |

SQL 1和SQL 2的执行计划中的Extra=Using index 表示使用覆盖索引扫描,不需要回表,再来看上面的业务SQL:

select user_id, user_name, phone from users where user_name = 'Laaa';

可以看到select后面的user_id,phone列不在索引idx_user_name中,就需要通过主键id进行回表查找,MySQL内部分如下两个阶段处理:

Section 1:select **id** from users where user_name = 'Laaa' //id = 100101

Section 2: select user_id, user_name, phone from users where id = 100101;

将Section 2的操作称为回表,即通过辅助索引中的主键id去原表中查找数据。

索引高度

MySQL的索引时B+tree结构,即使表里有上亿条数据,索引的高度都不会很高,通常维持在3-4层左右,我来计算下索引idx_name的高度,从上面知道索引信息:index_id  = 4003, page_no = 5,它的偏移量offset就是page_no x innodo_page_size + 64 =  81984,通过hexdump进行查看

$hexdump -s 81984 -n 10 /usr/local/var/mysql/test/users.ibd 0014040 00 02 00 00 00 00 00 00 0f a3                   001404a

其中索引的PAGE_LEVEL为00,即idx_user_name索引高度为1,0f a3  代表索引编号,转换为十进制是4003,正是index_id。

数据扫描方式

全表扫描

从左到右依次扫描整个B+Tree获取数据,扫描整个表数据,IO开销大,速度慢,等严重,影响MySQL的并发

对于OLAP的业务场景,需要扫描返回大量数据,这时候全表扫描的顺序IO效率更高。

索引扫描

通常来讲索引比表小,扫描的数据量小,消耗的IO少,执行速度块,几乎没有锁等,能够提高MySQL的并发。

对于OLTP系统,希望所有的SQL都能命中合适的索引总是美好的。

主要区别就是扫描数据量大小以及IO的操作,全表扫描是顺序IO,索引扫描是随机IO,MySQL对此做了优化,增加了change  buffer特性来提高IO性能。

索引优化案例

分页查询优化

业务要根据时间范围查询交易记录,接口原始的SQL如下:

select  * from trade_info where status = 0 and create_time >= '2020-10-01 00:00:00' and create_time <= '2020-10-07 23:59:59' order by id desc limit 102120, 20;

表trade_info上有索引idx_status_create_time(status,create_time),通过上面分析知道,等价于索引**(status,create_time,id)**,对于典型的分页limit  m,  n来说,越往后翻页越慢,也就是m越大会越慢,因为要定位m位置需要扫描的数据越来越多,导致IO开销比较大,这里可以利用辅助索引的覆盖扫描来进行优化,先获取id,这一步就是索引覆盖扫描,不需要回表,然后通过id跟原表trade_info进行关联,改写后的SQL如下:

select * from trade_info a ,  (select  id from trade_info where status = 0 and create_time >= '2020-10-01 00:00:00' and create_time <= '2020-10-07 23:59:59' order by id desc limit 102120, 20) as b   //这一步走的是索引覆盖扫描,不需要回表  where a.id = b.id;

很多同学只知道这样写效率高,但是未必知道为什么要这样改写,理解索引特性对编写高质量的SQL尤为重要。

分而治之总是不错的

营销系统有一批过期的优惠卷要失效,核心SQL如下:

-- 需要更新的数据量500w update coupons set status = 1 where status =0 and create_time >= '2020-10-01 00:00:00' and create_time <= '2020-10-07 23:59:59';

在Oracle里更新500w数据是很快,因为可以利用多个cpu core去执行,但是MySQL就需要注意了,一个SQL只能使用一个cpu  core去处理,如果SQL很复杂或执行很慢,就会阻塞后面的SQL请求,造成活动连接数暴增,MySQL CPU  100%,相应的接口Timeout,同时对于主从复制架构,而且做了业务读写分离,更新500w数据需要5分钟,Master上执行了5分钟,binlog传到了slave也需要执行5分钟,那就是Slave延迟5分钟,在这期间会造成业务脏数据,比如重复下单等。

优化思路:先获取where条件中的最小id和最大id,然后分批次去更新,每个批次1000条,这样既能快速完成更新,又能保证主从复制不会出现延迟。

优化如下

1.先获取要更新的数据范围内的最小id和最大id(表没有物理delete,所以id是连续的)

mysql> explain select min(id) min_id, max(id) max_id from coupons where status =0 and create_time >= '2020-10-01 00:00:00' and create_time <= '2020-10-07 23:59:59';  +----+-------------+-------+------------+-------+------------------------+------------------------+---------+--- | id | select_type | table | partitions | type  | possible_keys          | key                    | key_len | ref  | rows   | filtered | Extra                    | +----+-------------+-------+------------+-------+------------------------+------------------------+---------+--- |  1 | SIMPLE      | users | NULL       | range | idx_status_create_time | idx_status_create_time | 6       | NULL | 180300 |   100.00 | Using where; Using index |

Extra=Using where; Using  index使用了索引idx_status_create_time,同时需要的数据都在索引中能找到,所以不需要回表查询数据。

2.以每次1000条commit一次进行循环update,主要代码如下:

current_id = min_id; for  current_id < max_id do   update coupons set status = 1 where id >=current_id and id <= current_id + 1000;  //通过主键id更新1000条很快 commit; current_id += 1000; done

这两个案例告诉我们,要充分利用辅助索引包含主键id的特性,先通过索引获取主键id走覆盖索引扫描,不需要回表,然后再通过id去关联操作是高效的,同时根据MySQL的特性使用分而治之的思想既能高效完成操作,又能避免主从复制延迟产生的业务数据混乱。

MySQL索引设计

熟悉了索引的特性之后,就可以在业务开发过程中设计高质量的索引,降低接口的响应时间。

前缀索引

对于使用REDUNDANT或者COMPACT格式的InnoDB表,索引键前缀长度限制为767字节。如果TEXT或VARCHAR列的列前缀索引超过191个字符,则可能会达到此限制,假定为utf8mb4字符集,每个字符最多4个字节。

可以通过设置参数innodb_large_prefix来开启或禁用索引前缀长度的限制,即是设置为OFF,索引虽然可以创建成功,也会有一个警告,主要是因为index  size会很大,效率大量的IO的操作,即使MySQL优化器命中了该索引,效率也不会很高。

-- 设置innodb_large_prefix=OFF禁用索引前缀限制,虽然可以创建成功,但是有警告。 mysql> create index idx_nickname on users(nickname);    // `nickname` varchar(255) Records: 0  Duplicates: 0  Warnings: 1 mysql> show warnings; +---------+------+---------------------------------------------------------+ | Level   | Code | Message                                                 | +---------+------+---------------------------------------------------------+ | Warning | 1071 | Specified key was too long; max key length is 767 bytes |

业务发展初期,为了快速实现功能,对一些数据表字段的长度定义都比较宽松,比如用户表users的昵称nickname定义为varchar(128),而且有业务接口需要通过nickname查询,系统运行了一段时间之后,查询users表最大的nickname长度为30,这个时候就可以创建前缀索引来减小索引的长度提升性能。

-- `nickname` varchar(128) DEFAULT NULL定义的执行计划 mysql> explain select * from users where nickname = 'Laaa'; +----+-------------+-------+------------+------+---------------+--------------+---------+-------+------+-------- | id | select_type | table | partitions | type | possible_keys | key          | key_len | ref   | rows | filtered | Extra | +----+-------------+-------+------------+------+---------------+--------------+---------+-------+------+-------- |  1 | SIMPLE      | users | NULL       | ref  | idx_nickname  | idx_nickname | 515     | const |    1 |   100.00 | NULL  |

key_len=515,由于表和列都是utf8mb4字符集,每个字符占4个字节,变长数据类型+2Bytes,允许NULL额外+1Bytes,即128 x  4 + 2 + 1 =  515Bytes。创建前缀索引,前缀长度也可以不是当前表的数据列最大值,应该是区分度最高的那部分长度,一般能达到90%以上即可,例如email字段存储都是类似这样的值xxxx@yyy.com,前缀索引的最大长度可以是xxxx这部分的最大长度即可。

-- 创建前缀索引,前缀长度为30 mysql> create index idx_nickname_part on users(nickname(30)); -- 查看执行计划 mysql> explain select * from users where nickname = 'Laaa'; +----+-------------+-------+------------+------+--------------------------------+-------------------+---------+- | id | select_type | table | partitions | type | possible_keys                  | key               | key_len | ref   | rows | filtered | Extra       | +----+-------------+-------+------------+------+--------------------------------+-------------------+---------+- |  1 | SIMPLE      | users | NULL       | ref  | idx_nickname_part,idx_nickname | idx_nickname_part | 123     | const |    1 |   100.00 | Using where |

可以看到优化器选择了前缀索引,索引长度为123,即30 x 4 + 2 + 1 = 123 Bytes,大小不到原来的四分之。

前缀索引虽然可以减小索引的大小,但是不能消除排序。

mysql> explain select gender,count(*) from users where nickname like 'User100%' group by nickname limit 10; +----+-------------+-------+------------+-------+--------------------------------+--------------+---------+----- | id | select_type | table | partitions | type  | possible_keys                  | key          | key_len | ref  | rows | filtered | Extra                 | +----+-------------+-------+------------+-------+--------------------------------+--------------+---------+----- |  1 | SIMPLE      | users | NULL       | range | idx_nickname_part,idx_nickname | idx_nickname | 515     | NULL |  899 |   100.00 | Using index condition | --可以看到Extra= Using index condition表示使用了索引,但是需要回表查询数据,没有发生排序操作。 mysql> explain select gender,count(*) from users where nickname like  'User100%' group by nickname limit 10; +----+-------------+-------+------------+-------+-------------------+-------------------+---------+------+------ | id | select_type | table | partitions | type  | possible_keys     | key               | key_len | ref  | rows | filtered | Extra                        | +----+-------------+-------+------------+-------+-------------------+-------------------+---------+------+------ |  1 | SIMPLE      | users | NULL       | range | idx_nickname_part | idx_nickname_part | 123     | NULL |  899 |   100.00 | Using where; Using temporary | --可以看到Extra= Using where; Using temporaryn表示在使用了索引的情况下,需要回表去查询所需的数据,同时发生了排序操作。

复合索引

在单列索引不能很好的过滤数据的时候,可以结合where条件中其他字段来创建复合索引,更好的去过滤数据,减少IO的扫描次数,举个例子:业务需要按照时间段来查询交易记录,有如下的SQL:

select  * from trade_info where status = 1 and create_time >= '2020-10-01 00:00:00' and create_time <= '2020-10-07 23:59:59';

开发同学根据以往复合索引的设计的经验:唯一值多选择性好的列作为复合索引的前导列,所以创建复合索idx_create_time_status是高效的,因为create_time是一秒一个值,唯一值很多,选择性很好,而status只有离散的6个值,所以认为这样创建是没问题的,但是这个经验只适合于等值条件过滤,不适合有范围条件过滤的情况,例如idx_user_id_status(user_id,status)这个是没问题的,但是对于包含有create_time范围的复合索引来说,就不适应了,我们来看下这两种不同索引顺序的差异,即idx_status_create_time和idx_create_time_status。

-- 分别创建两种不同的复合索引 mysql> create index idx_status_create_time on trade_info(status, create_time); mysql> create index idx_create_time_status on trade_info(create_time,status); -- 查看SQL的执行计划 mysql> explain select * from users where status = 1 and create_time >='2021-10-01 00:00:00' and create_time <= '2021-10-07 23:59:59'; +----+-------------+-------+------------+-------+-----------------------------------------------+--------------- | id | select_type | table | partitions | type  | possible_keys                                 | key                    | key_len | ref  | rows  | filtered | Extra                 | +----+-------------+-------+------------+-------+-----------------------------------------------+--------------- |  1 | SIMPLE      | trade_info | NULL       | range | idx_status_create_time,idx_create_time_status | idx_status_create_time | 6       | NULL | 98518 |   100.00 | Using index condition |

从执行计划可以看到,两种不同顺序的复合索引都存在的情况,MySQL优化器选择的是idx_status_create_time索引,那为什么不选择idx_create_time_status,我们通过optimizer_trace来跟踪优化器的选择。

-- 开启optimizer_trace跟踪 mysql> set session optimizer_trace="enabled=on",end_markers_in_JSON=on; -- 执行SQL语句 mysql> select * from trade_info where status = 1 and create_time >='2021-10-01 00:00:00' and create_time <= '2021-10-07 23:59:59'; -- 查看跟踪结果 mysql>SELECT trace FROM information_schema.OPTIMIZER_TRACE\G;

 如何设计数据库索引

对比下两个索引的统计数据,如下所示:

如何设计数据库索引

MySQL优化器是基于Cost的,COST主要包括IO_COST和CPU_COST,MySQL的CBO(Cost-Based  Optimizer基于成本的优化器)总是选择Cost最小的作为最终的执行计划去执行,从上面的分析,CBO选择的是复合索引idx_status_create_time,因为该索引中的status和create_time都能参与了数据过滤,成本较低;而idx_create_time_status只有create_time参数数据过滤,status被忽略了,其实CBO将其简化为单列索引idx_create_time,选择性没有复合索引idx_status_create_time好。

复合索引设计原则

  1. 鸿蒙官方战略合作共建——HarmonyOS技术社区

  2. 将范围查询的列放在复合索引的最后面,例如idx_status_create_time。

  3. 列过滤的频繁越高,选择性越好,应该作为复合索引的前导列,适用于等值查找,例如idx_user_id_status。

这两个原则不是矛盾的,而是相辅相成的。

跳跃索引

一般情况下,如果表users有复合索引idx_status_create_time,我们都知道,单独用create_time去查询,MySQL优化器是不走索引,所以还需要再创建一个单列索引idx_create_time。用过Oracle的同学都知道,是可以走索引跳跃扫描(Index  Skip Scan),在MySQL 8.0也实现Oracle类似的索引跳跃扫描,在优化器选项也可以看到skip_scan=on。

| optimizer_switch             |use_invisible_indexes=off,skip_scan=on,hash_join=on |

适合复合索引前导列唯一值少,后导列唯一值多的情况,如果前导列唯一值变多了,则MySQL CBO不会选择索引跳跃扫描,取决于索引列的数据分表情况。

mysql> explain select id, user_id,status, phone from users where create_time >='2021-01-02 23:01:00' and create_time <= '2021-01-03 23:01:00'; +----+-------------+-------+------------+------+---------------+------+---------+------+--------+----------+---- | id | select_type | table | partitions | type | possible_keys | key  | key_len | ref  | rows   | filtered | Extra       | +----+-------------+-------+------------+------+---------------+------+---------+------+--------+----------+---- |  1 | SIMPLE      | users | NULL       | range  | idx_status_create_time          | idx_status_create_time | NULL    | NULL | 15636 |    11.11 | Using where; Using index for skip scan|

也可以通过optimizer_switch='skip_scan=off'来关闭索引跳跃扫描特性。

到此,相信大家对“如何设计数据库索引”有了更深的了解,不妨来实际操作一番吧!这里是编程网网站,更多相关内容可以进入相关频道进行查询,关注我们,继续学习!

您可能感兴趣的文档:

--结束END--

本文标题: 如何设计数据库索引

本文链接: https://www.lsjlt.com/news/61905.html(转载时请注明来源链接)

有问题或投稿请发送至: 邮箱/279061341@qq.com    QQ/279061341

本篇文章演示代码以及资料文档资料下载

下载Word文档到电脑,方便收藏和打印~

下载Word文档
猜你喜欢
  • 如何设计数据库索引
    本篇内容主要讲解“如何设计数据库索引”,感兴趣的朋友不妨来看看。本文介绍的方法操作简单快捷,实用性强。下面就让小编来带大家学习“如何设计数据库索引”吧!MySQL中的索引MySQL中的InnoDB引擎使用B...
    99+
    2022-10-18
  • 索引设计属于数据库设计的哪个阶段
    这篇文章给大家分享的是有关索引设计属于数据库设计的哪个阶段的内容。小编觉得挺实用的,因此分享给大家做个参考。一起跟随小编过来看看吧。索引设计属于数据库设计的物理设计阶段。数据库设计是指对于一个给定的应用环境...
    99+
    2022-10-18
  • 数据库中如何计算索引高度和索引段大小
    这篇文章主要介绍数据库中如何计算索引高度和索引段大小,文中介绍的非常详细,具有一定的参考价值,感兴趣的小伙伴们一定要看完! B*-Tree level (depth of the...
    99+
    2022-10-19
  • MySQL数据库索引的设计原则是什么
    本篇内容主要讲解“MySQL数据库索引的设计原则是什么”,感兴趣的朋友不妨来看看。本文介绍的方法操作简单快捷,实用性强。下面就让小编来带大家学习“MySQL数据库索引的设计原则是什么”吧!为了使索引的使用效...
    99+
    2022-10-18
  • 数据库建表如何设置索引名
    在建表时,可以通过在CREATE TABLE语句中使用CREATE INDEX子句来为表添加索引。索引名的设置可以通过在CREATE INDEX子句中使用INDEX关键字后面跟随索引名的方式进行。以下是一个示例:```CREATE TA...
    99+
    2023-08-09
    数据库
  • PHP学习笔记:数据库优化与索引设计
    在开发Web应用程序时,数据库操作是一个非常关键的环节。数据库的性能直接影响着Web应用程序的响应速度和用户体验。为了提升数据库的效率和查询速度,我们需要进行数据库优化和索引设计。一、数据库优化数据库架构优化:正规化设计:遵循数据库范式,减...
    99+
    2023-10-21
    PHP 数据库优化 索引设计
  • 数据库索引
    索引(index)是帮助MySQL高效获取数据的数据结构。常见的查询算法:顺序查找、二分查找、二叉树查找、哈希散列、分块查找、B树。   1)哈希算法:就是把任意长度值(key)通过散列算法变成固定长度的key地址,通过这个地址进行访问的数...
    99+
    2017-04-03
    数据库索引
  • 数据库--索引
    索引索引是对数据库表中一个或多个列的值进行排序的结构。如果想按特定职员的姓来查找他或她,则与在表中搜索所有的行相比,索引有助于更快地获取信息。没有索引的情况下,如果执行select * from ...
    99+
    2022-10-18
  • 如何在PHP开发中优化数据库表结构和索引设计?
    如何在PHP开发中优化数据库表结构和索引设计?在PHP开发过程中,数据库是一个必不可少的组成部分。而数据库表结构和索引设计的优化能够使得数据库的查询性能大幅度提升,从而提高系统的整体性能。本文将介绍一些常用的优化方法,以帮助PHP开发者优化...
    99+
    2023-11-02
    PHP优化 索引设计 数据库表结构
  • mysql数据库索引如何做?
    MySQL索引底层的实现,今天简单聊一聊,少讲“是怎么样”,更多说说“为什么设计成这样”。 问题1. 数据库为什么要设计索引? 图书馆存了1000W本图书,要从中找到《架构师之路》,一本本查,要查到什么时候...
    99+
    2022-10-18
  • 数据库如何创建索引
    数据库创建索引的方法打开需要操作的数据表。通过create index命令来添加索引。语法:CREATE [ UNIQUE ] [ CLUSTERED| NONCLUSTERED ] INDEX index_name ON { table ...
    99+
    2022-10-13
  • 数据库索引如何使用
    数据库索引是一种优化数据库查询性能的技术。通过使用索引,可以快速定位到数据库中存储的数据,减少查询的时间和资源消耗。使用数据库索引的...
    99+
    2023-08-17
    数据库
  • 数据库设计(一)——数据库设计
    数据库设计(一)——数据库设计 一、数据库设计简介 按照规范设计,将数据库的设计过程分为六个阶段: A、系统需求分析阶段B、概念结构设计阶段C、逻辑结构设计阶段D、物理结构设计阶段E、数据库实施阶段F、数据...
    99+
    2022-10-18
  • mysql如何清除索引数据库
    今天就跟大家聊聊有关 mysql如何清除索引数据库,可能很多人都不太了解,为了让大家更加了解,小编给大家总结了以下内容,希望大家根据这篇文章可以有所收获。mysql如何清除索引数据库1.在DOS窗口运行 ...
    99+
    2022-10-18
  • 万能数据库设计方法探索
    近日负责公司统一用户中心的数据库表结构设计,在工作过程中,诞生了一些另类的想法,特分享出来,期待大家拍砖。思想的演化过程如下。第一阶段:将企业、机构、家庭等实体抽象为“组织”,Organization,简称...
    99+
    2022-10-18
  • MySQL数据库引擎和索引
    一、MySQL 数据库引擎:1. Innodb引擎:Innodb引擎提供了对数据库ACID事务的支持,并且实现了SQL标准的四种隔离级别。在SQL标准中定义了四种隔离级别,每一种级别都规定了一个事务中所做的...
    99+
    2022-10-18
  • oracle 数据库设计-数据库表设计
    在数据库设计中,我的工作中经常会分析怎样商业逻辑中的表格如何设计。再设计表的关系之前 需要先了解关系型数据库特点 1关系型数据库,是指采用了关系模型来组织数据的数据库;2、关系型数据库的最大特点就是事务的一...
    99+
    2022-10-18
  • mysql数据库的索引
    day04  MySQL数据库的索引一、索引概述:    索引是由一张表中的某个列或多列组成,而创建索引的目的是为了更优化管理我们的数据库表,提升我们查询使...
    99+
    2022-10-18
  • 数据库中的索引
    目录 一、什么是索引? 索引的实现原理 什么时候考虑添加索引? 索引的类型 二、为什么要有索引? 三、怎么用索引? 索引的创建和删除 怎么查看一条sql语句中使用了索引? 索引失效的情况以及对应解决方案 一、什么是索引? 索引是数据...
    99+
    2023-09-02
    mysql
  • MongoDB数据库中如何使用索引
    本篇文章为大家展示了MongoDB数据库中如何使用索引,内容简明扼要并且容易理解,绝对能使你眼前一亮,通过这篇文章的详细介绍希望你能有所收获。  MongoDB的各种索引有哪些用法  1.单列索引  在字段...
    99+
    2022-10-18
软考高级职称资格查询
编程网,编程工程师的家园,是目前国内优秀的开源技术社区之一,形成了由开源软件库、代码分享、资讯、协作翻译、讨论区和博客等几大频道内容,为IT开发者提供了一个发现、使用、并交流开源技术的平台。
  • 官方手机版

  • 微信公众号

  • 商务合作