がレイトレース用のサンプリングとして, いい感じ.
PBRT本では, 計算の仕方は異なるが同じものなはず.
float radicalInverseVanDerCorput(unsigned bits, unsigned scramble) { bits = bitreverse(bits); bits ^= scramble; return static_cast<float>(bits) / static_cast<float>(0x100000000L); } float radicalInverseSobol(unsigned i, unsigned scramble) { for(unsigned v=1<<31; i; i>>=1, v ^= v>>1){ if(i&1){ scramble ^= v; } } return static_cast<float>(scramble) / static_cast<float>(0x100000000L); } float radicalInverseLarcherPillichshammer(unsigned i, unsigned scramble) { for(unsigned v=1<<31; i; i>>=1, v |= v>>1){ if(i&1){ scramble ^= v; } } return static_cast<float>(scramble) / static_cast<float>(0x100000000L); } void sobol02(float& v0, float& v1, unsigned i, unsigned scramble0, unsigned scramble1) { v0 = radicalInverseVanDerCorput(i, scramble0); v1 = radicalInverseSobol(i, scramble1); } void generate1D(Random& random, float* samples, int size) { unsigned scramble = random.rand(); for(int i = 0; i < size; ++i){ v[i] = radicalInverseVanDerCorput(i, scramble); } shuffle(random, samples, samples+size); } void generate2D(Random& random, Sample2D* samples, int size) { unsigned scramble2D[2] = {random.rand(), random.rand()}; for(int i = 0; i < size; ++i){ sobol02(samples[i].x_, samples[i].y_, i, scramble2D[0], scramble2D[1]); } shuffle(random, samples, samples+size); }
shuffleを入れないと, 収束しなくてはまった.
0 件のコメント:
コメントを投稿