1212
1313namespace Microsoft . Data . Analysis
1414{
15+ internal static class BitmapHelper
16+ {
17+ // Faster to use when we already have a span since it avoids indexing
18+ public static bool IsValid ( ReadOnlySpan < byte > bitMapBufferSpan , int index )
19+ {
20+ int nullBitMapSpanIndex = index / 8 ;
21+ byte thisBitMap = bitMapBufferSpan [ nullBitMapSpanIndex ] ;
22+ return IsBitSet ( thisBitMap , index ) ;
23+ }
24+
25+ public static bool IsBitSet ( byte curBitMap , int index )
26+ {
27+ return ( ( curBitMap >> ( index & 7 ) ) & 1 ) != 0 ;
28+ }
29+ }
30+
1531 /// <summary>
16- /// PrimitiveDataFrameColumnContainer is just a store for the column data. APIs that want to change the data must be defined in PrimitiveDataFrameColumn
32+ /// PrimitiveColumnContainer is just a store for the column data. APIs that want to change the data must be defined in PrimitiveDataFrameColumn
1733 /// </summary>
1834 /// <typeparam name="T"></typeparam>
1935 internal partial class PrimitiveColumnContainer < T > : IEnumerable < T ? >
@@ -223,7 +239,7 @@ public void ApplyElementwise(Func<T?, long, T?> func)
223239 for ( int i = 0 ; i < mutableBuffer . Length ; i ++ )
224240 {
225241 long curIndex = i + prevLength ;
226- bool isValid = IsValid ( mutableNullBitMapBuffer , i ) ;
242+ bool isValid = BitmapHelper . IsValid ( mutableNullBitMapBuffer , i ) ;
227243 T ? value = func ( isValid ? mutableBuffer [ i ] : null , curIndex ) ;
228244 mutableBuffer [ i ] = value . GetValueOrDefault ( ) ;
229245 SetValidityBit ( mutableNullBitMapBuffer , i , value != null ) ;
@@ -246,22 +262,14 @@ public void Apply<TResult>(Func<T?, TResult?> func, PrimitiveColumnContainer<TRe
246262
247263 for ( int i = 0 ; i < sourceBuffer . Length ; i ++ )
248264 {
249- bool isValid = IsValid ( sourceNullBitMap , i ) ;
265+ bool isValid = BitmapHelper . IsValid ( sourceNullBitMap , i ) ;
250266 TResult ? value = func ( isValid ? sourceBuffer [ i ] : null ) ;
251267 mutableResultBuffer [ i ] = value . GetValueOrDefault ( ) ;
252268 resultContainer . SetValidityBit ( mutableResultNullBitMapBuffers , i , value != null ) ;
253269 }
254270 }
255271 }
256272
257- // Faster to use when we already have a span since it avoids indexing
258- public bool IsValid ( ReadOnlySpan < byte > bitMapBufferSpan , int index )
259- {
260- int nullBitMapSpanIndex = index / 8 ;
261- byte thisBitMap = bitMapBufferSpan [ nullBitMapSpanIndex ] ;
262- return IsBitSet ( thisBitMap , index ) ;
263- }
264-
265273 public bool IsValid ( long index ) => NullCount == 0 || GetValidityBit ( index ) ;
266274
267275 private byte SetBit ( byte curBitMap , int index , bool value )
@@ -329,11 +337,6 @@ internal void SetValidityBit(long index, bool value)
329337 SetValidityBit ( bitMapBuffer . Span , ( int ) index , value ) ;
330338 }
331339
332- private bool IsBitSet ( byte curBitMap , int index )
333- {
334- return ( ( curBitMap >> ( index & 7 ) ) & 1 ) != 0 ;
335- }
336-
337340 private bool GetValidityBit ( long index )
338341 {
339342 if ( ( uint ) index >= Length )
@@ -350,7 +353,7 @@ private bool GetValidityBit(long index)
350353 int bitMapBufferIndex = ( int ) ( ( uint ) index / 8 ) ;
351354 Debug . Assert ( bitMapBuffer . Length > bitMapBufferIndex ) ;
352355 byte curBitMap = bitMapBuffer [ bitMapBufferIndex ] ;
353- return IsBitSet ( curBitMap , ( int ) index ) ;
356+ return BitmapHelper . IsBitSet ( curBitMap , ( int ) index ) ;
354357 }
355358
356359 public long Length ;
@@ -524,7 +527,7 @@ public PrimitiveColumnContainer<T> Clone<U>(PrimitiveColumnContainer<U> mapIndic
524527 spanIndex = buffer . Length - 1 - i ;
525528
526529 long mapRowIndex = mapIndicesIntSpan . IsEmpty ? mapIndicesLongSpan [ spanIndex ] : mapIndicesIntSpan [ spanIndex ] ;
527- bool mapRowIndexIsValid = mapIndices . IsValid ( mapIndicesNullBitMapSpan , spanIndex ) ;
530+ bool mapRowIndexIsValid = BitmapHelper . IsValid ( mapIndicesNullBitMapSpan , spanIndex ) ;
528531 if ( mapRowIndexIsValid && ( mapRowIndex < minRange || mapRowIndex >= maxRange ) )
529532 {
530533 int bufferIndex = ( int ) ( mapRowIndex / maxCapacity ) ;
@@ -539,7 +542,7 @@ public PrimitiveColumnContainer<T> Clone<U>(PrimitiveColumnContainer<U> mapIndic
539542 {
540543 mapRowIndex -= minRange ;
541544 value = thisSpan [ ( int ) mapRowIndex ] ;
542- isValid = IsValid ( thisNullBitMapSpan , ( int ) mapRowIndex ) ;
545+ isValid = BitmapHelper . IsValid ( thisNullBitMapSpan , ( int ) mapRowIndex ) ;
543546 }
544547
545548 retSpan [ i ] = isValid ? value : default ;
0 commit comments