From 06be8db7237f81068f87c2e51e43a90f1322ad25 Mon Sep 17 00:00:00 2001 From: Adam Reeve Date: Fri, 19 Apr 2024 14:41:56 +1200 Subject: [PATCH] GH-41302: [C#][Integration] Fix writing list and binary arrays with zero length offsets to IPC format (#41303) ### Rationale for this change Fixes the integration test failures caused by #41230 ### What changes are included in this PR? Only try to access the offset values if the array length is non-zero when writing list and binary arrays to IPC format. ### Are these changes tested? Yes, I've manually run the integration tests with C# and Java to verify they pass (when also including the changes from #41264), and also added new unit tests for this. ### Are there any user-facing changes? This may also be a bug that affects users but it isn't in a released version. * GitHub Issue: #41302 Authored-by: Adam Reeve Signed-off-by: Curt Hagenlocher --- .../src/Apache.Arrow/Ipc/ArrowStreamWriter.cs | 18 ++++++++++++++---- .../Apache.Arrow.Tests/ArrowFileWriterTests.cs | 12 ------------ 2 files changed, 14 insertions(+), 16 deletions(-) diff --git a/csharp/src/Apache.Arrow/Ipc/ArrowStreamWriter.cs b/csharp/src/Apache.Arrow/Ipc/ArrowStreamWriter.cs index 1b83735925556..a7e4c13525236 100644 --- a/csharp/src/Apache.Arrow/Ipc/ArrowStreamWriter.cs +++ b/csharp/src/Apache.Arrow/Ipc/ArrowStreamWriter.cs @@ -165,8 +165,13 @@ public void Visit(ListArray array) _buffers.Add(CreateBitmapBuffer(array.NullBitmapBuffer, array.Offset, array.Length)); _buffers.Add(CreateBuffer(GetZeroBasedValueOffsets(array.ValueOffsetsBuffer, array.Offset, array.Length))); - int valuesOffset = array.ValueOffsets[0]; - int valuesLength = array.ValueOffsets[array.Length] - valuesOffset; + int valuesOffset = 0; + int valuesLength = 0; + if (array.Length > 0) + { + valuesOffset = array.ValueOffsets[0]; + valuesLength = array.ValueOffsets[array.Length] - valuesOffset; + } var values = array.Values; if (valuesOffset > 0 || valuesLength < values.Length) @@ -206,8 +211,13 @@ public void Visit(BinaryArray array) _buffers.Add(CreateBitmapBuffer(array.NullBitmapBuffer, array.Offset, array.Length)); _buffers.Add(CreateBuffer(GetZeroBasedValueOffsets(array.ValueOffsetsBuffer, array.Offset, array.Length))); - int valuesOffset = array.ValueOffsets[0]; - int valuesLength = array.ValueOffsets[array.Length] - valuesOffset; + int valuesOffset = 0; + int valuesLength = 0; + if (array.Length > 0) + { + valuesOffset = array.ValueOffsets[0]; + valuesLength = array.ValueOffsets[array.Length] - valuesOffset; + } _buffers.Add(CreateSlicedBuffer(array.ValueBuffer, valuesOffset, valuesLength)); } diff --git a/csharp/test/Apache.Arrow.Tests/ArrowFileWriterTests.cs b/csharp/test/Apache.Arrow.Tests/ArrowFileWriterTests.cs index 449760364364c..297cb5e181cd3 100644 --- a/csharp/test/Apache.Arrow.Tests/ArrowFileWriterTests.cs +++ b/csharp/test/Apache.Arrow.Tests/ArrowFileWriterTests.cs @@ -245,17 +245,5 @@ public async Task WriteListArrayWithEmptyOffsets() await ValidateRecordBatchFile(stream, recordBatch, strictCompare: false); } - - private static void Shuffle(int[] values, Random random) - { - var length = values.Length; - for (int i = 0; i < length - 1; ++i) - { - var j = random.Next(i, length); - var tmp = values[i]; - values[i] = values[j]; - values[j] = tmp; - } - } } }