与这个问题相关,我决定检查我的数据仓库中的UDF(这应该在很大程度上是确定性的),并且我找到了几个不应该存在的UDF.
例如:
CREATE FUNCTION [udf_YearFromDataDtID]
(
@DATA_DT_ID int
)
RETURNS int
AS
BEGIN
RETURN @DATA_DT_ID / 10000
END
Run Code Online (Sandbox Code Playgroud)
显示在此查询中:
SELECT ROUTINE_NAME
FROM INFORMATION_SCHEMA.ROUTINES
WHERE IS_DETERMINISTIC = 'NO'
AND ROUTINE_TYPE = 'FUNCTION'
ORDER BY ROUTINE_NAME
Run Code Online (Sandbox Code Playgroud)
为什么是这样?
sql sql-server sql-server-2005 deterministic user-defined-functions
我认为这不是确定性的,因为DB_NAME()它不是确定性的?如果DB_NAME()不是确定性的,为什么它不是确定性的?
ALTER FUNCTION [TheSchema].[udf_IS_PRODUCTION] ()
RETURNS bit
WITH SCHEMABINDING
AS
BEGIN
RETURN CASE WHEN DB_NAME() = 'PRODUCTION' THEN CONVERT(bit, 1) ELSE CONVERT(bit, 0) END
END
Run Code Online (Sandbox Code Playgroud)
更新:此版本工作,是确定性的,允许在任何数据库中使用相同的代码并删除数据库名称的硬编码(这也允许我删除有关数据库名称编码的另一个自动系统运行状况异常)
ALTER FUNCTION [TheSchema].[udf_IS_PRODUCTION] ()
RETURNS bit
WITH SCHEMABINDING
AS
BEGIN
RETURN (SELECT IS_PRODUCTION FROM TheSchema.IS_PRODUCTION)
END
Run Code Online (Sandbox Code Playgroud)
仅供参考这是我的系统健康自我报告系统中的代码片段,用于监控潜在问题.
SELECT 'Non-deterministic Scalar UDF' AS Problem
,QUOTENAME(ROUTINE_SCHEMA) + '.' + QUOTENAME(ROUTINE_NAME) AS ROUTINE_NAME
FROM INFORMATION_SCHEMA.ROUTINES WITH (NOLOCK)
WHERE IS_DETERMINISTIC = 'NO'
AND ROUTINE_TYPE = 'FUNCTION'
AND DATA_TYPE <> 'TABLE'
ORDER BY …Run Code Online (Sandbox Code Playgroud) 假设我有两个确定性有限状态自动机,由以下转换图表示:
关键字 IF 的 FSA: IF
___ ___ _
/ \ I / \ F // \\
>| 0 |----->| 1 |----->||2||
\___/ \___/ \\_//
Run Code Online (Sandbox Code Playgroud)
ID 的 FSA: [AZ][A-Z0-9]*
------------
___ | _ LET |
/ \ LET // \\<------
>| 0 |----->||1||
\___/ \\_//<------
| NUM |
------------
Run Code Online (Sandbox Code Playgroud)
我可以使用什么算法将它们组合成具有三个最终状态的单个确定性有限状态自动机,由以下转换图表示:
-----------------------
| LETTER BUT F OR NUM | --------
___ | _ _ LET v _ | LET |
/ \ I // \\ F // \\----->// \\<------
>| 0 …Run Code Online (Sandbox Code Playgroud) 我有以下功能:
SET ANSI_NULLS ON
GO
SET QUOTED_IDENTIFIER ON
GO
ALTER FUNCTION [dbo].[IP4toBIGINT](
@ip4 varchar(15)
)
RETURNS bigint
WITH SCHEMABINDING
AS
BEGIN
-- oc3 oc2 oc1 oc0
-- 255.255.255.255
-- Declared as BIGINTs to avoid overflows when multiplying later on DECLARE @oct0 bigint, @oct1 bigint, @oct2 bigint, @oct3 bigint;
DECLARE @Result bigint;
SET @oct3 = CAST(PARSENAME(@ip4, 4) as tinyint);
SET @oct2 = CAST(PARSENAME(@ip4, 3) as tinyint);
SET @oct1 = CAST(PARSENAME(@ip4, 2) as tinyint);
SET @oct0 = CAST(PARSENAME(@ip4, 1) as tinyint);
-- …Run Code Online (Sandbox Code Playgroud) 我想在我的游戏引擎中实现确定性,以便能够保存和重放输入序列并使网络更容易.
我的引擎目前使用一个可变的时间步长:每一帧我计算更新/绘制最后一个时间并将其传递给我的实体的更新方法所花费的时间.这使得1000FPS游戏看起来像30FPS游戏一样快,但引入了不确定行为.
一个解决方案可能是将游戏固定到60FPS,但它会使输入更加延迟,并且不会获得更高帧率的好处.
所以我尝试使用一个线程(不断调用update(1)然后休眠16ms)并在游戏循环中尽可能快地绘制.它有点工作,但它经常崩溃,我的游戏变得无法播放.
有没有办法在我的游戏循环中实现线程来实现确定性而不必重写所有依赖于引擎的游戏?
使用其中一种本机方法(map、forEach、reduce、filter 等)遍历数组的顺序是否具有确定性并由标准保证?
EG,是否保证 foo、bar、baz 和 qux 是[0, 2, 6, 12]?
const a = [1, 2, 3, 4];
const foo = a.map((item, index) => item * index);
const bar = []; a.forEach((item, index) => bar[index] = item * index);
const baz = []; a.reduce((total, item, index) => baz[index] = item * index, 0);
const qux = []; a.filter((item, index) => qux[index] = item * index);
// etc
Run Code Online (Sandbox Code Playgroud)
(这些是(非常)人为的例子)
对于我的 ruby 测试套件,我需要可预测的 UUID。我知道 UUID 本质上是随机和非确定性的,这很好。但是在测试套件中,拥有可以通过夹具、数据助手、种子等重复使用的 UUID 会很有用。
我现在有一个简单的实现,很容易导致无效的 UUID:
def fake_uuid(character = "x")
[8, 4, 4, 4, 12].map { |length| character * length }.join("-")
end
fake_uuid('a') => "aaaaaaaa-aaaa-aaaa-aaaa-aaaaaaaaaaaa" # This is valid
fake_uuid('z') => "zzzzzzzz-zzzz-zzzz-zzzz-zzzzzzzzzzzz" # This is invalid, not hex.
Run Code Online (Sandbox Code Playgroud)
显然,我可以添加只允许 af,0-9 作为输入的检查。另一种方法是对预先生成的 UUID 列表进行硬编码,然后根据参数选择一个。
但我想知道,没有更好的方法吗?UUIDv5 会为此工作吗?有没有办法调用SecureRandom.uuid让它返回相同的 UUID(对于线程或会话)?它需要额外的宝石吗?或者我的方法是最接近的方法吗?
让它由所有相同的字符组成不是必需的。
让它具有一定的可读性是一个很大的优点,但不是必需的。这样,您可以例如确保 aCompany具有 UUIDcccccccc-cccc-cccc-cccc-cccccccccccc及其EmployeeUUID eeeeeeee-eeee-eeee-eeee-eeeeeeeeeeee。
我认为 Dijkstra 的算法是确定的,因此如果您选择相同的起始顶点,您将获得相同的结果(到每个其他顶点的距离相同)。但我不认为它是确定性的(它为每个操作定义了以下操作),因为这意味着它首先不必搜索最短距离。
我对么?如果我错了,您能否解释一下为什么它是确定性的,并举个例子?
对于相同的输入,满足以下条件的代码是否可以为每次运行生成不同的输出?
Pytorch Dataloader 的迭代顺序是否保证相同(在温和条件下)?
例如:
dataloader = DataLoader(my_dataset, batch_size=4,
shuffle=True, num_workers=4)
print("run 1")
for batch in dataloader:
print(batch["index"])
print("run 2")
for batch in dataloader:
print(batch["index"])
Run Code Online (Sandbox Code Playgroud)
到目前为止,我已经尝试对其进行测试,但它似乎没有修复,两次运行的顺序相同。有没有办法使订单相同?谢谢
编辑:我也试过做
unlabeled_sampler = data.sampler.SubsetRandomSampler(unlabeled_indices)
unlabeled_dataloader = data.DataLoader(train_dataset,
sampler=unlabeled_sampler, batch_size=args.batch_size, drop_last=False)
Run Code Online (Sandbox Code Playgroud)
然后遍历数据加载器两次,但结果是相同的不确定性。
deterministic ×10
algorithm ×2
c++ ×2
sql ×2
sql-server ×2
arrays ×1
dataloader ×1
dijkstra ×1
game-engine ×1
iterable ×1
iteration ×1
javascript ×1
pytorch ×1
ruby ×1
uuid ×1