Add Vector3<TLane, TNumber>

This commit is contained in:
2026-02-13 12:51:22 +09:00
parent f9cb909841
commit 75d33d0763
14 changed files with 1376 additions and 705 deletions

View File

@@ -17,6 +17,9 @@ public class MathematicsBenchmark
private float4 _fa = new float4(1, 2, 1, 2);
private float4 _fb = new float4(3, 4, 3, 4);
private Vector64<float> _va64 = Vector64.Create(1f, 2f);
private Vector64<float> _vb64 = Vector64.Create(3f, 4f);
[Benchmark]
public Vector4 VectorAdd()
{
@@ -28,7 +31,7 @@ public class MathematicsBenchmark
return _va;
}
[Benchmark]
//[Benchmark]
public float4 floatAdd()
{
for (var i = 0; i < 10; i++)
@@ -38,6 +41,17 @@ public class MathematicsBenchmark
return _fa;
}
[Benchmark]
public Vector64<float> Vector64Add()
{
for (var i = 0; i < 10; i++)
{
_va64 += _vb64;
}
return _va64;
}
#endif
#if FMA_BENCHMARK

View File

@@ -1,4 +1,5 @@
using Misaki.HighPerformance.Jobs;
using Misaki.HighPerformance.LowLevel.Utilities;
using Misaki.HighPerformance.Mathematics;
using Misaki.HighPerformance.Mathematics.SPMD;
using System.Numerics;
@@ -60,8 +61,7 @@ internal unsafe struct NoiseJobMath : IJobParallelFor
private static float2 GradientNoiseDirect(float2 uv)
{
uv.x %= 289;
uv.y %= 289;
uv %= 289;
var x = (34 * uv.x + 1) * uv.x % 289 + uv.y;
x = (34 * x + 1) * x % 289;
x = math.frac(x / 41) * 2 - 1;
@@ -261,7 +261,7 @@ internal unsafe struct NoiseJobMathSPMD : IJobSPMD<float>
var uvX = (indices % w) / w;
var uvY = TLane.Floor(indices / w) / h;
var result = Noise(uvX, uvY);
result.Store(buffers + baseIndex);
}

View File

@@ -1,2 +1 @@
BenchmarkDotNet.Running.BenchmarkRunner.Run<Misaki.HighPerformance.Test.Benchmark.SPMDBenchmark>();
return;
BenchmarkDotNet.Running.BenchmarkRunner.Run<Misaki.HighPerformance.Test.Benchmark.MathematicsBenchmark>();

View File

@@ -39,7 +39,7 @@ public static class CompressStoreTest
private unsafe static void TestPattern_Double(double[] input, bool[] keepPattern)
{
// 1. Setup Input Vector
// Handle case where Vector<T> is smaller than 8 (e.g. 2 or 4)
// Handle case where Vector<TLane> is smaller than 8 (e.g. 2 or 4)
var vecSize = Vector<double>.Count;
var safeInput = new double[vecSize];
var safeMaskVal = new double[vecSize];

View File

@@ -0,0 +1,60 @@
using Misaki.HighPerformance.Mathematics;
using Misaki.HighPerformance.Mathematics.SPMD;
using System.Runtime.InteropServices;
namespace Misaki.HighPerformance.Test.UnitTest.Jobs;
internal unsafe struct DotProductJob : IJobSPMD<float>
{
public float3* arrayA; // source array 1
public float3* arrayB; // source array 2
public float* results; // output array (dot products)
public readonly void Execute<TLane>(int baseIndex, int threadIndex)
where TLane : ISPMD<TLane, float>
{
var vecA = MathV.LoadVector3<TLane, float>((float*)(arrayA + baseIndex));
var vecB = MathV.LoadVector3<TLane, float>((float*)(arrayB + baseIndex));
var dotResult = MathV.Dot(vecA, vecB);
dotResult.Store(results + baseIndex);
}
}
[TestClass]
public class SPMDTest
{
[TestMethod]
public unsafe void TestSPMDVectorDot()
{
const int count = 1000;
var arrayA = (float3*)NativeMemory.Alloc((nuint)(sizeof(float3) * count));
var arrayB = (float3*)NativeMemory.Alloc((nuint)(sizeof(float3) * count));
var results = (float*)NativeMemory.Alloc(sizeof(float) * count);
for (var i = 0; i < count; i++)
{
arrayA[i] = new float3(i, i + 1, i + 2);
arrayB[i] = new float3(1, 2, 3);
}
var job = new DotProductJob
{
arrayA = arrayA,
arrayB = arrayB,
results = results
};
job.Run<DotProductJob, float>(count, -1);
// Verify first result: dot([0,1,2], [1,2,3]) = 0*1 + 1*2 + 2*3 = 8
Assert.AreEqual(8.0f, results[0], 0.001f);
// Verify last result: dot([999,1000,1001], [1,2,3]) = 999*1 + 1000*2 + 1001*3 = 6002
Assert.AreEqual(6002.0f, results[count - 1], 0.001f);
NativeMemory.Free(arrayA);
NativeMemory.Free(arrayB);
NativeMemory.Free(results);
}
}