C++ Metal-线程本地的命名空间变量?

C++ Metal-线程本地的命名空间变量?,c++,random,gpu,gpgpu,metal,C++,Random,Gpu,Gpgpu,Metal,我试图在金属中创建一个伪随机数生成器(PRNG),类似于推力的RNG,每次调用线程中的RNG时,它都会生成一个不同的随机数,给定一个特定的种子,在这种情况下,它将是网格中的线程位置。我把它设置得很好,现在我用我的代码得到了一张很好的均匀随机图片 但是,我的代码每个线程只工作一次。我想实现一个next\u rng()函数,该函数使用最后一个结果作为种子返回一个新的rng。然而,我在存储最后一个结果时遇到了问题,因为我的RNG是一个名称空间,并且我只能将最后一个结果存储在常量地址空间中,地址空间是不

我试图在金属中创建一个伪随机数生成器(PRNG),类似于
推力
的RNG,每次调用线程中的RNG时,它都会生成一个不同的随机数,给定一个特定的种子,在这种情况下,它将是网格中的
线程位置。我把它设置得很好,现在我用我的代码得到了一张很好的均匀随机图片

但是,我的代码每个线程只工作一次。我想实现一个
next\u rng()
函数,该函数使用最后一个结果作为种子返回一个新的
rng
。然而,我在存储最后一个结果时遇到了问题,因为我的RNG是一个名称空间,并且我只能将最后一个结果存储在
常量
地址空间中,地址空间是不可更新的。有没有办法绕过这个问题/重组我的代码以避免这个问题

我能在网上找到的最好的帮助是,不幸的是,它对我不起作用,因为我不能像在解决方案中那样在函数中声明一个静态变量

如果有帮助,我愿意以任何方式重新构造代码。我可以把它变成一个静态类或类或其他什么吗?没有线索,但我只想要一个PRNG

我的代码(简化)基本上与那篇文章的结构相同:

namespace metal_rng {

    thread unsigned* last_seed() {
        thread uint last_seed = 1; // Doesn't work because last-seed falls out of scope after the function quits

        // The following comment line doesn't even compile:
        // thread static uint last_seed = 1;

        return &last_seed;
    }

    unsigned TausStep(const unsigned z, const int s1, const int s2, const int s3, const unsigned M)
    {
        unsigned b=(((z << s1) ^ z) >> s2);
        return (((z & M) << s3) ^ b);
    }

    device float rng(const int initial_seed) {
        int seed = initial_seed * 1099087573UL;

        unsigned hashed = (1664525*(*last_seed()) + 1013904223UL);
        *last_seed() = hashed
        return (hashed) * 2.3283064365387e-10;
    }

    device float next_rng() {
          if (*last_seed() == 0) {
              return 0.0;
          } else {
              unsigned hashed = (1664525*(*last_seed()) + 1013904223UL);
              return (hashed) * 2.3283064365387e-10;
          }
    }
}
namespace metal\u rng{
线程未签名*last_seed(){
线程uint last_seed=1;//不工作,因为在函数退出后,最后一个种子不在作用域内
//以下注释行甚至没有编译:
//线程静态uint last_seed=1;
返回和最后一个种子;
}
无符号TausStep(常数无符号z、常数整数s1、常数整数s2、常数整数s3、常数无符号M)
{
无符号b=((z>s2);

返回(((z&M)我最终使用了@KenThomases的建议,我只是为RNG创建了一个类。我打包了代码并调用了RNG
Loki
。如果将来有人想使用它。

我最终使用了@KenThomases的建议,我只是为RNG创建了一个类。如果有人想,我打包了代码并调用了RNG
Loki
s将来使用它。

此RNG代码的客户端代码是什么样子的?您可能应该创建一个类来表示RNG,其中函数作为成员函数和状态(最后一个种子)作为成员变量。您可以在调用代码中将该类的实例创建为本地实例,并使用初始种子进行初始化。如果您需要在多个函数中使用它,则必须传递对该实例的引用,这很烦人,但可行。我正在将其用于monte carlo路径跟踪器。您的建议奏效了!我正在处理中将代码打包到一个整洁的框架中供任何人使用是非常困难的。我将在完成后立即共享一个指向回购协议的链接!非常感谢(:。还有关于如何在回购协议中为任何未来漫游者使用RNG的说明。此RNG代码的客户端代码是什么样子的?您可能应该创建一个类来表示RNG,其中函数为成员函数和状态(最后一个种子)作为成员变量。您可以在调用代码中将该类的实例创建为本地实例,并使用初始种子进行初始化。如果您需要在多个函数中使用它,则必须传递对该实例的引用,这很烦人,但可行。我正在将其用于monte carlo路径跟踪器。您的建议奏效了!我正在处理中将代码打包成一个整洁的框架供任何人使用。我将在完成后立即共享到repo的链接!非常感谢(:。还有关于如何在repo中为任何未来的漫游者使用RNG的说明。