Example #1
0
        /// <summary>
        /// Long-form of the kernel using existing comparison operation.
        /// </summary>
        static void UniqueKernel(Accelerator accelerator, long[] values)
        {
            Console.WriteLine("Unique Kernel");

            var uniqueKernel = accelerator.CreateUnique <long, ComparisonInt64>();

            using (var buffer = accelerator.Allocate1D(values))
            {
                // Allocate buffer to hold the new length.
                using var newLengthBuffer = accelerator.Allocate1D <long>(Index1D.One);

                // Allocate buffer for temporary work area.
                var tempSize = accelerator.ComputeUniqueTempStorageSize <long>(buffer.Length);
                using var tempBuffer = accelerator.Allocate1D <int>(tempSize);

                uniqueKernel(
                    accelerator.DefaultStream,
                    buffer.View,
                    newLengthBuffer.View,
                    tempBuffer.View);

                // Reads data from the GPU buffer into a new CPU array.
                // Implicitly calls accelerator.DefaultStream.Synchronize() to ensure
                // that the kernel and memory copy are completed first.
                var newLengthArray = newLengthBuffer.GetAsArray1D();
                var newLength      = newLengthArray[0];

                PrintResults(buffer.View, newLength);
            }

            Console.WriteLine();
        }
Example #2
0
        /// <summary>
        /// Creates a kernel to remove consecutive duplicate elements in a given view.
        /// </summary>
        /// <typeparam name="T">The input view element type.</typeparam>
        /// <typeparam name="TComparisonOperation">The comparison operation.</typeparam>
        /// <param name="accelerator">The accelerator.</param>
        /// <returns>The created unique handler.</returns>
        public static Unique <T> CreateUnique <T, TComparisonOperation>(
            this Accelerator accelerator)
            where T : unmanaged
            where TComparisonOperation : struct, IComparisonOperation <T>
        {
            var initializer = accelerator.CreateInitializer <int, Stride1D.Dense>();
            var kernel      = accelerator.LoadKernel <
                ArrayView <T>,
                ArrayView <long>,
                SequentialGroupExecutor,
                SpecializedValue <int>,
                Index1D>(
                UniqueKernel <T, TComparisonOperation>);

            return((stream, input, output, temp) =>
            {
                if (!input.IsValid)
                {
                    throw new ArgumentNullException(nameof(input));
                }
                if (!output.IsValid)
                {
                    throw new ArgumentNullException(nameof(output));
                }
                if (!temp.IsValid)
                {
                    throw new ArgumentNullException(nameof(temp));
                }
                if (output.Length < 1)
                {
                    throw new ArgumentOutOfRangeException(nameof(output));
                }
                if (temp.Length <
                    accelerator.ComputeUniqueTempStorageSize <T>(input.Length))
                {
                    throw new ArgumentOutOfRangeException(nameof(temp));
                }
                if (input.Length > int.MaxValue)
                {
                    throw new NotSupportedException(
                        ErrorMessages.NotSupportedArrayView64);
                }

                var viewManager = new TempViewManager(temp, nameof(temp));
                var executorView = viewManager.Allocate <int>();
                initializer(stream, temp.SubView(0, viewManager.NumInts), default);

                var(gridDim, groupDim) = accelerator.ComputeGridStrideLoopExtent(
                    input.IntLength,
                    out int numIterationsPerGroup);
                kernel(
                    stream,
                    (gridDim, groupDim),
                    input,
                    output,
                    new SequentialGroupExecutor(executorView),
                    new SpecializedValue <int>(groupDim * numIterationsPerGroup),
                    numIterationsPerGroup);
            });
        }
Example #3
0
 /// <summary>
 /// Removes consecutive duplicate elements in a supplied input view.
 /// </summary>
 /// <typeparam name="T">The input view element type.</typeparam>
 /// <typeparam name="TComparisonOperation">The comparison operation.</typeparam>
 /// <param name="accelerator">The accelerator.</param>
 /// <param name="stream">The accelerator stream.</param>
 /// <param name="input">The input view.</param>
 /// <returns>The new/valid length of the input view.</returns>
 public static long Unique <T, TComparisonOperation>(
     this Accelerator accelerator,
     AcceleratorStream stream,
     ArrayView <T> input)
     where T : unmanaged
     where TComparisonOperation : struct, IComparisonOperation <T>
 {
     using var output = accelerator.Allocate1D <long>(1);
     using var temp   = accelerator.Allocate1D <int>(
               accelerator.ComputeUniqueTempStorageSize <T>(input.Length));
     accelerator.CreateUnique <T, TComparisonOperation>()(
         stream,
         input,
         output.View,
         temp.View);
     output.View.CopyToCPU(stream, out long result, 1);
     return(result);
 }