表值函数对于插入顺序是否具有确定性?

Tim*_*Tim 4 sql-server determinism t-sql set-returning-functions non-deterministic

假设不使用 ORDER BY 子句,在实例化表并用连续插入填充表的 TABLE 值函数中,插入顺序是否具有确定性?

我需要查看发送给我们的给定数据集中使用的 Unicode 字符范围,以便弄清楚为什么 SSMS 中的查询结果中的某些空格(或者至少在眼睛看来是空格)没有被使用。在某些解析例程中,其行为类似于 char(32)。因此,我编写了一个快速而肮脏的函数,将相关列中的字符串值转换为一组可以查询的元组:

create function [foo].[AllChars]
(@in nvarchar(max))
returns @t TABLE (c nchar(1))
as
begin


declare @i int;
while len(@in)>0
begin
   insert @t(c) values (left(@in,1));
   set @in = substring(@in, 2, len(@in)-1)
end

return;
end
Run Code Online (Sandbox Code Playgroud)

可以这样称呼:

   select X.c theChar, unicode(X.c) uValue
   from myTable T
   cross apply foo.AllChars(T.myCol) X
Run Code Online (Sandbox Code Playgroud)

并将为myTable中的每一行返回一组元组:

t  116
h  104
e  101
   32
c  99
a  97
t  116
   10   <= culprit
i  105
n  110
   32
t  116
h  104
e  101
   32
h  104
a  97
t  116
   
Run Code Online (Sandbox Code Playgroud)

返回的结果按照字符在T.myCol中出现的顺序以及它们插入到 中的顺序@t。如果没有 ORDER BY 子句,该顺序是否得到保证?

Pau*_*ite 7

显示顺序仅由顶级ORDER BY.

\n

您可以重写该函数以返回位置键并使其内联:

\n
CREATE OR ALTER FUNCTION dbo.AllChars\n(\n    @in nvarchar(max)\n)\nRETURNS table\nAS\nRETURN\nSELECT\n    Position = S.[value],\n    TheCharacter = \n        SUBSTRING\n        (\n            @in COLLATE Latin1_General_100_CI_AS_SC, \n            S.[value], \n            1\n        )\nFROM GENERATE_SERIES\n(\n    CONVERT(bigint, 1), -- Types must match exactly\n    LEN(@in) - 1,       -- LEN returns bigint for max input\n    CONVERT(bigint, 1)  -- Types must match exactly\n) AS S;\n
Run Code Online (Sandbox Code Playgroud)\n

COLLATE在那里使用一个子句来演示补充字符。您可能会习惯使用默认的数据库排序规则。

\n

用法示例:

\n
DECLARE @in nvarchar(max) = \n    CONCAT(N\'the  cat in\', NCHAR(10), N\'the hat\');\n\nSELECT \n    AC.Position, \n    AC.TheCharacter,\n    Bytes = DATALENGTH(AC.TheCharacter),\n    Code = UNICODE(AC.TheCharacter)\nFROM dbo.AllChars(@in) AS AC\nORDER BY\n    AC.Position ASC;\n
Run Code Online (Sandbox Code Playgroud)\n

结果:

\n
\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n \n \n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n \n\n \n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n \n\n\n \n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n \n\n\n\n \n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n \n\n\n\n\n \n\n
位置人物字节代码
1t2116
2H2104
3这是2101
4232
54128526
6232
7C299
8A297
9t2116
10232
112105
12n2110
13\xe2\x90\x8a210
14t2116
15H2104
16这是2101
17232
18H2104
19A297
20t2116
\n
\n

数据库<>小提琴

\n

相关:MS SQL Server 是否有generate_series 函数

\n

另请参见Aaron Bertrand 的生成无循环的集合或序列。

\n