Questions tagged «t-sql»

Transact-SQL(T-SQL)是Microsoft SQL Server和SAP的Sybase使用的SQL的方言。


2
INSERT语句中的行值表达式数量超过了允许的最大1000行值数量
一个INSERT INTO脚本编写如下。 INSERT INTO tableName (Column1, Column2,....) VALUES (value1, Value2,...), (value1, Value2,...),.... 以下是我们在插入语句上面进行解析时遇到的错误 消息10738,级别15,状态1,行1007 INSERT语句中行值表达式的数量超过了允许的最大1000行值。 我的简单问题是,我们可以更改1000个值的限制吗?


3
限制对某些列的更新。只允许存储过程更新这些列
我有一些敏感的价格列,希望仅通过存储过程进行更新。如果不使用用于更新价格的存储过程,我希望所有代码或手动尝试更改这些价格列中的值都会失败。 我正在考虑使用触发器和令牌表来实现。我正在考虑的想法是有一个令牌表。存储过程将必须首先在令牌表中插入值。然后更新价格列。更新触发器将检查令牌表中是否存在已更新行的令牌。如果找到,它将继续。如果找不到令牌,它将引发异常并使更新事务失败。 有没有一种更好/更好的方法来实施此限制?

2
递归CTE为所有子代查找总计
这是我要使用递归T-SQL查询(大概是CTE)与以下预期结果进行搜索的程序集树。我想知道给定零件的每个组件的总数。 这意味着如果我搜索“铆钉”,我想知道装配体中每个级别的总数量,而不仅仅是直接子数量。 Assembly (id:1) | |-Rivet |-Rivet |-SubAssembly (id:2) | | | |-Rivet | |-Bolt | |-Bolt | |-SubSubAssembly (id:3) | | | |-Rivet | |-Rivet | |-SubAssembly (id:4) |-Rivet |-Bolt DESIRED Results ------- ID, Count 1 , 6 2 , 3 3 , 2 4 , 1 目前,我可以得到直系父母,但想知道如何扩展我的CTE,以使我可以将此信息向上滚动。 With …

3
创建多级层次结构,其中每个节点具有随机数量的子级
我需要创建一些涉及层次结构的测试数据。我可以简化并做几个CROSS JOINs,但这将使我的结构完全统一/没有任何变化。这不仅看起来很乏味,而且测试数据的缺乏变化有时掩盖了原本会发现的问题。因此,我想生成遵循以下规则的非统一层次结构: 3级深 1级随机是5-20个节点 级别2是1-10个节点,级别1的每个节点随机 级别3是1-5个节点,级别2的每个节点随机 所有分支的深度将为3级。此时,深度均匀是可以的。 在任何给定级别上,子节点的名称都可以重叠(即,子节点的名称在同一级别的所有节点上不必唯一)。 术语“随机”在此定义为伪随机,而不是唯一随机的。需要提到这一点,因为术语“随机”通常用于表示“不会产生重复项的给定集合的随机排序”。我接受random = random,如果第1级每个节点的子代数分别只有4、7和8,即使跨越第1级20个节点,每个节点的潜在散布为1-10个子代,那很好,因为那是随机的。 即使使用嵌套WHILE循环可以很容易地做到这一点,但首选还是要找到一种基于集合的方法。一般而言,生成测试数据并没有生产代码所具有的效率要求,但是针对基于集合的方法进行射击可能会更具教育意义,并且在将来找到基于集合的问题解决方法时会有所帮助。因此,WHILE循环不排除循环,只有在不可能使用基于集合的方法时才可以使用循环。 基于集合=理想情况下是单个查询,而不考虑CTE,APPLY等。因此,使用现有或内联数字表就可以了。使用WHILE / CURSOR /过程方法将不起作用。我想将数据的部分存储到临时表或表变量中就好了,只要这些操作都是基于集合的,没有循环即可。但是,话虽如此,除非可以证明多查询方法实际上更好,否则单查询方法可能比多查询更受青睐。还请记住,“更好”的构成通常是主观的;-)。还请记住,前一句中“通常”的使用也是主观的。 任何版本的SQL Server(我想是2005年及更高版本)都可以。 只有纯T-SQL:没有这些愚蠢的SQLCLR东西!至少在生成数据方面。创建目录和文件将使用SQLCLR完成。但是在这里,我只是专注于生成所创建内容的价值。 T-SQL多语句TVF被认为是过程性的,而不是基于集合的,即使在外部它们掩盖了集合中的过程方法。有时候这是绝对合适的。这不是那个时候之一。同样,也不允许使用T-SQL标量函数,这不仅是因为它们也是过程性的,而且查询优化器有时会缓存其值并重复该值,以使输出结果与预期不符。 T-SQL内联TVF(又名iTVF)是基于集合的okey-dokey,并且实际上与使用相同[ CROSS | OUTER ] APPLY,后者如上所述是可以的。 重复执行查询应产生与先前运行几乎不同的结果。 更新说明1:最终结果集应表示为Level3的每个不同节点都有一行,其完整路径从Level1开始。这意味着Level1和Level2值将必须在一个或多个行上重复,除非只有一个Level2节点仅包含一个Level3节点。 澄清更新2:每个节点都有一个非常好的首选项,每个节点都有一个名称或标签,而不仅仅是一个数字。这将使生成的测试数据更加有意义和现实。 我不确定这个附加信息是否重要,但是如果万一有助于了解某些情况,测试数据将与我对以下问题的回答有关: 将XML文件导入SQL Server 2012 尽管此时不相关,但是生成此层次结构的最终目标是创建一个目录结构来测试递归文件系统方法。级别1和2将是目录,级别3将最终成为文件名。我搜索了一下(在这里和通过Google),但只发现了一个参考,以生成随机层次结构: Linux:创建随机目录/文件层次结构 这个问题(在StackOverflow上)实际上在期望结果方面非常接近,因为它还试图创建用于测试的目录结构。但是,这个问题(以及答案)的重点是Linux / Unix shell脚本,而不是我们所生活的基于集合的世界。 现在,我知道了如何生成随机数据,并且已经在创建文件的内容,以便它们也可以显示变化。这里最棘手的部分是每个集合中元素的数量是随机的,而不是特定的字段。并且,每个节点内的元素数量必须与同一级别上的其他节点随机。 示例层次结构 Level 1 Level 3 |---- A | |-- 1 …

2
带有随机数和联接类型的意外结果
我有一个简单的脚本,该脚本获取四个随机数(1到4),然后重新加入以获取匹配的database_id数。当我使用LEFT JOIN运行脚本时,每次都会返回四行(预期结果)。但是,当我使用INNER JOIN运行它时,我得到的行数不尽相同-有时是两行,有时是八行。 从逻辑上讲,应该没有什么区别,因为我知道sys.databases中存在具有database_ids 1-4的行。并且由于我们从具有四行的随机数表中选择(而不是与之连接),因此返回的行数绝不能超过四行。 SQL Server 2012和2014中都会发生这种情况。是什么导致INNER JOIN返回不同数量的行? /* Works as expected -- always four rows */ SELECT rando.RandomNumber, d.database_id FROM (SELECT 1 + ABS(CHECKSUM(NEWID())) % (4) AS RandomNumber FROM sys.databases WHERE database_id <= 4) AS rando LEFT JOIN sys.databases d ON rando.RandomNumber = d.database_id; /* Returns a varying …
16 sql-server  t-sql 

2
如何检查非ASCII字符
检查VARCHAR字段是否包含非Ascii字符的最佳方法是什么? CHAR(1)通过CHAR(31)和CHAR(127)通过CHAR(255)。 我尝试使用PATINDEX,并遇到了以下问题。 检查下限范围是否正确。 SELECT * FROM mbrnotes WHERE PATINDEX('%[' + CHAR(1)+ '-' +CHAR(31)+']%',LINE_TEXT) > 0 我的数据有三个记录为0x1E,并且所有三个都返回了。 但是当我只检查上限时: SELECT * FROM mbrnotes WHERE PATINDEX('%[' + CHAR(127)+ '-' +CHAR(255)+']%',LINE_TEXT) > 0 它返回接近表中的所有记录(表计数170737和返回计数170735),并且由于我的数据在此范围内没有任何值,因此我认为它应该不返回任何记录。

3
具有“预览模式”的数据库存储过程
在我使用的数据库应用程序中,一个相当普遍的模式是需要为具有“预览模式”的报表或实用程序创建存储过程。当此类过程确实更新时,此参数指示应返回操作结果,但该过程实际上不应执行对数据库的更新。 一种实现方法是简单地if为参数编写一条语句,并具有两个完整的代码块。其中一个确实更新并返回数据,而另一个仅返回数据。但这是不希望的,因为代码重复并且相对较低的可信度,即预览数据实际上是对更新所发生情况的准确反映。 下面的示例尝试利用事务保存点和变量(与临时表相反,不受事务影响)与临时表相比,仅将单个代码块用作实时更新模式。 注意:不能选择事务回滚,因为此过程调用本身可能嵌套在事务中。这已在SQL Server 2012上进行了测试。 CREATE TABLE dbo.user_table (a int); GO CREATE PROCEDURE [dbo].[PREVIEW_EXAMPLE] ( @preview char(1) = 'Y' ) AS CREATE TABLE #dataset_to_return (a int); BEGIN TRANSACTION; -- preview mode required infrastructure DECLARE @output_to_return TABLE (a int); SAVE TRANSACTION savepoint; -- do stuff here INSERT INTO dbo.user_table (a) …
15 sql-server  t-sql 

2
添加联接提示时,为什么SQL Server行估计会更改?
我有一个查询,该查询连接了几个表并且执行得很差-行估计相差1000倍,并且选择了嵌套循环连接,从而导致了多个表扫描。查询的形状非常简单,看起来像这样: SELECT t1.id FROM t1 INNER JOIN t2 ON t1.id = t2.t1_id LEFT OUTER JOIN t3 ON t2.id = t3.t2_id LEFT OUTER JOIN t4 ON t3.t4_id = t4.id WHERE t4.id = some_GUID 在处理查询时,我注意到当我提示它对一个连接使用合并连接时,它的运行速度快了很多倍。我能理解-合并联接是联接数据的更好选择,但是SQL Server选择嵌套循环时并不能正确估计它。 我不完全理解的是,为什么此联接提示会更改所有计划运营商的所有估计?通过阅读不同的文章和书籍,我假设基数估计是在构建计划之前执行的,因此使用提示不会改变估计,而是明确地告诉SQL Server使用特定的物理联接实现。 但是,我看到的是,合并提示使所有估计变得非常完美。为什么会发生这种情况,并且有任何通用的技术可以使查询优化器在没有提示的情况下做出更好的估计-考虑到统计数据显然可以做到这一点? UPD:可在此处找到匿名的执行计划:https ://www.dropbox.com/s/hchfuru35qqj89s/merge_join.sqlplan?dl =0 https://www.dropbox.com/s/38sjtv0t7vjjfdp/no_hints_join.sqlplan?dl = 0 我使用TF 3604、9292和9204检查了两个查询使用的统计信息,它们是相同的。但是,查询之间扫描/查找的索引有所不同。 除此之外,我尝试使用来运行查询OPTION (FORCE ORDER)-它的运行速度比使用合并连接还要快,为每个连接选择HASH MATCH。

2
为什么标量值函数需要执行权限而不是选择权限?
我想知道为什么对于标量值函数,我必须授予用户执行权而不仅仅是选择权? 同时,表值函数仅在具有选择权限或db_datareader成员资格的情况下才能正常工作。 为了更清楚,这里是我的示例:我需要一个对数据库具有只读权限的用户。所以我创建了一个名为的用户,testUser并为其指定了db_datareader成员资格。然后我创建了一个名为的表值函数fn_InlineTable。一切都很棒。testUser全天运行此SQL select * from dbo.fn_InlineTable 然后我需要一个标量函数,所以我创建了一个叫做的标量函数fn_ScalarTest。 testUser无法运行此SQL Select dbo.fn_ScalarTest(1) 可以理解的是:这是因为我没有授予“ testUser”执行权限fn_ScalarTest。 我的问题是:基于此链接/programming/6150888/insert-update-delete-with-function-in-sql-server,说FUNCTION不能使用a来执行修改数据库状态的操作。那么,为什么不让标量函数与相同的“ SELECT”权限一起使用,而不是执行权限呢? 我希望我的问题有道理。谢谢。

1
如何设计查询以暂停/睡眠/等待指定的时间?
我正在针对SQL Server 2000实例测试监视应用程序。如何编写需要花费指定时间的T-SQL查询?例如,大多数脚本语言都具有类似SLEEP命令的内容,该命令使您可以在指定的时间段内暂停脚本执行。我正在寻找与SQL Server 2000兼容的类似内容。这旨在测试监视应用程序的长期运行的查询阈值设置。

3
从胜负平局数据获取连胜数和连胜类型
我做了一个SQL小提琴为这个问题,是否对任何人来说都使事情变得容易。 我有一个各种各样的幻想体育数据库,我想弄清楚的是如何得出“当前连胜”数据(如“ W2”(如果该队赢得了他们的最后两场比赛)或“ L1”(如果他们输了)他们赢得上一场比赛后的最后一场比赛-如果他们并列最近的比赛,则为“ T1”)。 这是我的基本架构: CREATE TABLE FantasyTeams ( team_id BIGINT NOT NULL ) CREATE TABLE FantasyMatches( match_id BIGINT NOT NULL, home_fantasy_team_id BIGINT NOT NULL, away_fantasy_team_id BIGINT NOT NULL, fantasy_season_id BIGINT NOT NULL, fantasy_league_id BIGINT NOT NULL, fantasy_week_id BIGINT NOT NULL, winning_team_id BIGINT NULL ) 的值NULL在winning_team_id列指示该匹配领带。 这是一个DML声明示例,其中包含6个团队和3周对战的示例数据: INSERT INTO …

4
如何在维护计划作业中更改或更新本地服务器连接
两天前,我们的客户更改了我们的Dev Server名称之一 重命名服务器后,由于服务器名称不匹配,所有我的维护作业和其他作业都失败了。 我们正在使用sql server 2012版本和 Server 2008 OS 所以今天早上我将我的Sql Server 2012名称重命名为更新的给定名称,并进行了表,程序更新 我试图在维护作业中更新本地服务器连接,但是无法编辑。然后我添加了新的服务器连接,但仍无用,执行作业时出现错误。 我尝试了作业属性选项中的目标页面后,也仅选择了目标服务器,并且禁用了多个目标服务器。 错误如下 以用户身份执行:NT Service \ SQLSERVERAGENT。用于64位版权(C)Microsoft Corporation的Microsoft(R)SQL Server执行软件包实用程序版本11.0.2100.60。版权所有。 开始时间:12:01:28 AM错误:2013-12-16 00:01:43.98代码:0xC00291EC源:{410F7661-F71A-4B68-9584-BA422AB00F02}执行SQL任务 说明:无法获取连接“本地服务器连接” 。连接可能配置不正确,或者您对此连接没有正确的权限。结束错误 错误:2013-12-16 00:02:00.00 代码:0xC0024104 源:Territory_Update 说明:任务上的Execute方法返回错误代码0x80131904(建立与SQL Server的连接时发生了与网络相关或特定于实例的错误。找不到服务器或无法访问该服务器。请验证实例名称是否正确以及该实例名称是否正确。 SQL Server配置为允许远程连接(提供程序:命名管道提供程序,错误:40-无法打开与SQL Server的连接)。Execute方法必须成功,并使用“ out”参数指示结果。结束错误 错误:2013-12-16 00:02:15.00 代码:0xC0024104 源:{4E2AF328-0B8D-4905-83BE-839FDDEFC09C} 说明:任务上的Execute方法返回错误代码0x80131904(建立与SQL Server的连接时发生了与网络相关或特定于实例的错误。找不到服务器或无法访问该服务器。请验证实例名称是否正确以及该实例名称是否正确。 SQL Server配置为允许远程连接(提供程序:命名管道提供程序,错误:40-无法打开与SQL Server的连接)。Execute方法必须成功,并使用“ out”参数指示结果。 结束错误DTExec:程序包执行返回DTSER_FAILURE(1)。 开始:12:01:28 AM 完成:12 …

2
如何使用执行计划优化T-SQL查询
我有一个SQL查询,过去两天我一直在尝试使用试错法和执行计划进行优化,但无济于事。请原谅我这样做,但我将在此处发布整个执行计划。我已尽力使查询和执行计划中的表名和列名通用化,以简化和保护我公司的IP。可以使用SQL Sentry Plan Explorer打开执行计划。 我已经做了相当多的T-SQL,但是使用执行计划来优化查询对我来说是一个新领域,并且我确实试图理解如何做到这一点。因此,如果有人可以帮助我并解释如何解释该执行计划以在查询中找到优化它的方法,我将永远感激不已。我还有许多要优化的查询-我只需要一个跳板就可以帮助我解决第一个问题。 这是查询: DECLARE @Param0 DATETIME = '2013-07-29'; DECLARE @Param1 INT = CONVERT(INT, CONVERT(VARCHAR, @Param0, 112)) DECLARE @Param2 VARCHAR(50) = 'ABC'; DECLARE @Param3 VARCHAR(100) = 'DEF'; DECLARE @Param4 VARCHAR(50) = 'XYZ'; DECLARE @Param5 VARCHAR(100) = NULL; DECLARE @Param6 VARCHAR(50) = 'Text3'; SET NOCOUNT ON DECLARE @MyTableVar TABLE …

By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.