Sat*_*ave 5 mysql index-statistics mysql-5.7
我正在使用 MySQL 5.7
如何为数据库中的所有表运行 ANALYZE TABLE。如果将来将新表添加到数据库中,它应该可以工作。
这是为了刷新表索引的统计信息。
小智 8
你可以运行
mysqlcheck -a --all-databases
Run Code Online (Sandbox Code Playgroud)
如果您正在使用 InnoDB 表(您应该如此):
SET @old_innodb_stats_on_metadata = @@global.innodb_stats_on_metadata;
SET GLOBAL innodb_stats_on_metadata='ON';
SHOW TABLE STATUS FROM db;
SET GLOBAL innodb_stats_on_metadata = @old_innodb_stats_on_metadata;
Run Code Online (Sandbox Code Playgroud)
对于 InnoDB,如果我上面显示的选项为 ON,则 ANALYZE TABLE 执行的操作也仅通过查看表状态来执行。也就是说,查看表状态或查询 INFORMATION_SCHEMA.TABLES 将触发与 ANALYZE TABLE 相同的表统计信息刷新。
该语句SHOW TABLE STATUS FROM db默认显示命名模式中的所有表,因此无需编写循环或其他答案所示的任何内容。
小智 1
我想要一种方法来获取数据库中每个表中的确切行数,并发现ANALYZE TABLE table_name需要确保该值正确。我无法将变量传递table_name给ANALYZE TABLE,所以这是我能做的最好的事情。
总之:
script_to_analyse_all_tables()循环遍历每个表名称的存储过程,为每个表生成查询ANALYZE TABLE table_name。然后,手动:
只需db_name在运行之前更新数据库的名称即可。
DROP PROCEDURE IF EXISTS `script_to_analyse_all_tables`;
DELIMITER $$
CREATE PROCEDURE script_to_analyse_all_tables()
BEGIN
-- declare variables
DECLARE finished INTEGER DEFAULT 0;
DECLARE this_table_name VARCHAR(256);
DECLARE full_statement VARCHAR(10000);
-- declare cursor for table names
DECLARE cursor_table_name CURSOR FOR
SELECT table_name FROM INFORMATION_SCHEMA.TABLES WHERE TABLE_SCHEMA = '[db_name]';
-- declare NOT FOUND handler
DECLARE CONTINUE HANDLER FOR NOT FOUND SET finished = 1;
-- open the cursor
OPEN cursor_table_name;
myLoop: LOOP
FETCH cursor_table_name INTO this_table_name;
IF finished = 1 THEN
LEAVE myLoop;
END IF;
SET full_statement = concat( IFNULL(full_statement,''), "ANALYZE TABLE ", this_table_name, ";");
END LOOP myLoop;
-- close the cursor
CLOSE cursor_table_name;
-- view results:
SELECT full_statement as "run the following statement:";
END $$
DELIMITER ;
CALL script_to_analyse_all_tables;
DROP PROCEDURE IF EXISTS `script_to_analyse_all_tables`;
Run Code Online (Sandbox Code Playgroud)
然后使用以下命令检查结果:
SELECT table_name, TABLE_ROWS FROM INFORMATION_SCHEMA.TABLES WHERE TABLE_SCHEMA = '[db_name]';