使用 T-SQL 插入 n 条记录

发布于 2024-07-26 04:50:44 字数 352 浏览 8 评论 0原文

我想在表中添加可变数量的记录(天)

并且我已经看到了一个巧妙的解决方案:

SET @nRecords=DATEDIFF(d,'2009-01-01',getdate())
SET ROWCOUNT @nRecords
INSERT int(identity,0,1) INTO #temp FROM sysobjects a,sysobjects b
SET ROWCOUNT 0

但遗憾的是这在 UDF 中不起作用(因为 #temp 和 SET ROWCOUNT)。 知道如何实现这一点吗?

目前我正在使用 WHILE 和表变量来完成此操作,但就性能而言,这不是一个好的解决方案。

I want to add a variable number of records in a table (days)

And I've seen a neat solution for this:

SET @nRecords=DATEDIFF(d,'2009-01-01',getdate())
SET ROWCOUNT @nRecords
INSERT int(identity,0,1) INTO #temp FROM sysobjects a,sysobjects b
SET ROWCOUNT 0

But sadly that doesn't work in a UDF (because the #temp and the SET ROWCOUNT). Any idea how this could be achieved?

At the moment I'm doing it with a WHILE and a table variable, but in terms of performance it's not a good solution.

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(8

别想她 2024-08-02 04:50:45

当您有预先构建的数字表时,只需使用它:

SELECT *
FROM numbers
WHERE number <= DATEDIFF(d,'2009-01-01',getdate())

首先有许多用于构建数字表的技术(使用此处的技术),但是一旦构建并建立索引,您就不会再次构建它。

When you have a pre-built numbers table, just use that:

SELECT *
FROM numbers
WHERE number <= DATEDIFF(d,'2009-01-01',getdate())

There are any number of techniques for building the numbers table in the first place (using techniques here), but once it's built and indexed, you don't build it again.

饭团 2024-08-02 04:50:45

这是我正在使用的方法,并且最适合我的目的并使用 SQL 2000。因为在我的例子中是在 UDF 内,所以我不能使用 ## 或 # 临时表,因此我使用表变量。
我正在做:

DECLARE @tblRows TABLE (pos int identity(0,1), num int) 
DECLARE @numRows int,@i int


SET @numRows = DATEDIFF(dd,@start,@end) + 1
SET @i=1

WHILE @i<@numRows
begin
    INSERT @tblRows SELECT TOP 1 1 FROM sysobjects a

    SET @i=@i+1
end

this is the approach I'm using and works best for my purposes and using SQL 2000. Because in my case is inside an UDF, I can't use ## or # temporary tables so I use a table variable.
I'm doing:

DECLARE @tblRows TABLE (pos int identity(0,1), num int) 
DECLARE @numRows int,@i int


SET @numRows = DATEDIFF(dd,@start,@end) + 1
SET @i=1

WHILE @i<@numRows
begin
    INSERT @tblRows SELECT TOP 1 1 FROM sysobjects a

    SET @i=@i+1
end
惜醉颜 2024-08-02 04:50:45

总体而言,每次迭代时将行数加倍要快得多,

CREATE TABLE dbo.Numbers(n INT NOT NULL PRIMARY KEY)
GO
DECLARE @i INT;
SET @i = 1;
INSERT INTO dbo.Numbers(n) SELECT 1;
WHILE @i<128000 BEGIN
  INSERT INTO dbo.Numbers(n)
    SELECT n + @i FROM dbo.Numbers;
  SET @i = @i * 2;
END; 

我故意没有设置 NOCOUNT ON,以便您看到它如何插入 1,2,4,8 行

Overall much faster to double the amount of rows at every iteration

CREATE TABLE dbo.Numbers(n INT NOT NULL PRIMARY KEY)
GO
DECLARE @i INT;
SET @i = 1;
INSERT INTO dbo.Numbers(n) SELECT 1;
WHILE @i<128000 BEGIN
  INSERT INTO dbo.Numbers(n)
    SELECT n + @i FROM dbo.Numbers;
  SET @i = @i * 2;
END; 

I deliberately did not SET NOCOUNT ON, so that you see how it inserts 1,2,4,8 rows

心意如水 2024-08-02 04:50:45

你可以做PinalDave 建议:

INSERT INTO MyTable (FirstCol, SecondCol)
SELECT 'First' ,1
UNION ALL
SELECT 'Second' ,2
UNION ALL
SELECT 'Third' ,3
UNION ALL
SELECT 'Fourth' ,4
UNION ALL
SELECT 'Fifth' ,5
GO

You could do what PinalDave suggests:

INSERT INTO MyTable (FirstCol, SecondCol)
SELECT 'First' ,1
UNION ALL
SELECT 'Second' ,2
UNION ALL
SELECT 'Third' ,3
UNION ALL
SELECT 'Fourth' ,4
UNION ALL
SELECT 'Fifth' ,5
GO
惟欲睡 2024-08-02 04:50:45

怎么样:

DECLARE @nRecords INT

SET @nRecords=DATEDIFF(d,'2009-01-01',getdate())

SELECT TOP (@nRecords)
    ROW_NUMBER() OVER (ORDER BY a.object_id, b.object_id) - 1
FROM sys.objects a, sys.objects b

如果您不希望它为零索引,请删除“- 1

至少需要 SQL Server 2005。

How about:

DECLARE @nRecords INT

SET @nRecords=DATEDIFF(d,'2009-01-01',getdate())

SELECT TOP (@nRecords)
    ROW_NUMBER() OVER (ORDER BY a.object_id, b.object_id) - 1
FROM sys.objects a, sys.objects b

If you don't want it zero-indexed, remove the "- 1"

Requires at least SQL Server 2005.

淡淡離愁欲言轉身 2024-08-02 04:50:44

如果您使用的是 SQL 2005 或更高版本,则可以使用递归 CTE 来获取日期或数字列表...

with MyCte AS
    (select   MyCounter = 0
     UNION ALL
     SELECT   MyCounter + 1
     FROM     MyCte
     where    MyCounter < DATEDIFF(d,'2009-01-01',getdate()))
select MyCounter, DATEADD(d, MyCounter, '2009-01-01')
from   MyCte 
option (maxrecursion 0)


/* output...
MyCounter   MyDate
----------- -----------------------
0           2009-01-01 00:00:00.000
1           2009-01-02 00:00:00.000
2           2009-01-03 00:00:00.000
3           2009-01-04 00:00:00.000
4           2009-01-05 00:00:00.000
5           2009-01-06 00:00:00.000
....
170         2009-06-20 00:00:00.000
171         2009-06-21 00:00:00.000
172         2009-06-22 00:00:00.000
173         2009-06-23 00:00:00.000
174         2009-06-24 00:00:00.000

(175 row(s) affected)

*/

If you're using SQL 2005 or newer, you can use a recursive CTE to get a list of dates or numbers...

with MyCte AS
    (select   MyCounter = 0
     UNION ALL
     SELECT   MyCounter + 1
     FROM     MyCte
     where    MyCounter < DATEDIFF(d,'2009-01-01',getdate()))
select MyCounter, DATEADD(d, MyCounter, '2009-01-01')
from   MyCte 
option (maxrecursion 0)


/* output...
MyCounter   MyDate
----------- -----------------------
0           2009-01-01 00:00:00.000
1           2009-01-02 00:00:00.000
2           2009-01-03 00:00:00.000
3           2009-01-04 00:00:00.000
4           2009-01-05 00:00:00.000
5           2009-01-06 00:00:00.000
....
170         2009-06-20 00:00:00.000
171         2009-06-21 00:00:00.000
172         2009-06-22 00:00:00.000
173         2009-06-23 00:00:00.000
174         2009-06-24 00:00:00.000

(175 row(s) affected)

*/
伪装你 2024-08-02 04:50:44

您可以使用 WHILE 语句来实现:

declare @i int
declare @rows_to_insert int
set @i = 0
set @rows_to_insert = 1000

while @i < @rows_to_insert
    begin
    INSERT INTO #temp VALUES (@i)
    set @i = @i + 1
    end

You can use a WHILE statement for that:

declare @i int
declare @rows_to_insert int
set @i = 0
set @rows_to_insert = 1000

while @i < @rows_to_insert
    begin
    INSERT INTO #temp VALUES (@i)
    set @i = @i + 1
    end
浮光之海 2024-08-02 04:50:44

你可以使用交叉连接

select top 100000 row_number() over(order by t1.number)-- here you can change 100000 to a number you want or a variable
from   master.dbo.spt_values t1
       cross join master.dbo.spt_values t2

you can use a cross join

select top 100000 row_number() over(order by t1.number)-- here you can change 100000 to a number you want or a variable
from   master.dbo.spt_values t1
       cross join master.dbo.spt_values t2
~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文