ios Swift:寻找与 Java 的 Random() PRNG 具有相同输出的交叉兼容方法

ios Swift: looking for a cross compatible method to Java's Random() PRNG that has identical output

这是我的意见: 我正在编写一个应用程序,该应用程序需要从 Java 中编写的游戏中准确重现 PRNG 输出,该游戏使用 Java random() 和给定的种子来创建所有初始游戏 'world' 数据。

我面临的问题是 Java 的 random() 和 ios Swift 原生 PRNG 在给定完全相同的种子时不会生成相同的值。

这是我的测试用例: 在所有情况下都使用相同的 'seed',公式适用于 0 到 9 之间的随机整数。

在Java中:

import java.util.Random;
long seed = 987234904;
Random rnd = new Random(seed);
int result = rnd.nextInt(10);

Java random() 'result' = 0

在 ios Swift - 使用 srand48() / drand48():

import UIKit
var seed: Int = 987234904
srand48(seed)
var result = Int(drand48()*10)

ios Swift drand48() 'result' = 7

在 ios Swift - 使用 rand_r():

import UIKit
var seed: UInt32 = 987234904
var result = Int(Float(rand_r(&seed))/Float(INT32_MAX)*10)

iosSwiftrand_r()结果=4

考虑到这一点 - 是否有可用的 ios Swift|Objective-C|C++ 代码片段|库,其功能和输出与 Java 的 random() 版本?

不,这不可能(很可能),因为随机的实现甚至不需要在不同的版本和系统中保持不变,您必须实现自己的随机算法才能确定。或者您可以生成一个序列,将其保存并以某种方式将其传输到其他设备,但这要复杂得多。

查看 this link 中的示例部分,其中给出了一个算法并指出这可能对两台不同的机器有用:

static unsigned long next = 1;

/* RAND_MAX assumed to be 32767 */
int myrand(void) {
    next = next * 1103515245 + 12345;
    return((unsigned)(next/65536) % 32768);
}

void mysrand(unsigned seed) {
    next = seed;
}

您只需将其翻译成首选语言

在 iOS 9 和 OS X 10.11 中,GameplayKit provides a suite of deterministic PRNGs — one of the primary rationales being so that you can replicate a random sequence across multiple devices or between server and client for multiplayer games. (See the WWDC session 了解更多基本原理和其他有趣的东西。)

特别是,GKLinearCongruentialRandomSource 使用 Knuth 标准,因此应该与 java.util.Random 兼容(当然,当使用相同的 48 位种子初始化时)。

好的 - 这是解决方法:

我在 Apple 论坛上问了同样的问题,一个好心人 'ahltorp' 分享了一个他们一直在使用的 c 函数来做同样的事情。它 swift 兼容,我已经根据我的模拟对其进行了测试,它是数据的完美匹配!

Github C 函数的位置:https://github.com/ahltorp/swiftjavarandom

Swift 使用示例

var inseed: UInt64 = 987234904   
java_random_setseed(&inseed, inseed)  
var result = java_random_nextint_n(&inseed, 10)  
print(result) 

结果 = 0 :-)

Link到苹果论坛讨论: https://forums.developer.apple.com/thread/5791?q=Swift%20prng