百万数据查问优化技巧-SQL-Server-则-30 (百万数据查问题怎么查)
互联网时代的进程越走越深,经常使用的人也越来越多,关于MySQL的数据库优化指南很多,而关于SQLSERVER的T-SQL优化指南看下来比拟少,近期有学习SQLSERVER的同窗识到SQLSERVER数据库有哪些优化倡导?本文罗列了局部经常出现的优化倡导,详细内容如下:
1、优化倡导
索引优化:
NULL值判别防止全表扫描:
eg:关于蕴含status列的用户表Users,防止经常使用SELECT*FROMUsersWHEREstatusISNULL,可以在设计表时设置status自动值,确保一切用户都有一个形态,而后经常使用SELECT*FROMUsersWHEREstatus=0启动查问。
!=或<>操作符防止全表扫描:
eg:思考一个产品表Products,假设要查问一切不属于某个特定类别的产品,防止经常使用SELECT*FROMProductsWHERECategoryID!=5,而是经常使用SELECT*FROMProductsWHERECategoryID<>5。
OR衔接条件防止全表扫描:
eg:关于一个在校生效果表Grades,假设须要查问得分为A或B的记载,防止经常使用SELECT*FROMGradesWHEREGrade='A'ORGrade='B',而是经常使用SELECT*FROMGradesWHEREGrade='A'UNIONALLSELECT*FROMGradesWHEREGrade='B'。
IN和NOTIN防止全表扫描:
eg:思考一个员工表Employees,假设须要查问属于某个特定部门的员工,防止经常使用SELECT*FROMEmployeesWHEREDepartmentIDIN(1,2,3),而是经常使用SELECT*FROMEmployeesWHEREDepartmentIDBETWEEN1AND3。
LIKE查问优化:
eg:在一个文章表Articles中,假设须要含糊查问题目蕴含主要词的文章,防止经常使用SELECT*FROMArticlesWHERETitleLIKE'%SQL%',可以思考全文检索或许其余优化方式。
参数经常使用防止全表扫描:
eg:在一个订单表Orders中,假设须要依据输入的订单号查问订单信息,防止经常使用SELECT*FROMOrdersWHEREOrderID=@OrderID,可以经常使用强迫索引的方式,如SELECT*FROMOrdersWITH(INDEX(OrderID_Index))WHEREOrderID=@OrderID。
字段表白式操作防止全表扫描:
eg:在一个商品表Products中,假设须要查问多少钱除以2等于100的商品,防止经常使用SELECT*FROMProductsWHEREPrice/2=100,可以改为SELECT*FROMProductsWHEREPrice=100*2。
字段函数操作防止全表扫描:
eg:在一个员工表Employees中,假设须要查问名字以"Smith"扫尾的员工,防止经常使用SELECT*FROMEmployeesWHERELEFT(LastName,5)='Smith',可以改为SELECT*FROMEmployeesWHERELastNameLIKE'Smith%'。
不要在=左边启动函数、算术运算:
eg:在一个库存表Inventory中,防止经常使用SELECT*FROMInventoryWHEREYEAR(StockDate)=2023,而是经常使用SELECT*FROMInventoryWHEREStockDate>='2023-01-01'ANDStockDate<'2024-01-01'。
索引字段顺序经常使用防止全表扫描:
eg:在一个订单表Orders中,假设有复合索引(CustomerID,OrderDate),查问时应该先经常使用CustomerID,如SELECT*FROMOrdersWHERECustomerID=@CustomerIDANDOrderDateBETWEEN@StartDateAND@EndDate。
防止写没无心义的查问:
eg:不倡导经常使用SELECTcol1,col2INTO#tFROMtWHERE1=0,可以改为明白创立表结构并经常使用CREATETABLE#t(...)。
经常使用EXISTS替代IN:
eg:在一个产品表Products中,防止经常使用SELECT*FROMProductsWHEREProductIDIN(SELECTProductIDFROMDiscontinuedProducts),可以改为SELECT*FROMProductsWHEREEXISTS(SELECT1FROMDiscontinuedProductsWHEREProductID=Products.ProductID)。
索引不必定对一切查问有效:
eg:在一共性别字段Gender简直平均散布的表中,对Gender建设索引或许不会提高查问效率。
索引数量审慎选用:
eg:在一个订单表Orders中,不宜过多地在每个列上建设索引,须要依据查问和降级的详细需求启动掂量。
降级clustered索引数据列审慎操作:
eg:在一个用户表Users中,假设频繁降级用户姓名,思考能否将姓名列设为非汇集索引,以防止整个表记载顺序调整。
经常使用数字型字段:
eg:在一个在校生效果表Grades中,假设考试效果以整数方式示意,经常使用整数型字段而非字符型字段。
经常使用VARCHAR/NVARCHAR:
eg:在一个文章表Articles中,假设存储文章内容,经常使用VARCHAR(MAX)而非TEXT。
防止经常使用SELECT*:
eg:在一个员工表Employees中,防止经常使用SELECT*FROMEmployees,而是明白指定须要的列,如SELECTEmployeeID,FirstName,LastNameFROMEmployees。
经常使用表变量替代暂时表:
eg:在一个小型数据集的状况下,可以经常使用表变量而不是创立暂时表来存储两边结果。例如,经常使用表变量替代以下的暂时表:
--不介绍CREATETABLE#TempResults(IDINT,NameVARCHAR(255),...--介绍DECLARE@TempResultsTABLE(IDINT,NameVARCHAR(255),...);
防止频繁创立和删除暂时表:
eg:在一个存储环节中,假设须要屡次经常使用相反的暂时表,不要在每次经常使用时都创立和删除,而是在存储环节的扫尾创立一次性,最后删除。
正当经常使用暂时表:
eg:在一个复杂的查问中,假设须要屡次援用两边结果,可以思考经常使用暂时表。但应留意不要滥用,确保暂时表的经常使用是必要的。
选用适合的暂时表创立方式:
eg:在须要一次性性拔出少量数据的状况下,可以经常使用SELECTINTO替代CREATETABLE和INSERT的两步操作,以缩小日志记载。
--不介绍CREATETABLE#TempTable(IDINT,NameVARCHAR(255),...);INSERTINTO#TempTableSELECTID,Name,...FROMSomeTable;--介绍SELECTID,Name,...INTO#TempTableFROMSomeTable;
显式删除暂时表:
eg:在存储环节或脚本的最后,确保显式删除一切创立的暂时表,以监禁系统表资源。
--不介绍DROPTABLE#TempTable;--介绍TRUNCATETABLE#TempTable;DROPTABLE#TempTable;
防止经常使用游标:
eg:在一个订单表Orders中,防止经常使用游标来逐行处置数据,可以思考经常使用汇合操作或许其余优化方法。
基于集的方法替代游标或暂时表:
eg:在须要对少量数据启动操作时,尽量寻觅基于集的处置方案,以防止经常使用游标或暂时表。例如,经常使用窗口函数或联接来处置数据。
存储环节中经常使用SETNOCOUNTON/OFF:
eg:在存储环节中经常使用SETNOCOUNTON和SETNOCOUNTOFF,以缩小向客户端发送DONE_IN_PROC信息,提高性能。
--存储环节扫尾SETNOCOUNTON;--存储环节开头SETNOCOUNTOFF;
防止小事务操作:
eg:在一个银行买卖表Transactions中,防止在一个事务中处置过多的买卖记载,以提高系统并发才干。
防止向客户端前往大数据量:
eg:在一个日志表Logs中,假设查问或许前往少量的日志记载,应该审查客户端能否真的须要这么少数据,思考分页或其余方式缩小前往的数据量。
经常使用EXPLN或ShowExecutionPlan剖析查问口头方案,发现潜在疑问。
2、结语
相熟其余数据库的同窗应该也能对比出,很少数据库的优化阅历是相通的,所以在学习其余数据库的时刻可以自创已把握的阅历去对比学习,这样学习起来也会事倍功半。
如何提高SQL Server大数据条件下的查询速度?
1.关于索引优化建索引的选择必须结合SQL查询、修改、删除语句的需要,一般的说法是在WHERE里经常出现的字段建索引。 如果在WHERE经常是几个字段一起出现而且是用AND连接的,那就应该建这几个字段一起的联合索引,而且次序也需要考虑,一般是最常出现的放前面,重复率低的放前面。 SQLServer提供了一种简化并自动维护数据库的工具。 这个称之为数据库维护计划向导(DatabaseMaintenancePlanWizard,DMPW)的工具也包括了对索引的优化。 如果你运行这个向导,你会看到关于数据库中关于索引的统计量,这些统计量作为日志工作并定时更新,这样就减轻了手工重建索引或者DBCCINDEXDEFRAG所带来的工作量。 如果你不想自动定期刷新索引统计量,你还可以在DMPW中选择重新组织数据和数据页,这将停止旧有索引并按特定的填充因子重建索引。 2.改善硬件(双CPU,Raid5,增加内存)tempdb这个临时数据库,它对性能的影响较大。 tempdb和其他数据库一样可以增大,可以缩小。 当数据文件需要增长的时候,通常不能保持剩余部分的连续性。 这时文件就会产生碎片,这种碎片会造成性能下降。 这种碎片属于外来性碎片。 要阻止在tempdb中产生外来性碎片,必须保证有足够的硬盘空间。 一般将tempdb的容量放到平均使用容量。 而你也应该允许tempdb自动增长,比如你有个一个超大的join操作,它建立了一个超过tempdb容量的时候,该查询将失败。 你还要设置一个合理的单位增长量。 因为如果你设得太小,将会产生许多外来性碎片,反而会占用更多资源。 sqlserver调优最有效的做法之一,就是把争夺资源的操作独立出去。 tempdb就是一个需要独立出去的部分而tempdb和其他系统库一样是公用的,是存取最可能频繁的库,所有处理临时表、子查询、GROUPBY、排序、DISTINCT、连接等等。 它最适合放到一个具有快速读写能力的设备上。 比如RAID0卷或RAID0+1卷上。 查询语句一定要使用存储过程;3、查询尽量使用TOP子句4.将表按一定的约束分成子表,(如按分类)创建约束,在用Like时,先用分类andlike,应该可能解决问题.而且效果立秆见影!(你要确定SQL会认识你建的分区视图).我一个表有上百万的记录(700兆),用分区视图后,查询速度基本跟10万行一样.如果还是太慢,还可以考滤分布式分区视图!这总可以解决问题了吧!关键在于你能否把大表按某种约束分解成子表.
50种方法巧妙优化你的SQLServer数据库(二)
26、MIN() 和 MAX()能使用到合适的索引。 27、数据库有一个原则是代码离数据越近越好,所以优先选择Default,依次为Rules,Triggers, Constraint(约束如外健主健CheckUNIQUE……,数据类型的长度等等都是约束),Procedure.这样不仅维护工作小,编写程序质量高,并且执行的速度快。 28、如果要插入大的二进制值到Image列,使用存储过程,千万不要用内嵌INsert来插入(不知JAVA是否)。 因为这样应用程序首先将二进制值转换成字符串(尺寸是它的两倍),服务器受到字符后又将他转换成二进制值.存储过程就没有这些动作: 方法: Create procedure p_insert as insert into table(Fimage) values (@image) 在前台调用这个存储过程传入二进制参数,这样处理速度明显改善。 29、Between在某些时候比IN速度更快,Between能够更快地根据索引找到范围。 用查询优化器可见到差别。 select * from chineseresume where title in (男,女) Select * from chineseresume where between 男 and 女 是一样的。 由于in会在比较多次,所以有时会慢些。 30、在必要是对全局或者局部临时表创建索引,有时能够提高速度,但不是一定会这样,因为索引也耗费大量的资源。 他的创建同是实际表一样。 31、不要建没有作用的事物例如产生报表时,浪费资源。 只有在必要使用事物时使用它。 32、用OR的字句可以分解成多个查询,并且通过UNION 连接多个查询。 他们的速度只同是否使用索引有关,如果查询需要用到联合索引,用UNION all执行的效率更高.多个OR的字句没有用到索引,改写成UNION的形式再试图与索引匹配。 一个关键的问题是否用到索引。 33、尽量少用视图,它的效率低。 对视图操作比直接对表操作慢,可以用stored procedure来代替她。 特别的是不要用视图嵌套,嵌套视图增加了寻找原始资料的难度。 我们看视图的本质:它是存放在服务器上的被优化好了的已经产生了查询规划的SQL。 对单个表检索数据时,不要使用指向多个表的视图,直接从表检索或者仅仅包含这个表的视图上读,否则增加了不必要的开销,查询受到干扰.为了加快视图的查询,MsSQL增加了视图索引的功能。 34、没有必要时不要用DISTINCT和ORDER BY,这些动作可以改在客户端执行。 它们增加了额外的开销。 这同UNION 和UNION ALL一样的道理。 select top 20 ,comid,position,,worklocation, convert(varchar(10),,120) as postDate1,workyear,degreedescription FROM jobcn__query ad where referenceID in(JCNAD,JCNAD,JCNAD,JCNAD,JCNAD,JCNAD,JCNAD,JCNAD,JCNAD,JCNAD,JCNAD,JCNAD,JCNAD,JCNAD,JCNAD,JCNAD,JCNAD,JCNAD,JCNAD,JCNAD) order by postdate desc 35、在IN后面值的列表中,将出现最频繁的值放在最前面,出现得最少的放在最后面,减少判断的次数。 36、当用SELECT INTO时,它会锁住系统表(sysobjects,sysindexes等等),阻塞其他的连接的存取。 创建临时表时用显示申明语句,而不是 select INTO. drop table t_lxh begin tran select * into t_lxh from chineseresume where name = XYZ --commit 在另一个连接中SELECT * from sysobjects可以看到 SELECT INTO 会锁住系统表,Create table 也会锁系统表(不管是临时表还是系统表)。 所以千万不要在事物内使用它!!!这样的话如果是经常要用的临时表请使用实表,或者临时表变量。 37、一般在GROUP BY 个HAVING字句之前就能剔除多余的行,所以尽量不要用它们来做剔除行的工作。 他们的执行顺序应该如下:select 的Where字句选择所有合适的行,Group By用来分组个统计行,Having字句用来剔除多余的分组。 这样Group By 个Having的开销小,查询快.对于大的数据行进行分组和Having十分消耗资源。 如果Group BY的目的不包括计算,只是分组,那么用Distinct更快 38、一次更新多条记录比分多次更新每次一条快,就是说批处理好 39、少用临时表,尽量用结果集和Table类性的变量来代替它,Table 类型的变量比临时表好 40、在SQL2000下,计算字段是可以索引的,需要满足的条件如下: a、计算字段的表达是确定的 b、不能用在TEXT,Ntext,Image数据类型 c、必须配制如下选项 ANSI_NULLS = ON, ANSI_PADDINGS = ON, …….
免责声明:本文转载或采集自网络,版权归原作者所有。本网站刊发此文旨在传递更多信息,并不代表本网赞同其观点和对其真实性负责。如涉及版权、内容等问题,请联系本网,我们将在第一时间删除。同时,本网站不对所刊发内容的准确性、真实性、完整性、及时性、原创性等进行保证,请读者仅作参考,并请自行核实相关内容。对于因使用或依赖本文内容所产生的任何直接或间接损失,本网站不承担任何责任。