mirror of
https://github.com/nushell/nushell.git
synced 2025-08-12 00:50:13 +02:00
Shrink the size of Expr
(#12610)
# Description Continuing from #12568, this PR further reduces the size of `Expr` from 64 to 40 bytes. It also reduces `Expression` from 128 to 96 bytes and `Type` from 32 to 24 bytes. This was accomplished by: - for `Expr` with multiple fields (e.g., `Expr::Thing(A, B, C)`), merging the fields into new AST struct types and then boxing this struct (e.g. `Expr::Thing(Box<ABC>)`). - replacing `Vec<T>` with `Box<[T]>` in multiple places. `Expr`s and `Expression`s should rarely be mutated, if at all, so this optimization makes sense. By reducing the size of these types, I didn't notice a large performance improvement (at least compared to #12568). But this PR does reduce the memory usage of nushell. My config is somewhat light so I only noticed a difference of 1.4MiB (38.9MiB vs 37.5MiB). --------- Co-authored-by: Stefan Holderbach <sholderbach@users.noreply.github.com>
This commit is contained in:
@ -100,9 +100,9 @@ pub trait Eval {
|
||||
|
||||
Ok(Value::record(record, expr.span))
|
||||
}
|
||||
Expr::Table(headers, vals) => {
|
||||
Expr::Table(table) => {
|
||||
let mut output_headers = vec![];
|
||||
for expr in headers {
|
||||
for expr in table.columns.as_ref() {
|
||||
let header = Self::eval::<D>(state, mut_state, expr)?.coerce_into_string()?;
|
||||
if let Some(idx) = output_headers
|
||||
.iter()
|
||||
@ -111,7 +111,7 @@ pub trait Eval {
|
||||
return Err(ShellError::ColumnDefinedTwice {
|
||||
col_name: header,
|
||||
second_use: expr.span,
|
||||
first_use: headers[idx].span,
|
||||
first_use: table.columns[idx].span,
|
||||
});
|
||||
} else {
|
||||
output_headers.push(header);
|
||||
@ -119,8 +119,8 @@ pub trait Eval {
|
||||
}
|
||||
|
||||
let mut output_rows = vec![];
|
||||
for val in vals {
|
||||
let record = output_headers.iter().zip(val).map(|(col, expr)| {
|
||||
for val in table.rows.as_ref() {
|
||||
let record = output_headers.iter().zip(val.as_ref()).map(|(col, expr)| {
|
||||
Self::eval::<D>(state, mut_state, expr).map(|val| (col.clone(), val))
|
||||
}).collect::<Result<_,_>>()?;
|
||||
|
||||
@ -131,15 +131,15 @@ pub trait Eval {
|
||||
}
|
||||
Ok(Value::list(output_rows, expr.span))
|
||||
}
|
||||
Expr::Keyword(_, _, expr) => Self::eval::<D>(state, mut_state, expr),
|
||||
Expr::Keyword(kw) => Self::eval::<D>(state, mut_state, &kw.expr),
|
||||
Expr::String(s) => Ok(Value::string(s.clone(), expr.span)),
|
||||
Expr::Nothing => Ok(Value::nothing(expr.span)),
|
||||
Expr::ValueWithUnit(e, unit) => match Self::eval::<D>(state, mut_state, e)? {
|
||||
Value::Int { val, .. } => unit.item.build_value(val, unit.span),
|
||||
Expr::ValueWithUnit(value) => match Self::eval::<D>(state, mut_state, &value.expr)? {
|
||||
Value::Int { val, .. } => value.unit.item.build_value(val, value.unit.span),
|
||||
x => Err(ShellError::CantConvert {
|
||||
to_type: "unit value".into(),
|
||||
from_type: x.get_type().to_string(),
|
||||
span: e.span,
|
||||
span: value.expr.span,
|
||||
help: None,
|
||||
}),
|
||||
},
|
||||
@ -150,27 +150,27 @@ pub trait Eval {
|
||||
Expr::Subexpression(block_id) => {
|
||||
Self::eval_subexpression::<D>(state, mut_state, *block_id, expr.span)
|
||||
}
|
||||
Expr::Range(from, next, to, operator) => {
|
||||
let from = if let Some(f) = from {
|
||||
Expr::Range(range) => {
|
||||
let from = if let Some(f) = &range.from {
|
||||
Self::eval::<D>(state, mut_state, f)?
|
||||
} else {
|
||||
Value::nothing(expr.span)
|
||||
};
|
||||
|
||||
let next = if let Some(s) = next {
|
||||
let next = if let Some(s) = &range.next {
|
||||
Self::eval::<D>(state, mut_state, s)?
|
||||
} else {
|
||||
Value::nothing(expr.span)
|
||||
};
|
||||
|
||||
let to = if let Some(t) = to {
|
||||
let to = if let Some(t) = &range.to {
|
||||
Self::eval::<D>(state, mut_state, t)?
|
||||
} else {
|
||||
Value::nothing(expr.span)
|
||||
};
|
||||
|
||||
Ok(Value::range(
|
||||
Range::new(from, next, to, operator.inclusion, expr.span)?,
|
||||
Range::new(from, next, to, range.operator.inclusion, expr.span)?,
|
||||
expr.span,
|
||||
))
|
||||
}
|
||||
|
Reference in New Issue
Block a user