我正在尝试学习T-SQL编程,但我发现下面的代码有错误。该代码用于学习如何不按顺序进行排序,它看起来像气泡排序算法。
我首先创建表格并尝试进行排序后插入随机数
代码:
CREATE TABLE #NumbersArray
(
ArrayIndex INT PRIMARY KEY,
Value INT
)
GO
INSERT INTO #NumbersArray(ArrayIndex, Value)
SELECT 0, 5
UNION ALL
SELECT 1, 1
UNION ALL
SELECT 2, 3
UNION ALL
SELECT 3, 4
UNION ALL
SELECT 4, 2
SELECT * FROM #NumbersArray
GO
DECLARE @CurrentIndex INT,
@MaxIndex INT,
@swapoccured BIT
SET @swapoccured = 1
SET @MaxIndex = (SELECT COUNT(*) - 1 FROM #NumbersArray)
WHILE (@swapoccured = 1)
BEGIN
SET @swapoccured = 0
SET @CurrentIndex = 0
WHILE (@CurrentIndex < @MaxIndex)
DECLARE @value1 INT
DECLARE @value2 INT
BEGIN -- Mistake was here. I put the begin in wrong place
SET @value1 = (SELECT Value FROM #NumbersArray WHERE ArrayIndex = @CurrentIndex)
SET @value2 = (SELECT Value FROM #NumbersArray WHERE ArrayIndex = @CurrentIndex + 1)
IF (@value1 > @value2)
BEGIN
UPDATE #NumbersArray
SET Value = @value2
WHERE ArrayIndex = @CurrentIndex
UPDATE #NumbersArray
SET Value = @value1
WHERE ArrayIndex = @CurrentIndex + 1
SET @swapoccured = 1
END
SET @CurrentIndex = @CurrentIndex + 1
END
END
SELECT * FROM #NumbersArray
所以我认为我的代码排在第二个排序的中间,因为我的代码从未完成,但是我可以确定问题所在。
答案 0 :(得分:3)
此代码用于学习如何按...进行无序排序...
嗯,那根本不可能做到。
在关系数据库中,表本质上是未排序的。确保查询返回的结果顺序的唯一方法是使用order by
子句。
我正在尝试学习T-SQL编程
了解SQL的任何方言的第一件事是,它旨在与基于集合的方法一起使用-意味着操作是在行集上完成的,而不是基于过程的方法(又名to_timedelta
-通过苦苦挣扎来生。)
您可以搜索“基于集合还是过程”,并找到许多文章,详细说明这些方法之间的区别。
因此,话虽这么说-在SQL世界中不鼓励使用循环(甚至包括嵌套循环)-包括游标,while循环甚至递归公用表表达式。
在大多数情况下,您可以通过使用RBAR来避免使用循环-使用基于集的方法来更改RBAR方法,并使您的代码更高效,并且在大多数情况下更易于编写,读取和维护。 / p>
答案 1 :(得分:1)
首先,没有ORDER BY
子句就不可能对数据进行排序(请阅读@ZoharPeled的回答),因此这不是合适的方法。这样,我将只关注您的错误。原因是第二个WHILE
循环。如果没有BEGIN .. END
,则此循环将无限地声明一个变量:WHILE (@CurrentIndex < @MaxIndex) DECLARE @value1 INT
。
这可能是您想要的(仅用于学习如何使用WHILE
循环,而不是如何订购数据):
CREATE TABLE #NumbersArray
(
ArrayIndex INT PRIMARY KEY,
Value INT
)
GO
INSERT INTO #NumbersArray(ArrayIndex, Value)
SELECT 0, 5
UNION ALL
SELECT 1, 1
UNION ALL
SELECT 2, 3
UNION ALL
SELECT 3, 4
UNION ALL
SELECT 4, 2
SELECT * FROM #NumbersArray
GO
DECLARE @CurrentIndex INT,
@MaxIndex INT,
@swapoccured BIT
SET @swapoccured = 1
SET @MaxIndex = (SELECT COUNT(*) - 1 FROM #NumbersArray)
WHILE (@swapoccured = 1)
BEGIN
SET @swapoccured = 0
SET @CurrentIndex = 0
DECLARE @value1 INT
DECLARE @value2 INT
WHILE (@CurrentIndex < @MaxIndex)
BEGIN
SET @value1 = (SELECT Value FROM #NumbersArray WHERE ArrayIndex = @CurrentIndex)
SET @value2 = (SELECT Value FROM #NumbersArray WHERE ArrayIndex = @CurrentIndex + 1)
IF (@value1 > @value2)
BEGIN
UPDATE #NumbersArray
SET Value = @value2
WHERE ArrayIndex = @CurrentIndex
UPDATE #NumbersArray
SET Value = @value1
WHERE ArrayIndex = @CurrentIndex + 1
SET @swapoccured = 1
END
SET @CurrentIndex = @CurrentIndex + 1
END
END
SELECT * FROM #NumbersArray
DROP TABLE #NumbersArray