SELECT语句中“加锁选项”功能说明

 更新时间:2016年11月25日 16:44  点击:1626
SELECT 语句中“加锁选项”的功能说明
SQL Server提供了强大而完备的锁机制来帮助实现数据库系统的并发性和高性能。用户既能使用SQL Server的缺省设置也可以在select 语句中使用“加锁选项”来实现预期的效果。
 本文介绍了SELECT语句中的各项“加锁选项”以及相应的功能说明。
功能说明: 
NOLOCK(不加锁)
此选项被选中时,SQL Server 在读取或修改数据时不加任何锁。
 在这种情况下,用户有可能读取到未完成事务(Uncommited Transaction)或回滚(Roll Back)中的数据, 即所谓的“脏数据”。
HOLDLOCK(保持锁)
此选项被选中时,SQL Server 会将此共享锁保持至整个事务结束,而不会在途中释放。
UPDLOCK(修改锁)
此选项被选中时,SQL Server 在读取数据时使用修改锁来代替共享锁,并将此锁保持至整个事务或命令结束。使用此选项能够保证多个进程能同时读取数据但只有该进程能修改数据。
TABLOCK(表锁)
此选项被选中时,SQL Server 将在整个表上置共享锁直至该命令结束。
 这个选项保证其他进程只能读取而不能修改数据。
PAGLOCK(页锁)
此选项为默认选项, 当被选中时,SQL Server 使用共享页锁。
TABLOCKX(排它表锁)
此选项被选中时,SQL Server 将在整个表上置排它锁直至该命令或事务结束。这将防止其他进程读取或修改表中的数据。
使用这些选项将使系统忽略原先在SET语句设定的事务隔离级别(Transaction Isolation Level)。
 请查阅SQL Server 联机手册获取更多信息。

下面是我多年经验的总结: 网络编程总要和数据库打交道。和数据库打交道总要接触到SQL。如何使你的SQL 跑得快一点,本文介绍几种行之有效的方法: 方法一、尽量使用复杂的SQL来代替简单的一堆SQL. 同样的事务,一个复杂的SQL完成的效率高于一堆简单SQL完成的效率。有多个查询时,要善于使用JOIN。
 oRs=objDBC.Execute('SELECT * FROM Books') for(; !oRs.Eof; oRs.MoveNext()) { oRs2=objDBC.Execute('SELECT * FROM Authors WHERE AuthorID='' oRs ('AuthorID').value '''); Response.write(oRs('Title').value ' ' oRs2('Name') '<br>'); } 要比下面的代码慢: oRs=objDBC.Execute('SELECT Books.Title,Authors.Name FROM Books JOIN Authors ON Authors.AuthorID=Books.AuthorID'); for(; !oRs.Eof; oRs.MoveNext()) { Response.write(oRs('Title').value ' ' oRs('Name') '<br>'); } 方法二、尽量避免使用可更新Recordset oRs=objDBC.Execute('SELECT * FROM Authors WHERE AuthorID=17',(some flags)); oRs('Name')='Karl Karlsson'; oRs.Update(); 要比下面的代码慢: objDBC.Execute('UPDATE Authors SET Name='Karl Karlsson' WHERE AuthorID=17'); 方法三、更新数据库时,尽量采用批处理更新将所有的SQL组成一个大的批处理SQL,并一次运行;这比一个一个地更新数据要有效率得多。这样也更加满足你进行事务处理的需要: (in JScript) strSQL=''; strSQL ='SET XACT_ABORT ON '; strSQL ='BEGIN TRANSACTION '; strSQL ='INSERT INTO Orders(OrdID,CustID,OrdDat) VALUES('9999', '1234',GETDATE()) '; strSQL ='INSERT INTO OrderRows(OrdID,OrdRow,Item,Qty) VALUES('9999 ','01','G4385',5) '; strSQL ='INSERT INTO OrderRows(OrdID,OrdRow,Item,Qty) VALUES('9999 ','02','G4726',1) '; strSQL ='COMMIT TRANSACTION '; strSQL ='SET XACT_ABORT OFF '; objDBC.Execute(strSQL); 其中,SET XACT_ABORT OFF 语句告诉SQL Server,如果下面的事务处理过程中,如果遇到错误,就取消已经完成的事务。
 方法四、数据库索引 方法五、避免使Text字段太大当字符串的值大小不固定时,用varchar比用char的效果要好些。我曾经看到一个例子程序,字段被定义为TEXT(255),但是他的取值经常只有20个字符。这个数据表有50k个记录,从而使这个数据库很大,大的数据库必然较慢。
 

如果您在Access数据库、Access项目中删除数据或对象,可能会产生碎片并导致磁盘空间使用效率的降低。同时,数据库文件的大小并未减小,而是不断的增大,直至您的硬盘没有空间。有没有好的处理方法呢?其实,在Access中可以对数据库进行压缩优化以提升Access数据库和Access项目的性能,这样的压缩处理的实质是复制该文件,并重新组织文件在磁盘上的存储方式。但是,在Access项目中进行这样的压缩不会影响到数据库对象(例如表或视图),因为它们是存储在Microsoft SQL Server数据库中而不是在Access项目本身中。同样,这样的压缩也不会影响到Access项目中的自动编号。在Access数据库中,如果已经从表的末尾删除了记录,压缩该数据库是就会重新设置自动编号值。添加的下一个记录的自动编号值将会比表中没有删除的最后记录的自动编号值大一。
下面介绍如何在VB中用一个CompactJetDatabase过程实现对Access数据库文件的压缩处理,在这个过程中有一个可选参数,就是在压缩前你是否需要把原有的数据库文件备份到临时目录(True或False)。我用此办法使21.6MB的数据库压缩到仅仅300KB。
'这些代码可放在模块中,在其他窗体也使用
Public Declare Function GetTempPath Lib "kernel32" Alias _
"GetTempPathA" (ByVal nBufferLength As Long, ByVal lpBuffer As String) As Long
Public Const MAX_PATH = 260
Public Sub CompactJetDatabase(Location As String, Optional BackupOriginal As Boolean = True)
On Error GoTo CompactErr
Dim strBackupFile As String
Dim strTempFile As String
'检查数据库文件是否存在
If Len(Dir(Location)) Then
'如果需要备份就执行备份
If BackupOriginal = True Then
strBackupFile = GetTemporaryPath & "backup.mdb"
If Len(Dir(strBackupFile)) Then Kill strBackupFile
FileCopy Location, strBackupFile
End If
'创建临时文件名
strTempFile = GetTemporaryPath & "temp.mdb"
If Len(Dir(strTempFile)) Then Kill strTempFile
'通过DBEngine压缩数据库文件
DBEngine.CompactDatabase Location, strTempFile
'删除原来的数据库文件
Kill Location
'拷贝刚刚压缩过临时数据库文件至原来位置
FileCopy strTempFile, Location
在SQL server 中恢复数据的几种办法:
1.自然就是 backup 的 恢复方法 backup 这种方法是最安全,最可靠的方法操作起来也很简单,只要在 sql server 的 enterprise manager中选择 restore 就可以了。
用T-SQL 也可以完成:
RESTORE DATABASE test FROM DISK = ’c:mssql7ackup est.bak’
当然这是用的 文件恢复,如果是 设备恢复 自然也是可以的。
2.可是有的时候,SQL server 是在我们毫无准备的情况下瘫痪的,有的时候是伴随者 NT 的瘫痪而引起的,(这个时候,豆腐想 墙上 Gates 的画像有仍了几个 西红柿),怎么办呢?这个时候就只有采用 sql server 的 t-sql 中提供的系统存储过程了:
sp_atach_db
在这里举一个简单的例子:
sp_attach_db @dbname = N’pubs’,
@filename1 = N’c:mssql7datapubs.mdf’,
@filename2 = N’c:mssql7datapubs_log.ldf’
这种方法应该说是有很高的成功率的,不过在 实践中 豆腐听说 这样后,数据库成为只读的,那也没有办法了。如果只有 mdf 没有 ldf 文件的话,可以使用 sp_attach_single_file
sp_attach_single_file_db @dbname = ’pubs’, @physname = ’c:mssql7datapubs.mdf’
这个方法本来是 用来 对 sp_deatach 的操作的反操作,不过直接使用也还是可以成功的。
这里有几个关于SQL SERVER的问题想向您请教(服务器端脚本编程):
(1)如何在SQL SERVER中用SQL语句获得当前的数据库名称?
(2)如何在定义一个全局变量而不是局部变量,因为我在这里定义了
一个循环,在这个循环里有对一个临时表加字段和对临时表插入数据
的操作。但这两个操作必须放在不同的批次里.(需要用GO语句分开)。
这时控制循环的变量参数就不起作用了,因为变量参数只能在一个
批次里起作用,到下一个批次就要重新定义了。真头疼!能不能定义
全局变量,让它在所有批次中都起作用?
这两个问题,其实并不具有一定的普遍性,但是解决这两个问题的 思路和方法 却有一定的 普遍性,所以我专门把这两个问题拿出来 讲一下
(1)首先 这个当前 所在 DataBase 肯定需要用到 系统存储过程 这一点是 十分肯定的,我自然想到了sp_who 执行后,列出了当前所有的 系统进程的 所有信息,我一看 有 Runnable,有 Slepping 肯定应该是 runnable 了,一看 他的 spid 想起来了,有个系统的 全局变量@@SPID,先试一下,sp_who @@spid 哈哈 成功了这个问题的解决之道 是 一定要熟悉 系统的存储过程和系统全局变量,并且要善于观察和思考
(2) 至于 第二个问题,则纯粹是一种 t-sql 编程的思路问题,首先我不赞同用一个规则去判断两个 存储过程,因为这不符和 t-SQL 编程的规范,但是既然问题出来了,就要想办法 解决,我们知道在 两个批次里 是不可能共巷数据的,所以 我想到了 cursor 游标,最终 经过测试,也成功了。

[!--infotagslink--]

相关文章

  • Mybatis Plus select 实现只查询部分字段

    这篇文章主要介绍了Mybatis Plus select 实现只查询部分字段的操作,具有很好的参考价值,希望对大家有所帮助。如有错误或未考虑完全的地方,望不吝赐教...2021-09-01
  • vue 监听 Treeselect 选择项的改变操作

    这篇文章主要介绍了vue 监听 Treeselect 选择项的改变操作,具有很好的参考价值,希望对大家有所帮助。一起跟随小编过来看看吧...2020-09-01
  • Mysql select语句设置默认值的方法

    1.在没有设置默认值的情况下: 复制代码 代码如下:SELECT userinfo.id, user_name, role, adm_regionid, region_name , create_timeFROM userinfoLEFT JOIN region ON userinfo.adm_regionid = region.id 结果:...2014-05-31
  • vue treeselect获取当前选中项的label实例

    这篇文章主要介绍了vue treeselect获取当前选中项的label实例,具有很好的参考价值,希望对大家有所帮助。一起跟随小编过来看看吧...2020-09-01
  • vue Treeselect下拉树只能选择第N级元素实现代码

    这篇文章主要介绍了vue Treeselect下拉树只能选择第N级元素实现代码,具有很好的参考价值,希望对大家有所帮助。一起跟随小编过来看看吧...2020-09-01
  • Vue select 绑定动态变量的实例讲解

    这篇文章主要介绍了Vue select 绑定动态变量的实例讲解,具有很好的参考价值,希望对大家有所帮助。一起跟随小编过来看看吧...2020-10-23
  • MySQL中SELECT+UPDATE处理并发更新问题解决方案分享

    问题背景: 假设MySQL数据库有一张会员表vip_member(InnoDB表),结构如下: 当一个会员想续买会员(只能续买1个月、3个月或6个月)时,必须满足以下业务要求: &#8226;如果end_at早于当前时间,则设置start_at为当前时间,end_at为当前时...2014-05-31
  • jQuery为动态生成的select元素添加事件的方法

    下面小编就为大家带来一篇jQuery为动态生成的select元素添加事件的方法。小编觉得挺不错的,现在就分享给大家,也给大家做个参考。一起跟随小编过来看看吧...2016-09-01
  • javascript获取select标签选中的值

    这篇文章主要介绍javascript获取select标签选中的值方法,比较实用,需要的朋友可以参考下。...2016-06-12
  • js实现可输入可选择的select下拉框

    这篇文章主要为大家详细介绍了js实现可输入可选择的select下拉框,可及时匹配包含输入的内容,具有一定的参考价值,感兴趣的小伙伴们可以参考一下...2017-01-09
  • C#实现图片放大功能的按照像素放大图像方法

    这篇文章主要介绍了C#实现图片放大功能的按照像素放大图像方法,功能非常实用,需要的朋友可以参考下...2020-06-25
  • Mybatis之Select Count(*)的获取返回int的值操作

    这篇文章主要介绍了Mybatis之Select Count(*)的获取返回int的值操作,具有很好的参考价值,希望对大家有所帮助。一起跟随小编过来看看吧...2020-11-23
  • python中翻译功能translate模块实现方法

    在本篇文章中小编给各位整理了一篇关于python中翻译功能translate模块实现方法,有需要的朋友们可以参考下。...2020-12-18
  • Select下拉框模糊查询功能实现代码

    这篇文章主要介绍了Select下拉框模糊查询功能实现代码的相关资料,非常不错,具有参考借鉴价值,需要的朋友可以参考下...2016-07-29
  • jquery Ajax实现Select动态添加数据

    这篇文章主要为大家详细介绍了jquery Ajax实现Select动态添加数据的相关资料,具有一定的参考价值,感兴趣的小伙伴们可以参考一下...2017-06-15
  • 最简单js代码实现select二级联动下拉菜单

    这个是简单也是最基本的下拉框联动的示例,这个示例主要针对那些只有二级联动,且第一级是固定的选项,第二级的内容也比较简单,不刷新的联动,感兴趣的小伙伴们可以参考一下...2016-04-19
  • 微信小程序实现导航功能的操作步骤

    这篇文章主要给大家介绍了关于微信小程序实现导航功能的操作步骤,文中通过示例代码介绍的非常详细,对大家的学习或者工作具有一定的参考学习价值,需要的朋友们下面随着小编来一起学习学习吧...2021-03-10
  • JavaScript实现通过select标签跳转网页的方法

    这篇文章主要介绍了JavaScript实现通过select标签跳转网页的方法,涉及javascript事件响应及窗口操作相关技巧,需要的朋友可以参考下...2016-10-02
  • Element中select多数据加载优化的实现

    本文主要介绍了Element中select多数据加载优化的实现,文中通过示例代码介绍的非常详细,具有一定的参考价值,感兴趣的小伙伴们可以参考一下...2021-09-27
  • phpMyAdmin 高级功能设置的方法图解

    phpmyadmin还有高级功能可能大部份站长不知道吧,今天本文章就来给大家介绍phpMyAdmin 高级功能设置的方法图解,希望文章对大家会有所帮助。 phpMyAdmin 安装后,默认...2016-11-25