1// Licensed to the Apache Software Foundation (ASF) under one
2// or more contributor license agreements. See the NOTICE file
3// distributed with this work for additional information
4// regarding copyright ownership. The ASF licenses this file
5// to you under the Apache License, Version 2.0 (the
6// "License"); you may not use this file except in compliance
7// with the License. You may obtain a copy of the License at
8//
9// http://www.apache.org/licenses/LICENSE-2.0
10//
11// Unless required by applicable law or agreed to in writing,
12// software distributed under the License is distributed on an
13// "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
14// KIND, either express or implied. See the License for the
15// specific language governing permissions and limitations
16// under the License.
17
18#include "arrow/array/builder_base.h"
19
20#include <algorithm>
21#include <cstddef>
22#include <cstdint>
23#include <cstring>
24#include <sstream>
25#include <utility>
26#include <vector>
27
28#include "arrow/array.h"
29#include "arrow/buffer.h"
30#include "arrow/status.h"
31#include "arrow/type.h"
32#include "arrow/type_traits.h"
33#include "arrow/util/bit-util.h"
34#include "arrow/util/int-util.h"
35#include "arrow/util/logging.h"
36
37namespace arrow {
38
39Status ArrayBuilder::TrimBuffer(const int64_t bytes_filled, ResizableBuffer* buffer) {
40 if (buffer) {
41 if (bytes_filled < buffer->size()) {
42 // Trim buffer
43 RETURN_NOT_OK(buffer->Resize(bytes_filled));
44 }
45 // zero the padding
46 buffer->ZeroPadding();
47 } else {
48 // Null buffers are allowed in place of 0-byte buffers
49 DCHECK_EQ(bytes_filled, 0);
50 }
51 return Status::OK();
52}
53
54Status ArrayBuilder::AppendToBitmap(bool is_valid) {
55 RETURN_NOT_OK(Reserve(1));
56 UnsafeAppendToBitmap(is_valid);
57 return Status::OK();
58}
59
60Status ArrayBuilder::AppendToBitmap(const uint8_t* valid_bytes, int64_t length) {
61 RETURN_NOT_OK(Reserve(length));
62 UnsafeAppendToBitmap(valid_bytes, length);
63 return Status::OK();
64}
65
66Status ArrayBuilder::Resize(int64_t capacity) {
67 RETURN_NOT_OK(CheckCapacity(capacity, capacity_));
68 capacity_ = capacity;
69 return null_bitmap_builder_.Resize(capacity);
70}
71
72Status ArrayBuilder::Advance(int64_t elements) {
73 if (length_ + elements > capacity_) {
74 return Status::Invalid("Builder must be expanded");
75 }
76 length_ += elements;
77 return null_bitmap_builder_.Advance(elements);
78}
79
80Status ArrayBuilder::Finish(std::shared_ptr<Array>* out) {
81 std::shared_ptr<ArrayData> internal_data;
82 RETURN_NOT_OK(FinishInternal(&internal_data));
83 *out = MakeArray(internal_data);
84 return Status::OK();
85}
86
87void ArrayBuilder::Reset() {
88 capacity_ = length_ = null_count_ = 0;
89 null_bitmap_builder_.Reset();
90}
91
92Status ArrayBuilder::SetNotNull(int64_t length) {
93 RETURN_NOT_OK(Reserve(length));
94 UnsafeSetNotNull(length);
95 return Status::OK();
96}
97
98void ArrayBuilder::UnsafeAppendToBitmap(const std::vector<bool>& is_valid) {
99 for (bool element_valid : is_valid) {
100 UnsafeAppendToBitmap(element_valid);
101 }
102}
103
104void ArrayBuilder::UnsafeSetNotNull(int64_t length) {
105 length_ += length;
106 null_bitmap_builder_.UnsafeAppend(length, true);
107}
108
109} // namespace arrow
110