提高数据库的性能?

提高数据库的性能?,第1张

提升数据性能可以提升查询速度,优化数据库结构,减少服务器压力等,那么如何优化数据库呢?昆明电脑培训http://www.kmbdqn.cn/来看看下面的文章!

1.数据库I/O方面硬件性能

最有可能影响性能的是磁盘和网络吞吐量。解决办法:

·扩大虚拟内存,并保证有足够可以扩充的空间

·把数据库服务器上的不必要服务关闭掉

·把SQL数据库服务器的吞吐量调为最大

2.调整数据库

·若对该表的查询频率比较高,则建立索引。

·分区(如MySQL,按时间分区)

·尽量使用固定长度字段和限制字段长度(如varchar(10))优势:

降低物理存储空间

提高数据库处理速度

附带校验数据库是否合法功能

3.使用存储过程

应用程序的实现过程中,能够采用存储过程实现的对数据库的操作尽量通过存储过程来实现。

因为存储过程是存放在数据库服务器上的一次性被设计、编码、测试,并被再次使用,需要执行该任务的应用可以简单地执行存储过程,并且只返回结果集或者数值。

这样不仅可以使程序模块化,同时提高响应速度,减少网络流量,并且通过输入参数接受输入,使得在应用中完成逻辑的一致性实现。

4.SQL语句方面

建立查询条件索引仅仅是提高速度的前提条件,响应速度的提高还依赖于对索引的使用。不良的SQL往往来自于不恰当的索引设计、不充份的连接条件和不可优化的where子句。

·优化sql语句,减少比较次数

·限制返回条目数(mysql中使用limit)

网络宽带,磁盘IO,查询速度都会影响到数据库的性能。

    具体问题具体分析,举例来说明为什么磁盘IO成瓶颈数据库的性能急速下降了。

   为什么当磁盘IO成瓶颈之后, 数据库的性能不是达到饱和的平衡状态,而是急剧下降。为什么数据库的性能有非常明显的分界点,原因是什么?

    相信大部分做数据库运维的朋友,都遇到这种情况。 数据库在前一天性能表现的相当稳定,数据库的响应时间也很正常,但就在今天,在业务人员反馈业务流量没有任何上升的情况下,数据库的变得不稳定了,有时候一个最简单的insert操作, 需要几十秒,但99%的insert却又可以在几毫秒完成,这又是为什么了?

dba此时心中有无限的疑惑,到底是什么原因呢? 磁盘IO性能变差了?还是业务运维人员反馈的流量压根就不对? 还是数据库内部出问题?昨天不是还好好的吗?

 当数据库出现响应时间不稳定的时候,我们在操作系统上会看到磁盘的利用率会比较高,如果观察仔细一点,还可以看到,存在一些读的IO. 数据库服务器如果存在大量的写IO,性能一般都是正常跟稳定的,但只要存在少量的读IO,则性能开始出现抖动,存在大量的读IO时(排除配备非常高速磁盘的机器),对于在线交易的数据库系统来说,大概性能就雪崩了。为什么操作系统上看到的磁盘读IO跟写IO所带来的性能差距这么大呢?

如果亲之前没有注意到上述的现象,亲对上述的结论也是怀疑。但请看下面的分解。

在写这个文章之前,作者阅读了大量跟的IO相关的代码,如异步IO线程的相关的,innodb_buffer池相关的,以及跟读数据块最相关的核心函数buf_page_get_gen函数以及其调用的相关子函数。为了将文章写得通俗点,看起来不那么累,因此不再一行一行的将代码解析写出来。

咱们先来提问题。 buf_page_get_gen函数的作用是从Buffer bool里面读数据页,可能存在以下几种情况。

提问. 数据页不在buffer bool 里面该怎么办?

  回答:去读文件,将文件中的数据页加载到buffer pool里面。下面是函数buffer_read_page的函数,作用是将物理数据页加载到buffer pool, 图片中显示

buffer_read_page函数栈的顶层是pread64(),调用了操作系统的读函数。

buf_read_page的代码

 如果去读文件,则需要等待物理读IO的完成,如果此时IO没有及时响应,则存在堵塞。这是一个同步读的操作,如果不完成该线程无法继续后续的步骤。因为需要的数据页不再buffer 中,无法直接使用该数据页,必须等待操作系统完成IO .

再接着上面的回答提问:

当第二会话线程执行sql的时候,也需要去访问相同的数据页,它是等待上面的线程将这个数据页读入到缓存中,还是自己再发起一个读磁盘的然后加载到buffer的请求呢?   代码告诉我们,是前者,等待第一个请求该数据页的线程读入buffer pool。

试想一下,如果第一个请求该数据页的线程因为磁盘IO瓶颈,迟迟没有将物理数据页读入buffer pool, 这个时间区间拖得越长,则造成等待该数据块的用户线程就越多。对高并发的系统来说,将造成大量的等待。 等待数据页读入的函数是buf_wait_for_read,下面是该函数相关的栈。

通过解析buf_wait_for_read函数的下层函数,我们知道其实通过首先自旋加锁pin的方式,超过设定的自旋次数之后,进入等待,等待IO完成被唤醒。这样节省不停自旋pin时消耗的cpu,但需要付出被唤起时的开销。

再继续扩展问题: 如果会话线程A 经过物理IO将数据页1001读入buffer之后,他需要修改这个页,而在会话线程A之后的其他的同样需要访问数据页1001的会话线程,即使在数据页1001被入读buffer pool之后,将仍然处于等待中。因为在数据页上读取或者更新的时候,同样需要上锁,这样才能保证数据页并发读取/更新的一致性。

由此可见,当一个高并发的系统,出现了热点数据页需要从磁盘上加载到buffer pool中时,造成的延迟,是难以想象的。因此排在等待热点页队列最后的会话线程最后才得到需要的页,响应时间也就越长,这就是造成了一个简单的sql需要执行几十秒的原因。

再回头来看上面的问题,mysql数据库出现性能下降时,可以看到操作系统有读IO。 原因是,在数据库对数据页的更改,是在内存中的,然后通过检查点线程进行异步写盘,这个异步的写操作是不堵塞执行sql的会话线程的。所以,即使看到操作系统上有大量的写IO,数据库的性能也是很平稳的。但当用户线程需要查找的数据页不在buffer pool中时,则会从磁盘上读取,在一个热点数据页不是非常多的情况下,我们设置足够大的innodb_buffer_pool的size, 基本可以缓存所有的数据页,因此一般都不会出现缺页的情况,也就是在操作系统上基本看不到读的IO。  当出现读的IO时,原因时在执行buf_read_page_low函数,从磁盘上读取数据页到buffer pool, 则数据库的性能则开始下降,当出现大量的读IO,数据库的性能会非常差。

你最好买一本专门讲ORACLE性能优化的书,好好看看\x0d\x0a1、调整数据库服务器的性能\x0d\x0aOracle数据库服务器是整个系统的核心,它的性能高低直接影响整个系统的性能,为了调整Oracle数据库服务器的性能,主要从以下几个方面考虑: \x0d\x0a1.1、调整操作系统以适合Oracle数据库服务器运行\x0d\x0aOracle数据库服务器很大程度上依赖于运行服务器的操作系统,如果操作系统不能提供最好性能,那么无论如何调整,Oracle数据库服务器也无法发挥其应有的性能。 \x0d\x0a1.1.1、为Oracle数据库服务器规划系统资源 \x0d\x0a据已有计算机可用资源, 规划分配给Oracle服务器资源原则是:尽可能使Oracle服务器使用资源最大化,特别在Client/Server中尽量让服务器上所有资源都来运行Oracle服务。 \x0d\x0a1.1.2、调整计算机系统中的内存配置 \x0d\x0a多数操作系统都用虚存来模拟计算机上更大的内存,它实际上是硬盘上的一定的磁盘空间。当实际的内存空间不能满足应用软件的要求时,操作系统就将用这部分的磁盘空间对内存中的信息进行页面替换,这将引起大量的磁盘I/O操作,使整个服务器的性能下降。为了避免过多地使用虚存,应加大计算机的内存。 \x0d\x0a1.1.3、为Oracle数据库服务器设置操作系统进程优先级 \x0d\x0a不要在操作系统中调整Oracle进程的优先级,因为在Oracle数据库系统中,所有的后台和前台数据库服务器进程执行的是同等重要的工作,需要同等的优先级。所以在安装时,让所有的数据库服务器进程都使用缺省的优先级运行。 \x0d\x0a1.2、调整内存分配\x0d\x0aOracle数据库服务器保留3个基本的内存高速缓存,分别对应3种不同类型的数据:库高速缓存,字典高速缓存和缓冲区高速缓存。库高速缓存和字典高速缓存一起构成共享池,共享池再加上缓冲区高速缓存便构成了系统全程区(SGA)。SGA是对数据库数据进行快速访问的一个系统全程区,若SGA本身需要频繁地进行释放、分配,则不能达到快速访问数据的目的,因此应把SGA放在主存中,不要放在虚拟内存中。内存的调整主要是指调整组成SGA的内存结构的大小来提高系统性能,由于Oracle数据库服务器的内存结构需求与应用密切相关,所以内存结构的调整应在磁盘I/O调整之前进行。 \x0d\x0a1.2.1、库缓冲区的调整 \x0d\x0a库缓冲区中包含私用和共享SQL和PL/SQL区,通过比较库缓冲区的命中率决定它的大小。要调整库缓冲区,必须首先了解该库缓冲区的活动情况,库缓冲区的活动统计信息保留在动态性能表v$librarycache数据字典中,可通过查询该表来了解其活动情况,以决定如何调整。 \x0d\x0a \x0d\x0aSelect sum(pins),sum(reloads) from v$librarycache \x0d\x0a \x0d\x0aPins列给出SQL语句,PL/SQL块及被访问对象定义的总次数;Reloads列给出SQL 和PL/SQL块的隐式分析或对象定义重装载时在库程序缓冲区中发生的错误。如果sum(pins)/sum(reloads) ≈0,则库缓冲区的命中率合适;若sum(pins)/sum(reloads)>1, 则需调整初始化参数 shared_pool_size来重新调整分配给共享池的内存量。 \x0d\x0a1.2.2、数据字典缓冲区的调整 \x0d\x0a数据字典缓冲区包含了有关数据库的结构、用户、实体信息。数据字典的命中率,对系统性能影响极大。数据字典缓冲区的使用情况记录在动态性能表v$librarycache中,可通过查询该表来了解其活动情况,以决定如何调整。 \x0d\x0a \x0d\x0aSelect sum(gets),sum(getmisses) from v$rowcache \x0d\x0a \x0d\x0aGets列是对相应项请求次数的统计;Getmisses 列是引起缓冲区出错的数据的请求次数。对于频繁访问的数据字典缓冲区,sum(getmisses)/sum(gets) 回答于 2022-11-15


欢迎分享,转载请注明来源:夏雨云

原文地址:https://www.xiayuyun.com/zonghe/227066.html

(0)
打赏 微信扫一扫微信扫一扫 支付宝扫一扫支付宝扫一扫
上一篇 2023-04-08
下一篇2023-04-08

发表评论

登录后才能评论

评论列表(0条)

    保存