Skip to content

Commit 074e485

Browse files
committed
remove more copy
1 parent 8099036 commit 074e485

File tree

2 files changed

+24
-12
lines changed

2 files changed

+24
-12
lines changed

datafusion/common/src/datatype.rs

Lines changed: 17 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -66,6 +66,11 @@ pub trait FieldExt {
6666
/// Rename the field, returning a new Field with the given name
6767
fn renamed(self, new_name: &str) -> Self;
6868

69+
/// Retype the field with the given data type (this is different than
70+
/// [`Field::with_type`] as it tries to avoid copying if the data type is the
71+
/// same for [`FieldRefs`])
72+
fn retyped(self, new_data_type: DataType) -> Self;
73+
6974
/// Add field metadata,
7075
fn with_field_metadata(self, metadata: &FieldMetadata) -> Self;
7176

@@ -149,6 +154,10 @@ impl FieldExt for Field {
149154
}
150155
}
151156

157+
fn retyped(self, new_data_type: DataType) -> Self {
158+
self.with_data_type(new_data_type)
159+
}
160+
152161
fn with_field_metadata(self, metadata: &FieldMetadata) -> Self {
153162
metadata.add_to_field(self)
154163
}
@@ -188,6 +197,14 @@ impl FieldExt for Arc<Field> {
188197
}
189198
}
190199

200+
fn retyped(self, new_data_type: DataType) -> Self {
201+
if self.data_type() == &new_data_type {
202+
self
203+
} else {
204+
Arc::new(Arc::unwrap_or_clone(self).with_data_type(new_data_type))
205+
}
206+
}
207+
191208
fn with_field_metadata(self, metadata: &FieldMetadata) -> Self {
192209
metadata.add_to_field_ref(self)
193210
}

datafusion/expr/src/expr_schema.rs

Lines changed: 7 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -456,13 +456,10 @@ impl ExprSchemable for Expr {
456456
Expr::ScalarVariable(ty, _) => {
457457
Ok(Arc::new(Field::new(&schema_name, ty.clone(), true)))
458458
}
459-
Expr::Literal(l, metadata) => {
460-
let mut field = Field::new(&schema_name, l.data_type(), l.is_null());
461-
if let Some(metadata) = metadata {
462-
field = metadata.add_to_field(field);
463-
}
464-
Ok(Arc::new(field))
465-
}
459+
Expr::Literal(l, metadata) => Ok(Arc::new(
460+
Field::new(&schema_name, l.data_type(), l.is_null())
461+
.with_field_metadata_opt(metadata.as_ref()),
462+
)),
466463
Expr::IsNull(_)
467464
| Expr::IsNotNull(_)
468465
| Expr::IsTrue(_)
@@ -564,8 +561,7 @@ impl ExprSchemable for Expr {
564561
let new_fields = fields
565562
.into_iter()
566563
.zip(new_data_types)
567-
.map(|(f, d)| f.as_ref().clone().with_data_type(d))
568-
.map(Arc::new)
564+
.map(|(f, d)| f.retyped(d))
569565
.collect::<Vec<FieldRef>>();
570566

571567
let arguments = args
@@ -585,12 +581,11 @@ impl ExprSchemable for Expr {
585581
// _ => Ok((self.get_type(schema)?, self.nullable(schema)?)),
586582
Expr::Cast(Cast { expr, data_type }) => expr
587583
.to_field(schema)
588-
.map(|(_, f)| f.as_ref().clone().with_data_type(data_type.clone()))
589-
.map(Arc::new),
584+
.map(|(_, f)| f.retyped(data_type.clone())),
590585
Expr::Placeholder(Placeholder {
591586
id: _,
592587
field: Some(field),
593-
}) => Ok(field.as_ref().clone().with_name(&schema_name).into()),
588+
}) => Ok(Arc::clone(field).renamed(&schema_name)),
594589
Expr::Like(_)
595590
| Expr::SimilarTo(_)
596591
| Expr::Not(_)

0 commit comments

Comments
 (0)