AskOverflow.Dev

AskOverflow.Dev Logo AskOverflow.Dev Logo

AskOverflow.Dev Navigation

  • 主页
  • 系统&网络
  • Ubuntu
  • Unix
  • DBA
  • Computer
  • Coding
  • LangChain

Mobile menu

Close
  • 主页
  • 系统&网络
    • 最新
    • 热门
    • 标签
  • Ubuntu
    • 最新
    • 热门
    • 标签
  • Unix
    • 最新
    • 标签
  • DBA
    • 最新
    • 标签
  • Computer
    • 最新
    • 标签
  • Coding
    • 最新
    • 标签
主页 / dba / 问题 / 138802
Accepted
Solomon Rutzky
Solomon Rutzky
Asked: 2016-05-18 12:58:10 +0800 CST2016-05-18 12:58:10 +0800 CST 2016-05-18 12:58:10 +0800 CST

空变量/参数/临时表/临时过程名称的好处或用例?

  • 772

我才发现,通过纯粹的光彩意外地,那个 SQL Server 允许您创建没有任何名称的变量、参数、表变量、临时表(本地和全局)和临时存储过程(本地和全局)!好吧,至少不是我认为的名字。意思是,您可以指定DECLARE @ INT = 5;它是有效的 T-SQL:它执行时没有错误,甚至在 SSMS 中都没有用红色波浪下划线标记(本问题末尾显示了带有完整示例列表的代码)。

鉴于数据库标识符的 MSDN 页面指出(强调我的):

有两类标识符:
常规标识符
...定界
标识符
... 常规标识符和定界标识符都必须包含1 到128 个字符。对于本地临时表,标识符最多可以包含 116 个字符。

这当然看起来不像预期的行为,我最初认为这是一个缺陷(不会导致任何错误,但似乎不是“正确”的行为)并提交了一个连接错误:Parameter, Variable, and Temporary表和过程名称/标识符可以为空。

但是,同一个 MSDN 页面还指出:

常规标识符的规则

变量、函数和存储过程的名称必须符合以下 Transact-SQL 标识符规则。

  1. 第一个字符必须是以下之一:

    • Unicode 标准 3.2 定义的字母。字母的 Unicode 定义包括从 a 到 z、从 A 到 Z 的拉丁字符,以及来自其他语言的字母字符。
    • 下划线 (_)、at 符号 (@) 或井号 (#)。

      标识符开头的某些符号在 SQL Server 中具有特殊含义。以 at 符号开头的常规标识符始终表示局部变量或参数,不能用作任何其他类型对象的名称。以数字符号开头的标识符表示临时表或过程。以双数字符号 (##) 开头的标识符表示全局临时对象。尽管数字符号或双数字符号字符可用于开始其他类型的对象的名称,但我们不推荐这种做法。

因此,可以解释为名称的 1 个字符的最低要求(从最上面引用的显示“1 到 128 个字符”的部分)可以通过简单地满足以下任一@或以下条件#:

  1. 它指出那些将是“第一个”字符,而不是某种类型的事物类型的外部指示,并且
  2. 没有任何内容说明当@或#是第一个字符时,需要2 到128 个字符。

那么,如果这种行为既不是错误也不是缺陷,那么利用这种能力有什么好处吗?是否有合法的用例可以通过执行此操作而受益(即对项目的某些功能性好处,而不仅仅是减少源代码的字符数)?

我想不出一个,除了不专业和在你搬到新雇主时为每个人留下可怕的难以管理的代码之外。

但我也可以看到一个相关的功能问题,因为在许多解析 T-SQL 对象的项目中有许多代码块。如果有人使用 RegEx 模式查找@后跟诸如 之类的(\w+)内容,那么它将跳过这些条目。

-- Local variables:
DECLARE @ INT = 99;
DECLARE @@ VARCHAR(10);
SELECT CONVERT(VARCHAR(20), @), STR(@);
SET @@ = STR(@);
SELECT @@;
GO

-- Table Variable:
DECLARE @ TABLE (Col1 INT);
INSERT INTO @ (Col1) VALUES (86);
SELECT * FROM @;
GO

-- Local Temporary Table:
CREATE TABLE # (Col2 DATETIME);
INSERT INTO # (Col2) VALUES (GETDATE());
SELECT * FROM #;
SELECT OBJECT_ID(N'tempdb..#');
GO

-- Global Temporary Stored Procedure
CREATE PROCEDURE ##  ( @ INT = 999 )
AS
SELECT @ AS [Huh?];
GO

EXEC ##;

EXEC ## 204;

DECLARE @ INT = 12345;
EXEC ## @ = @;
-- The above also work in another session on the same instance, in a different Database

SELECT * FROM tempdb.sys.parameters tsp WHERE tsp.[object_id] = OBJECT_ID(N'tempdb..##');
-- returns 1 row showing a name of just "@"

PS 我在这里、谷歌和 Microsoft Connect 上搜索过,但找不到任何对“缺失”或“空”变量名或“标识符”的引用。但是,@MartinSmith 确实指出了以下 StackOverflow 答案中使用的这种“能力”以减少代码的字符数:Building an ASCII chart of the most commonly used words in a given text。

sql-server t-sql
  • 1 1 个回答
  • 193 Views

1 个回答

  • Voted
  1. Best Answer
    Solomon Rutzky
    2016-05-26T07:24:22+08:002016-05-26T07:24:22+08:00

    似乎这种行为/能力既已知又已弃用。前几天我正在查看sys.dm_os_performance_counters DMV 并注意到以下两个条目:

    object_name                      counter_name    instance_name
    -----------------------------    ------------    -------------------------------
    SQLServer:Deprecated Features    Usage           '@' and names that start with '@@' as
                                                     Transact-SQL identifiers
    
    SQLServer:Deprecated Features    Usage           '#' and '##' as the name of temporary
                                                     tables and stored procedures
    

    然后我检查了 MSDN 文档,发现这两个都在 SQL Server 2016页面中已弃用的数据库引擎功能中,在“Transact-SQL”类别下的SQL Server 未来版本部分不支持的功能中:

    Deprecated feature                     Replacement                               Feature ID
    -----------------------------------    --------------------------------------    ----------
    Use of #, ## as temporary table and    Use at least one additional character.    185
    temporary stored procedure names.
    
    Use of @, @@, or @@ as                 Do not use @ or @@ or names that begin    186
    Transact-SQL identifiers.              with @@ as identifiers.
    

    我能找到的关于此弃用通知的最早参考是在SQL Server 2008 文档中。虽然“已弃用的数据库引擎功能”页面上的版本下拉菜单没有 SQL Server 2005 的条目,但您仍然可以通过https://msdn.microsoft.com/en-us/library访问该文档/ms143729(v=sql.90).aspx,并查看这些项目均未列出。

    这些信息使我得出以下结论:

    • 问题第 1 部分(这是错误还是预期行为):

      它是有意的,尽管是不受欢迎的行为。

    • 问题第 2 部分(此行为是否有好处):

      这里不仅似乎没有任何有益的用例,即使有,也不会因为这种行为/能力被弃用而影响太大,因此不应该继续使用,特别是在新代码中/ 项目。

    • 1

相关问题

  • SQL Server - 使用聚集索引时如何存储数据页

  • 我需要为每种类型的查询使用单独的索引,还是一个多列索引可以工作?

  • 什么时候应该使用唯一约束而不是唯一索引?

  • 死锁的主要原因是什么,可以预防吗?

  • 如何确定是否需要或需要索引

Sidebar

Stats

  • 问题 205573
  • 回答 270741
  • 最佳答案 135370
  • 用户 68524
  • 热门
  • 回答
  • Marko Smith

    连接到 PostgreSQL 服务器:致命:主机没有 pg_hba.conf 条目

    • 12 个回答
  • Marko Smith

    如何让sqlplus的输出出现在一行中?

    • 3 个回答
  • Marko Smith

    选择具有最大日期或最晚日期的日期

    • 3 个回答
  • Marko Smith

    如何列出 PostgreSQL 中的所有模式?

    • 4 个回答
  • Marko Smith

    列出指定表的所有列

    • 5 个回答
  • Marko Smith

    如何在不修改我自己的 tnsnames.ora 的情况下使用 sqlplus 连接到位于另一台主机上的 Oracle 数据库

    • 4 个回答
  • Marko Smith

    你如何mysqldump特定的表?

    • 4 个回答
  • Marko Smith

    使用 psql 列出数据库权限

    • 10 个回答
  • Marko Smith

    如何从 PostgreSQL 中的选择查询中将值插入表中?

    • 4 个回答
  • Marko Smith

    如何使用 psql 列出所有数据库和表?

    • 7 个回答
  • Martin Hope
    Jin 连接到 PostgreSQL 服务器:致命:主机没有 pg_hba.conf 条目 2014-12-02 02:54:58 +0800 CST
  • Martin Hope
    Stéphane 如何列出 PostgreSQL 中的所有模式? 2013-04-16 11:19:16 +0800 CST
  • Martin Hope
    Mike Walsh 为什么事务日志不断增长或空间不足? 2012-12-05 18:11:22 +0800 CST
  • Martin Hope
    Stephane Rolland 列出指定表的所有列 2012-08-14 04:44:44 +0800 CST
  • Martin Hope
    haxney MySQL 能否合理地对数十亿行执行查询? 2012-07-03 11:36:13 +0800 CST
  • Martin Hope
    qazwsx 如何监控大型 .sql 文件的导入进度? 2012-05-03 08:54:41 +0800 CST
  • Martin Hope
    markdorison 你如何mysqldump特定的表? 2011-12-17 12:39:37 +0800 CST
  • Martin Hope
    Jonas 如何使用 psql 对 SQL 查询进行计时? 2011-06-04 02:22:54 +0800 CST
  • Martin Hope
    Jonas 如何从 PostgreSQL 中的选择查询中将值插入表中? 2011-05-28 00:33:05 +0800 CST
  • Martin Hope
    Jonas 如何使用 psql 列出所有数据库和表? 2011-02-18 00:45:49 +0800 CST

热门标签

sql-server mysql postgresql sql-server-2014 sql-server-2016 oracle sql-server-2008 database-design query-performance sql-server-2017

Explore

  • 主页
  • 问题
    • 最新
    • 热门
  • 标签
  • 帮助

Footer

AskOverflow.Dev

关于我们

  • 关于我们
  • 联系我们

Legal Stuff

  • Privacy Policy

Language

  • Pt
  • Server
  • Unix

© 2023 AskOverflow.DEV All Rights Reserve