Abhilash437 commented on code in PR #408: URL: https://github.com/apache/arrow-dotnet/pull/408#discussion_r3776764129
########## src/Apache.Arrow/Arrays/RunEndEncodedArray.Builder.cs: ########## @@ -0,0 +1,400 @@ +// Licensed to the Apache Software Foundation (ASF) under one or more +// contributor license agreements. See the NOTICE file distributed with +// this work for additional information regarding copyright ownership. +// The ASF licenses this file to You under the Apache License, Version 2.0 +// (the "License"); you may not use this file except in compliance with +// the License. You may obtain a copy of the License at +// +// http://www.apache.org/licenses/LICENSE-2.0 +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. + +using System; +using System.Collections.Generic; +using Apache.Arrow.Memory; + +namespace Apache.Arrow; + +public partial class RunEndEncodedArray +{ + /// <summary> + /// Builder for <see cref="RunEndEncodedArray"/>. + /// </summary> + /// <typeparam name="TRunEndBuilder">The type of the run ends array builder.</typeparam> + /// <typeparam name="TValueBuilder">The type of the values array builder.</typeparam> + /// <typeparam name="TRunEndArray">The type of the run ends array (must be Int16Array, Int32Array, or Int64Array).</typeparam> + /// <typeparam name="TValueArray">The type of the values array.</typeparam> + /// <typeparam name="TValue">The type of values contained in the values array.</typeparam> + public class Builder<TRunEndBuilder, TValueBuilder, TRunEndArray, TValueArray, TValue> + : IArrowArrayBuilder<TValue, RunEndEncodedArray, Builder<TRunEndBuilder, TValueBuilder, TRunEndArray, TValueArray, TValue>> + where TRunEndBuilder : IArrowArrayBuilder<TRunEndArray> + where TValueBuilder : IArrowArrayBuilder<TValueArray> + where TRunEndArray : IArrowArray + where TValueArray : IArrowArray + { + private readonly IEqualityComparer<TValue> _comparer; + private int _currentRunLength; + private TValue _lastValue; + private bool _lastValueIsNull; + private bool _hasValue; + + /// <summary> + /// Gets the run ends builder. + /// </summary> + public TRunEndBuilder RunEndsBuilder { get; } + + /// <summary> + /// Gets the values builder. + /// </summary> + public TValueBuilder ValuesBuilder { get; } + + /// <summary> + /// Gets the total logical length of elements appended to this builder. + /// </summary> + public int Length => _currentRunLength; + + /// <summary> + /// Initializes a new instance of the <see cref="Builder{TRunEndBuilder, TValueBuilder, TRunEndArray, TValueArray, TValue}"/> class. + /// </summary> + /// <param name="runEndsBuilder">The builder to use for run-ends.</param> + /// <param name="valuesBuilder">The builder to use for values.</param> + /// <param name="comparer">Optional equality comparer for value run-length grouping.</param> + public Builder(TRunEndBuilder runEndsBuilder, TValueBuilder valuesBuilder, IEqualityComparer<TValue> comparer = null) + { + RunEndsBuilder = runEndsBuilder ?? throw new ArgumentNullException(nameof(runEndsBuilder)); + ValuesBuilder = valuesBuilder ?? throw new ArgumentNullException(nameof(valuesBuilder)); + _comparer = comparer ?? EqualityComparer<TValue>.Default; + } + + /// <summary> + /// Appends a single value to the builder, automatically grouping identical consecutive values into runs. + /// </summary> + /// <param name="value">The value to append.</param> + /// <returns>The builder instance for method chaining.</returns> + public Builder<TRunEndBuilder, TValueBuilder, TRunEndArray, TValueArray, TValue> Append(TValue value) + { + if (value is null) + { + return AppendNull(); + } + + if (_hasValue) + { + if (!_lastValueIsNull && _comparer.Equals(value, _lastValue)) + { + _currentRunLength++; + } + else + { + FlushCurrentRun(); + StartNewRun(value, isNull: false); + } + } + else + { + StartNewRun(value, isNull: false); + } + + return this; + } + + /// <summary> + /// Appends a null value to the builder. + /// </summary> + /// <returns>The builder instance for method chaining.</returns> + public Builder<TRunEndBuilder, TValueBuilder, TRunEndArray, TValueArray, TValue> AppendNull() + { + if (_hasValue) + { + if (_lastValueIsNull) + { + _currentRunLength++; + } + else + { + FlushCurrentRun(); + StartNewRun(default, isNull: true); + } + } + else + { + StartNewRun(default, isNull: true); + } + + return this; + } + + /// <summary> + /// Appends a span of values to the builder. + /// </summary> + /// <param name="span">The span of values to append.</param> + /// <returns>The builder instance for method chaining.</returns> + public Builder<TRunEndBuilder, TValueBuilder, TRunEndArray, TValueArray, TValue> Append(ReadOnlySpan<TValue> span) + { + foreach (TValue value in span) + { + Append(value); + } + return this; + } + + /// <summary> + /// Appends a sequence of values to the builder. + /// </summary> + /// <param name="values">The sequence of values to append.</param> + /// <returns>The builder instance for method chaining.</returns> + public Builder<TRunEndBuilder, TValueBuilder, TRunEndArray, TValueArray, TValue> AppendRange(IEnumerable<TValue> values) + { + if (values == null) + { + throw new ArgumentNullException(nameof(values)); + } + + foreach (TValue value in values) + { + Append(value); + } + return this; + } + + /// <summary> + /// Reserves capacity in the inner builders. + /// </summary> + /// <param name="capacity">The capacity to reserve.</param> + /// <returns>The builder instance for method chaining.</returns> + public Builder<TRunEndBuilder, TValueBuilder, TRunEndArray, TValueArray, TValue> Reserve(int capacity) + { + return this; + } Review Comment: `Reserve(capacity)` now validates input and throws an `ArgumentOutOfRangeException` when `capacity < 0`. Capacity reservation is delegated to both inner builders (`RunEndsBuilder` and `ValuesBuilder`) via a new `ReserveBuilder` helper method. -- This is an automated message from the Apache Git Service. To respond to the message, please log on to GitHub and use the URL above to go to the specific comment. To unsubscribe, e-mail: [email protected] For queries about this service, please contact Infrastructure at: [email protected]
