2010-02-02 5 views
9

Я продолжаю получать эту ошибку: любые идеи?создание функции с использованием newID()

Invalid use of side-effecting or time-dependent operator in 'newid' within a function.

Я работаю с MS-SQL Server 2005. Вот T-SQL заявление:

Create Function [dbo].[GetNewNumber]() 
RETURNS int 
AS 
BEGIN 

    Declare @code int 

    set @code = (SELECT CAST(CAST(newid() AS binary(3)) AS int)) 

    RETURN (@code) 
END 

ответ

8

Функция не позволит вам использовать NewID, но это можно обойти.

Create View vwGetNewNumber 
as 
Select Cast(Cast(newid() AS binary(3)) AS int) as NextID 

Create Function [dbo].[GetNewNumber] () RETURNS int 
AS 
BEGIN 
Declare @code int 
Select top 1 @code=NextID from vwGetNewNumber 
RETURN (@code) 
END 

Затем вы можете использовать select dbo.[GetNewNumber](), как и планировалось.

+0

Если я беспокоиться о том же количестве генерируются дважды или эти шансы астрономические ??? –

+0

Они не являются пределами возможностей вообще, всего лишь 100 миллионов доступных номеров, сделанных исключительно случайным шансом. По теории проблем дня рождения ваши шансы на матч придут раньше, чем вы ожидаете. – Andrew

+0

+1, хорошее обходное решение. Хотя это может быть защитное кодирование, «верх 1» кажется ненужным в этом случае и очень немного медленнее, чем без. –

10

Вы не можете использовать NEWID() внутри функции.

Обычный обходной путь (по моему опыту, это еще была необходимость GETDATE()) должен иметь передать его в:

Create Function [dbo].[GetNewNumber](@newid UNIQUEIDENTIFIER ) 
RETURNS int 
AS 
BEGIN 

    Declare @code int 

    set @code = (SELECT CAST(CAST(@newid AS binary(3)) AS int)) 

    RETURN (@code) 
END 

И называют это нравится:

SELECT dbo.GetNewNumber(NEWID()) 
2

Значит ли это нужно сделать с помощью вызова функции? Всякий раз, когда я нужна эта функциональность, я просто использую:

checksum(newid()) 

Это будет генерировать отрицательные числа - если они должны быть положительными, вы могли бы использовать

abs(checksum(newid()))