MCPcopy Create free account
hub / github.com/apache/arrow / FromProto

Function FromProto

cpp/src/arrow/engine/substrait/expression_internal.cc:137–206  ·  view source on GitHub ↗

Source from the content-addressed store, hash-verified

135}
136
137Result<compute::Expression> FromProto(const substrait::Expression::ReferenceSegment* ref,
138 const ExtensionSet& ext_set,
139 const ConversionOptions& conversion_options,
140 std::optional<compute::Expression> in_expr) {
141 auto in_ref = ref;
142 auto& current = in_expr;
143 while (ref != nullptr) {
144 switch (ref->reference_type_case()) {
145 case substrait::Expression::ReferenceSegment::kStructField: {
146 auto index = ref->struct_field().field();
147 if (!current) {
148 // Root StructField (column selection)
149 current = compute::field_ref(FieldRef(index));
150 } else if (auto current_ref = current->field_ref()) {
151 // Nested StructFields on the root (selection of struct-typed column
152 // combined with selecting struct fields)
153 current = compute::field_ref(FieldRef(*current_ref, index));
154 } else if (current->call() && current->call()->function_name == "struct_field") {
155 // Nested StructFields on top of an arbitrary expression
156 auto* field_options =
157 checked_cast<compute::StructFieldOptions*>(current->call()->options.get());
158 field_options->field_ref = FieldRef(std::move(field_options->field_ref), index);
159 } else {
160 // First StructField on top of an arbitrary expression
161 current = compute::call("struct_field", {std::move(*current)},
162 arrow::compute::StructFieldOptions({index}));
163 }
164
165 // Segment handled, continue with child segment (if any)
166 if (ref->struct_field().has_child()) {
167 ref = &ref->struct_field().child();
168 } else {
169 ref = nullptr;
170 }
171 break;
172 }
173 case substrait::Expression::ReferenceSegment::kListElement: {
174 if (!current) {
175 // Root ListField (illegal)
176 return Status::Invalid(
177 "substrait::ListElement cannot take a Relation as an argument");
178 }
179
180 // ListField on top of an arbitrary expression
181 current = compute::call(
182 "list_element",
183 {std::move(*current), compute::literal(ref->list_element().offset())});
184
185 // Segment handled, continue with child segment (if any)
186 if (ref->list_element().has_child()) {
187 ref = &ref->list_element().child();
188 } else {
189 ref = nullptr;
190 }
191 break;
192 }
193 default:
194 // Unimplemented construct, break current of loop

Callers 1

ARROW_ASSIGN_OR_RAISEFunction · 0.70

Calls 15

field_refFunction · 0.85
EnumToStringFunction · 0.85
NormalizeFunctionNameFunction · 0.85
DecodeArgFunction · 0.85
DecodeOptionFunction · 0.85
ToCharsFunction · 0.85
MakeStructOptionsClass · 0.85
or_Function · 0.85
UnsafeFunction · 0.85
Date32ScalarClass · 0.85
Time64ScalarClass · 0.85

Tested by

no test coverage detected