Skip to content

Commit c29fcfc

Browse files
authored
GH-692: Preserve nullability information while transfering DecimalVector and Decimal256Vector (#693)
## What's Changed This PR proposes to use the "from" `ValueVector`'s field while transferring `DecimalVector` and `Decimal256Vector` to preserve nullability information. This is to have similar behavior with all the other primitive value vectors. Note that the `FieldType` of the value vector has nullability information. Closes #692 .
1 parent c57184a commit c29fcfc

File tree

4 files changed

+63
-3
lines changed

4 files changed

+63
-3
lines changed

vector/src/main/java/org/apache/arrow/vector/Decimal256Vector.java

Lines changed: 5 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -567,8 +567,11 @@ private class TransferImpl implements TransferPair {
567567

568568
public TransferImpl(String ref, BufferAllocator allocator) {
569569
to =
570-
new Decimal256Vector(
571-
ref, allocator, Decimal256Vector.this.precision, Decimal256Vector.this.scale);
570+
(Decimal256Vector.this.field != null
571+
&& Decimal256Vector.this.field.getFieldType() != null)
572+
? new Decimal256Vector(ref, Decimal256Vector.this.field.getFieldType(), allocator)
573+
: new Decimal256Vector(
574+
ref, allocator, Decimal256Vector.this.precision, Decimal256Vector.this.scale);
572575
}
573576

574577
public TransferImpl(Field field, BufferAllocator allocator) {

vector/src/main/java/org/apache/arrow/vector/DecimalVector.java

Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -565,7 +565,10 @@ private class TransferImpl implements TransferPair {
565565

566566
public TransferImpl(String ref, BufferAllocator allocator) {
567567
to =
568-
new DecimalVector(ref, allocator, DecimalVector.this.precision, DecimalVector.this.scale);
568+
(DecimalVector.this.field != null && DecimalVector.this.field.getFieldType() != null)
569+
? new DecimalVector(ref, DecimalVector.this.field.getFieldType(), allocator)
570+
: new DecimalVector(
571+
ref, allocator, DecimalVector.this.precision, DecimalVector.this.scale);
569572
}
570573

571574
public TransferImpl(Field field, BufferAllocator allocator) {

vector/src/test/java/org/apache/arrow/vector/TestDecimal256Vector.java

Lines changed: 28 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -26,6 +26,7 @@
2626
import org.apache.arrow.memory.ArrowBuf;
2727
import org.apache.arrow.memory.BufferAllocator;
2828
import org.apache.arrow.vector.types.pojo.ArrowType;
29+
import org.apache.arrow.vector.types.pojo.FieldType;
2930
import org.apache.arrow.vector.util.TransferPair;
3031
import org.junit.jupiter.api.AfterEach;
3132
import org.junit.jupiter.api.BeforeEach;
@@ -375,6 +376,33 @@ public void testGetTransferPairWithField() {
375376
assertSame(fromVector.getField(), toVector.getField());
376377
}
377378

379+
@Test
380+
public void testGetTransferPairWithoutField() {
381+
final Decimal256Vector fromVector = new Decimal256Vector("decimal", allocator, 10, scale);
382+
final TransferPair transferPair =
383+
fromVector.getTransferPair(fromVector.getField().getName(), allocator);
384+
final Decimal256Vector toVector = (Decimal256Vector) transferPair.getTo();
385+
// A new Field created inside a new vector should reuse the field type (should be the same in
386+
// memory as the original Field's field type).
387+
assertSame(fromVector.getField().getFieldType(), toVector.getField().getFieldType());
388+
}
389+
390+
@Test
391+
public void testGetTransferPairWithoutFieldNonNullable() {
392+
final FieldType decimal256NonNullableType =
393+
new FieldType(
394+
false, new ArrowType.Decimal(10, scale, Decimal256Vector.TYPE_WIDTH * 8), null);
395+
final Decimal256Vector fromVector =
396+
new Decimal256Vector("decimal", decimal256NonNullableType, allocator);
397+
final TransferPair transferPair =
398+
fromVector.getTransferPair(fromVector.getField().getName(), allocator);
399+
final Decimal256Vector toVector = (Decimal256Vector) transferPair.getTo();
400+
// A new Field created inside a new vector should reuse the field type (should be the same in
401+
// memory as the original Field's field type).
402+
assertSame(fromVector.getField().getFieldType(), toVector.getField().getFieldType());
403+
assertSame(decimal256NonNullableType, toVector.getField().getFieldType());
404+
}
405+
378406
private void verifyWritingArrowBufWithBigEndianBytes(
379407
Decimal256Vector decimalVector, ArrowBuf buf, BigDecimal[] expectedValues, int length) {
380408
decimalVector.allocateNew();

vector/src/test/java/org/apache/arrow/vector/TestDecimalVector.java

Lines changed: 26 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -26,6 +26,7 @@
2626
import org.apache.arrow.memory.ArrowBuf;
2727
import org.apache.arrow.memory.BufferAllocator;
2828
import org.apache.arrow.vector.types.pojo.ArrowType;
29+
import org.apache.arrow.vector.types.pojo.FieldType;
2930
import org.apache.arrow.vector.util.TransferPair;
3031
import org.junit.jupiter.api.AfterEach;
3132
import org.junit.jupiter.api.BeforeEach;
@@ -371,6 +372,31 @@ public void testGetTransferPairWithField() {
371372
assertSame(fromVector.getField(), toVector.getField());
372373
}
373374

375+
@Test
376+
public void testGetTransferPairWithoutField() {
377+
final DecimalVector fromVector = new DecimalVector("decimal", allocator, 10, scale);
378+
final TransferPair transferPair =
379+
fromVector.getTransferPair(fromVector.getField().getName(), allocator);
380+
final DecimalVector toVector = (DecimalVector) transferPair.getTo();
381+
// A new Field created inside a new vector should reuse the field type (should be the same in
382+
// memory as the original Field's field type).
383+
assertSame(fromVector.getField().getFieldType(), toVector.getField().getFieldType());
384+
}
385+
386+
@Test
387+
public void testGetTransferPairWithoutFieldNonNullable() {
388+
final FieldType decimalNonNullableType =
389+
new FieldType(false, new ArrowType.Decimal(10, scale), null);
390+
final DecimalVector fromVector =
391+
new DecimalVector("decimal", decimalNonNullableType, allocator);
392+
final TransferPair transferPair =
393+
fromVector.getTransferPair(fromVector.getField().getName(), allocator);
394+
final DecimalVector toVector = (DecimalVector) transferPair.getTo();
395+
// A new Field created inside a new vector should reuse the field type (should be the same in
396+
// memory as the original Field's field type).
397+
assertSame(fromVector.getField().getFieldType(), toVector.getField().getFieldType());
398+
}
399+
374400
private void verifyWritingArrowBufWithBigEndianBytes(
375401
DecimalVector decimalVector, ArrowBuf buf, BigDecimal[] expectedValues, int length) {
376402
decimalVector.allocateNew();

0 commit comments

Comments
 (0)