Uh oh!
There was an error while loading. Please reload this page.
- Notifications
You must be signed in to change notification settings - Fork 4.3k
PARQUET-490: [C++][Parquet] Basic support for reading DELTA_BINARY_PACKED data#10627
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Closed
Uh oh!
There was an error while loading. Please reload this page.
Closed
Changes from all commits
Commits
Show all changes
9 commits
Select commit
Hold shift + click to select a range
cf4a51f
ARROW-13206: [C++][Parquet] Basic support for encoding DELTA_BINARY_P…
69fbac2
Support for int64 data of DELTA_BINARY_PACKED encoding when delta_bit…
06ae900
Update LICENSE.txt and add script to generate bpacking64_default.h
shanhuuang b12024b
Update LICENSE.txt and test case
shanhuuang 510b9d4
do not call InitBlock() if there is only one record
shanhuuang 4251e2f
Modify the code and test case according to reviews.
shanhuuang cc5942c
Modify test case and change the limitation of values_per_mini_block_ …
shanhuuang bff315d
Add JIRA issue number to TODO
pitrou 932c281
Fix lint failure
pitrou File filter
Filter by extension
Conversations
Failed to load comments.
Loading
Uh oh!
There was an error while loading. Please reload this page.
Jump to
Jump to file
Failed to load files.
Loading
Uh oh!
There was an error while loading. Please reload this page.
Diff view
Diff view
There are no files selected for viewing
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -20,6 +20,7 @@ | ||
| #pragma once | ||
| #include <string.h> | ||
| #include <algorithm> | ||
| #include <cstdint> | ||
| @@ -77,6 +78,15 @@ class BitWriter { | ||
| // Writes an int zigzag encoded. | ||
| bool PutZigZagVlqInt(int32_t v); | ||
| /// Write a Vlq encoded int64 to the buffer. Returns false if there was not enough | ||
| /// room. The value is written byte aligned. | ||
| /// For more details on vlq: | ||
| /// en.wikipedia.org/wiki/Variable-length_quantity | ||
| bool PutVlqInt(uint64_t v); | ||
| // Writes an int64 zigzag encoded. | ||
| bool PutZigZagVlqInt(int64_t v); | ||
| /// Get a pointer to the next aligned byte and advance the underlying buffer | ||
| /// by num_bytes. | ||
| /// Returns NULL if there was not enough space. | ||
| @@ -155,6 +165,14 @@ class BitReader { | ||
| // Reads a zigzag encoded int `into` v. | ||
| bool GetZigZagVlqInt(int32_t* v); | ||
| /// Reads a vlq encoded int64 from the stream. The encoded int must start at | ||
| /// the beginning of a byte. Return false if there were not enough bytes in | ||
| /// the buffer. | ||
| bool GetVlqInt(uint64_t* v); | ||
| // Reads a zigzag encoded int64 `into` v. | ||
| bool GetZigZagVlqInt(int64_t* v); | ||
| /// Returns the number of bytes left in the stream, not including the current | ||
| /// byte (i.e., there may be an additional fraction of a byte). | ||
| int bytes_left() { | ||
| @@ -165,6 +183,9 @@ class BitReader { | ||
| /// Maximum byte length of a vlq encoded int | ||
| static constexpr int kMaxVlqByteLength = 5; | ||
| /// Maximum byte length of a vlq encoded int64 | ||
| static constexpr int kMaxVlqByteLengthForInt64 = 10; | ||
| private: | ||
| const uint8_t* buffer_; | ||
| int max_bytes_; | ||
| @@ -263,8 +284,13 @@ inline void GetValue_(int num_bits, T* v, int max_bytes, const uint8_t* buffer, | ||
| #pragma warning(disable : 4800 4805) | ||
| #endif | ||
| // Read bits of v that crossed into new buffered_values_ | ||
| *v = *v | static_cast<T>(BitUtil::TrailingBits(*buffered_values, *bit_offset) | ||
| << (num_bits - *bit_offset)); | ||
| if (ARROW_PREDICT_TRUE(num_bits - *bit_offset < static_cast<int>(8 * sizeof(T)))) { | ||
| // if shift exponent(num_bits - *bit_offset) is not less than sizeof(T), *v will not | ||
| // change and the following code may cause a runtime error that the shift exponent | ||
| // is too large | ||
| *v = *v | static_cast<T>(BitUtil::TrailingBits(*buffered_values, *bit_offset) | ||
| << (num_bits - *bit_offset)); | ||
| } | ||
| #ifdef _MSC_VER | ||
| #pragma warning(pop) | ||
| #endif | ||
| @@ -282,8 +308,6 @@ inline bool BitReader::GetValue(int num_bits, T* v) { | ||
| template <typename T> | ||
| inline int BitReader::GetBatch(int num_bits, T* v, int batch_size) { | ||
| DCHECK(buffer_ != NULL); | ||
| // TODO: revisit this limit if necessary | ||
| DCHECK_LE(num_bits, 32); | ||
| DCHECK_LE(num_bits, static_cast<int>(sizeof(T) * 8)); | ||
| int bit_offset = bit_offset_; | ||
| @@ -313,7 +337,18 @@ inline int BitReader::GetBatch(int num_bits, T* v, int batch_size) { | ||
| reinterpret_cast<uint32_t*>(v + i), batch_size - i, num_bits); | ||
| i += num_unpacked; | ||
| byte_offset += num_unpacked * num_bits / 8; | ||
| } else if (sizeof(T) == 8 && num_bits > 32) { | ||
| // Use unpack64 only if num_bits is larger than 32 | ||
| // TODO (ARROW-13677): improve the performance of internal::unpack64 | ||
| // and remove the restriction of num_bits | ||
| int num_unpacked = | ||
| internal::unpack64(buffer + byte_offset, reinterpret_cast<uint64_t*>(v + i), | ||
| batch_size - i, num_bits); | ||
| i += num_unpacked; | ||
| byte_offset += num_unpacked * num_bits / 8; | ||
| } else { | ||
| // TODO: revisit this limit if necessary | ||
| DCHECK_LE(num_bits, 32); | ||
| const int buffer_size = 1024; | ||
| uint32_t unpack_buffer[buffer_size]; | ||
| while (i < batch_size) { | ||
| @@ -418,14 +453,59 @@ inline bool BitReader::GetVlqInt(uint32_t* v) { | ||
| } | ||
| inline bool BitWriter::PutZigZagVlqInt(int32_t v) { | ||
| auto u_v = ::arrow::util::SafeCopy<uint32_t>(v); | ||
| return PutVlqInt((u_v << 1) ^ (u_v >> 31)); | ||
| uint32_t u_v = ::arrow::util::SafeCopy<uint32_t>(v); | ||
| u_v = (u_v << 1) ^ static_cast<uint32_t>(v >> 31); | ||
| return PutVlqInt(u_v); | ||
| } | ||
| inline bool BitReader::GetZigZagVlqInt(int32_t* v) { | ||
| uint32_t u; | ||
| if (!GetVlqInt(&u)) return false; | ||
| *v = ::arrow::util::SafeCopy<int32_t>((u >> 1) ^ (u << 31)); | ||
| u = (u >> 1) ^ (~(u & 1) + 1); | ||
| *v = ::arrow::util::SafeCopy<int32_t>(u); | ||
shanhuuang marked this conversation as resolved.
Uh oh!There was an error while loading. Please reload this page. | ||
| return true; | ||
| } | ||
| inline bool BitWriter::PutVlqInt(uint64_t v) { | ||
| bool result = true; | ||
| while ((v & 0xFFFFFFFFFFFFFF80ULL) != 0ULL) { | ||
| result &= PutAligned<uint8_t>(static_cast<uint8_t>((v & 0x7F) | 0x80), 1); | ||
shanhuuang marked this conversation as resolved.
Uh oh!There was an error while loading. Please reload this page. | ||
| v >>= 7; | ||
| } | ||
| result &= PutAligned<uint8_t>(static_cast<uint8_t>(v & 0x7F), 1); | ||
| return result; | ||
| } | ||
| inline bool BitReader::GetVlqInt(uint64_t* v) { | ||
| uint64_t tmp = 0; | ||
| for (int i = 0; i < kMaxVlqByteLengthForInt64; i++) { | ||
| uint8_t byte = 0; | ||
| if (ARROW_PREDICT_FALSE(!GetAligned<uint8_t>(1, &byte))) { | ||
| return false; | ||
| } | ||
| tmp |= static_cast<uint64_t>(byte & 0x7F) << (7 * i); | ||
| if ((byte & 0x80) == 0) { | ||
| *v = tmp; | ||
| return true; | ||
| } | ||
| } | ||
| return false; | ||
| } | ||
| inline bool BitWriter::PutZigZagVlqInt(int64_t v) { | ||
| uint64_t u_v = ::arrow::util::SafeCopy<uint64_t>(v); | ||
| u_v = (u_v << 1) ^ static_cast<uint64_t>(v >> 63); | ||
| return PutVlqInt(u_v); | ||
| } | ||
| inline bool BitReader::GetZigZagVlqInt(int64_t* v) { | ||
| uint64_t u; | ||
| if (!GetVlqInt(&u)) return false; | ||
| u = (u >> 1) ^ (~(u & 1) + 1); | ||
| *v = ::arrow::util::SafeCopy<int64_t>(u); | ||
| return true; | ||
| } | ||
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Oops, something went wrong.
Uh oh!
There was an error while loading. Please reload this page.
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Uh oh!
There was an error while loading. Please reload this page.