Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

SELECT * INTO retains ORDER BY in SQL Server 2008 but not 2012

Execute the following SQL in 2008 and 2012. When executed in 2008, the returned result is in its correct sort order. In 2012, the sortorder is not retained.

Is this a known change? Is there a work-around for 2012 to retain the sort order?

CREATE TABLE #MyTable(Name VARCHAR(50), SortOrder INT)
INSERT INTO #MyTable SELECT 'b', 2 UNION ALL SELECT 'c', 3 UNION ALL SELECT 'a', 1 UNION ALL SELECT 'e', 5 UNION ALL SELECT 'd', 4

SELECT * INTO #Result FROM #MyTable ORDER BY SortOrder

SELECT * FROM #Result

DROP TABLE #MyTable
DROP TABLE #Result
like image 929
Rivka Avatar asked May 20 '13 18:05

Rivka


People also ask

Can we use ORDER BY in CTE?

Can we use ORDER BY clause in a CTE expression? The ORDER BY clause is invalid in views, inline functions, derived tables, subqueries, and common table expressions, unless TOP, OFFSET or FOR XML is also specified. Incorrect syntax near ','. Clearly, you cannot.

What is the default ORDER BY in SQL Server?

The ORDER BY statement in SQL is used to sort the fetched data in either ascending or descending according to one or more columns. By default ORDER BY sorts the data in ascending order. We can use the keyword DESC to sort the data in descending order and the keyword ASC to sort in ascending order.

Can we use ORDER BY in insert query?

Yes. The actual order in which rows are inserted into the target table is dependent on the execution plan.


2 Answers

Workaround : You could add a SET ROWCOUNT before this type of query, then put if back to zero after to reset it, it works. This will force SQL to keep the order in your query.

SET ROWCOUNT 1000000000

CREATE TABLE #MyTable(Name VARCHAR(50), SortOrder INT)
INSERT INTO #MyTable SELECT 'b', 2 UNION ALL SELECT 'c', 3 UNION ALL SELECT 'a', 1 UNION ALL SELECT 'e', 5 UNION ALL SELECT 'd', 4

SELECT * INTO #Result FROM #MyTable ORDER BY SortOrder

SELECT * FROM #Result

SET ROWCOUNT 0

DROP TABLE #MyTable
DROP TABLE #Result
like image 51
patrick imbault Avatar answered Oct 04 '22 16:10

patrick imbault


How can you tell what the order is inside a table by using select * from #result? There is no guarantee as to the order in a select query.

However, the results are different on SQL Fiddle. If you want to guarantee that the results are the same, then add a primary key. Then the insertion order is guaranteed:

CREATE TABLE MyTable(Name VARCHAR(50), SortOrder INT)
INSERT INTO MyTable SELECT 'b', 2 UNION ALL SELECT 'c', 3 UNION ALL SELECT 'a', 1 UNION ALL SELECT 'e', 5 UNION ALL SELECT 'd', 4


select top 0 * into result from MyTable;

alter table Result add id int identity(1, 1) primary key;

insert into Result(name, sortorder)
    SELECT * FROM MyTable
    ORDER BY SortOrder;

I still abhor doing select * from Result after this. But yes, it does return them in the correct order in both SQL Server 2008 and 2012. Not only that, but because SQL Server guarantees that primary keys are inserted in the proper order, the records are even guaranteed to be in the correct order in this case.

BUT . . . just because the records are in a particular order on the pages doesn't mean they will be retrieved in that order with no order by clause.

like image 28
Gordon Linoff Avatar answered Oct 04 '22 16:10

Gordon Linoff