pub struct Encoder {
pub cfg: EncoderConfig,
pub hdr: Vec<u8>,
pub meta: Vec<u8>,
pub data: Vec<u8>,
/* private fields */
}Expand description
Stateful encoder that accumulates encoded layer bytes.
Logical temporary buffers live in Codecs and are passed alongside
the encoder while a stream is being transformed and serialized. Physical
encoders live here with their own scratch buffers, then copy complete
payloads into data.
§Buffer layout
The MLT layer wire format is:
[varint(body_len + 1)] [tag = 1]
[name: string] [extent: varint] [column_count: varint] <- hdr
[col_type₁] [col_type₂] … [col_typeN] <- meta
[col₁ stream data] [col₂ stream data] … [colN stream data] <- dataThe three sections are accumulated into separate buffers so they can be combined at the end without any in-place insertion or extra copies:
hdr– layer header (name, extent,column_count).meta– column-type bytes (one byte + optional name per column).data– encoded stream data; also the target ofimpl Write.
§Sort-strategy trialing
Create one Encoder per sort-strategy trial, encode the layer into it,
and keep the one whose total_len() is smallest:
let mut codecs = Codecs::default();
let mut best: Option<Encoder> = None;
for strategy in strategies {
let mut enc = Encoder::new(cfg);
layer.write_to(&mut enc, &mut codecs)?;
if best.as_ref().is_none_or(|b| enc.total_len() < b.total_len()) {
best = Some(enc);
}
}
return best.unwrap().into_layer_bytes();§Stream-level encoding alternatives
Use Encoder::try_alternatives to open a competition,
then submit each candidate via AltSession::with. The guard’s Drop
impl finalises the competition automatically:
let mut alt = enc.try_alternatives();
alt.with(|enc| write_stream_as_varint(data, enc))?;
alt.with(|enc| write_stream_as_fastpfor(data, enc))?;
// alt drops → keeps whichever was shorterFields§
§cfg: EncoderConfigEncoding configuration: controls which optimization strategies are tried (sort orders, compression algorithms, etc.).
Set once at construction time via Encoder::new; propagated
automatically to all sub-encoders so individual encode methods do not
need a separate cfg argument.
hdr: Vec<u8>Layer header bytes: name, extent, column_count.
Written to hdr via Encoder::write_header. This section comes
first in the wire format and is never subject to alternatives.
meta: Vec<u8>Column-type metadata bytes.
Each column contributes one type byte (plus a name string for property
columns). Written by the write_columns_meta_to methods, which write
directly to enc.meta. This section comes second in the wire format
and is never subject to alternatives (column types are fixed).
data: Vec<u8>Encoded stream data.
All stream counts, per-stream encoding-metadata bytes, and encoded
data bytes land here via impl Write. This section comes last in
the wire format and is where stream-level alternatives compete.
Implementations§
Source§impl Encoder
impl Encoder
Sourcepub fn new(cfg: EncoderConfig) -> Self
pub fn new(cfg: EncoderConfig) -> Self
Create a new encoder with the given EncoderConfig.
Use Encoder::default() when the default configuration is sufficient.
Sourcepub fn with_explicit(cfg: EncoderConfig, explicit: ExplicitEncoder) -> Self
pub fn with_explicit(cfg: EncoderConfig, explicit: ExplicitEncoder) -> Self
Like Self::new but with the explicit encoder set for deterministic encoding
(tests, synthetics). Use with StagedLayer::encode_explicit.
Sourcepub fn write_header(
&mut self,
name: &str,
extent: u32,
column_count: usize,
) -> MltResult<()>
pub fn write_header( &mut self, name: &str, extent: u32, column_count: usize, ) -> MltResult<()>
Write the layer header (name, extent, column_count) to hdr.
Must be called exactly once per layer, after all column meta and data.
Sourcepub fn total_len(&self) -> usize
pub fn total_len(&self) -> usize
Total encoded bytes across all three sections (hdr + meta + data).
Sourcepub fn into_raw_bytes(self) -> Vec<u8> ⓘ
pub fn into_raw_bytes(self) -> Vec<u8> ⓘ
Concatenate hdr + meta + data into a single buffer without a
tag/size prefix.
Use this when the caller expects raw layer body bytes (without the size/tag framing)
rather than a complete framed wire record — see Self::into_layer_bytes for the framed form.
Sourcepub fn into_layer_bytes(self) -> MltResult<Vec<u8>>
pub fn into_layer_bytes(self) -> MltResult<Vec<u8>>
Assemble the complete Tag-01 layer record.
Sourcepub fn try_alternatives(&mut self) -> AltSession<'_>
pub fn try_alternatives(&mut self) -> AltSession<'_>
Begin a new encoding competition.
Returns an AltSession guard. Submit each candidate via
AltSession::with; the guard’s Drop impl finalises
the competition and retains the shortest candidate automatically.
Nesting is supported: calling try_alternatives inside a
with closure opens an inner competition on the same stack,
resolved before the outer candidate is committed.
§Example
let mut alt = enc.try_alternatives();
for cand in candidates {
alt.with(|enc| write_candidate(cand, enc))?;
}
// alt drops → finalises the competitionTrait Implementations§
Source§impl Write for Encoder
Writes bytes to Encoder::data.
impl Write for Encoder
Writes bytes to Encoder::data.
This blanket implementation makes Encoder compatible with all
BinarySerializer, VarIntWriter, and other Write-based utilities so that
stream-data methods do not need a separate code path.
Source§fn write(&mut self, buf: &[u8]) -> Result<usize>
fn write(&mut self, buf: &[u8]) -> Result<usize>
Source§fn flush(&mut self) -> Result<()>
fn flush(&mut self) -> Result<()>
Source§fn write_all(&mut self, buf: &[u8]) -> Result<()>
fn write_all(&mut self, buf: &[u8]) -> Result<()>
Source§fn is_write_vectored(&self) -> bool
fn is_write_vectored(&self) -> bool
can_vector)Source§fn write_all_vectored(&mut self, bufs: &mut [IoSlice<'_>]) -> Result<(), Error>
fn write_all_vectored(&mut self, bufs: &mut [IoSlice<'_>]) -> Result<(), Error>
write_all_vectored)Auto Trait Implementations§
impl Freeze for Encoder
impl !RefUnwindSafe for Encoder
impl !Send for Encoder
impl !Sync for Encoder
impl Unpin for Encoder
impl UnsafeUnpin for Encoder
impl !UnwindSafe for Encoder
Blanket Implementations§
Source§impl<T> BorrowMut<T> for Twhere
T: ?Sized,
impl<T> BorrowMut<T> for Twhere
T: ?Sized,
Source§fn borrow_mut(&mut self) -> &mut T
fn borrow_mut(&mut self) -> &mut T
Source§impl<W> FixedIntWriter for Wwhere
W: Write,
impl<W> FixedIntWriter for Wwhere
W: Write,
Source§impl<T> FmtForward for T
impl<T> FmtForward for T
Source§fn fmt_binary(self) -> FmtBinary<Self>where
Self: Binary,
fn fmt_binary(self) -> FmtBinary<Self>where
Self: Binary,
self to use its Binary implementation when Debug-formatted.Source§fn fmt_display(self) -> FmtDisplay<Self>where
Self: Display,
fn fmt_display(self) -> FmtDisplay<Self>where
Self: Display,
self to use its Display implementation when
Debug-formatted.Source§fn fmt_lower_exp(self) -> FmtLowerExp<Self>where
Self: LowerExp,
fn fmt_lower_exp(self) -> FmtLowerExp<Self>where
Self: LowerExp,
self to use its LowerExp implementation when
Debug-formatted.Source§fn fmt_lower_hex(self) -> FmtLowerHex<Self>where
Self: LowerHex,
fn fmt_lower_hex(self) -> FmtLowerHex<Self>where
Self: LowerHex,
self to use its LowerHex implementation when
Debug-formatted.Source§fn fmt_octal(self) -> FmtOctal<Self>where
Self: Octal,
fn fmt_octal(self) -> FmtOctal<Self>where
Self: Octal,
self to use its Octal implementation when Debug-formatted.Source§fn fmt_pointer(self) -> FmtPointer<Self>where
Self: Pointer,
fn fmt_pointer(self) -> FmtPointer<Self>where
Self: Pointer,
self to use its Pointer implementation when
Debug-formatted.Source§fn fmt_upper_exp(self) -> FmtUpperExp<Self>where
Self: UpperExp,
fn fmt_upper_exp(self) -> FmtUpperExp<Self>where
Self: UpperExp,
self to use its UpperExp implementation when
Debug-formatted.Source§fn fmt_upper_hex(self) -> FmtUpperHex<Self>where
Self: UpperHex,
fn fmt_upper_hex(self) -> FmtUpperHex<Self>where
Self: UpperHex,
self to use its UpperHex implementation when
Debug-formatted.Source§impl<T> Pipe for Twhere
T: ?Sized,
impl<T> Pipe for Twhere
T: ?Sized,
Source§fn pipe<R>(self, func: impl FnOnce(Self) -> R) -> Rwhere
Self: Sized,
fn pipe<R>(self, func: impl FnOnce(Self) -> R) -> Rwhere
Self: Sized,
Source§fn pipe_ref<'a, R>(&'a self, func: impl FnOnce(&'a Self) -> R) -> Rwhere
R: 'a,
fn pipe_ref<'a, R>(&'a self, func: impl FnOnce(&'a Self) -> R) -> Rwhere
R: 'a,
self and passes that borrow into the pipe function. Read moreSource§fn pipe_ref_mut<'a, R>(&'a mut self, func: impl FnOnce(&'a mut Self) -> R) -> Rwhere
R: 'a,
fn pipe_ref_mut<'a, R>(&'a mut self, func: impl FnOnce(&'a mut Self) -> R) -> Rwhere
R: 'a,
self and passes that borrow into the pipe function. Read moreSource§fn pipe_borrow<'a, B, R>(&'a self, func: impl FnOnce(&'a B) -> R) -> R
fn pipe_borrow<'a, B, R>(&'a self, func: impl FnOnce(&'a B) -> R) -> R
Source§fn pipe_borrow_mut<'a, B, R>(
&'a mut self,
func: impl FnOnce(&'a mut B) -> R,
) -> R
fn pipe_borrow_mut<'a, B, R>( &'a mut self, func: impl FnOnce(&'a mut B) -> R, ) -> R
Source§fn pipe_as_ref<'a, U, R>(&'a self, func: impl FnOnce(&'a U) -> R) -> R
fn pipe_as_ref<'a, U, R>(&'a self, func: impl FnOnce(&'a U) -> R) -> R
self, then passes self.as_ref() into the pipe function.Source§fn pipe_as_mut<'a, U, R>(&'a mut self, func: impl FnOnce(&'a mut U) -> R) -> R
fn pipe_as_mut<'a, U, R>(&'a mut self, func: impl FnOnce(&'a mut U) -> R) -> R
self, then passes self.as_mut() into the pipe
function.Source§fn pipe_deref<'a, T, R>(&'a self, func: impl FnOnce(&'a T) -> R) -> R
fn pipe_deref<'a, T, R>(&'a self, func: impl FnOnce(&'a T) -> R) -> R
self, then passes self.deref() into the pipe function.Source§impl<T> Tap for T
impl<T> Tap for T
Source§fn tap_borrow<B>(self, func: impl FnOnce(&B)) -> Self
fn tap_borrow<B>(self, func: impl FnOnce(&B)) -> Self
Borrow<B> of a value. Read moreSource§fn tap_borrow_mut<B>(self, func: impl FnOnce(&mut B)) -> Self
fn tap_borrow_mut<B>(self, func: impl FnOnce(&mut B)) -> Self
BorrowMut<B> of a value. Read moreSource§fn tap_ref<R>(self, func: impl FnOnce(&R)) -> Self
fn tap_ref<R>(self, func: impl FnOnce(&R)) -> Self
AsRef<R> view of a value. Read moreSource§fn tap_ref_mut<R>(self, func: impl FnOnce(&mut R)) -> Self
fn tap_ref_mut<R>(self, func: impl FnOnce(&mut R)) -> Self
AsMut<R> view of a value. Read moreSource§fn tap_deref<T>(self, func: impl FnOnce(&T)) -> Self
fn tap_deref<T>(self, func: impl FnOnce(&T)) -> Self
Deref::Target of a value. Read moreSource§fn tap_deref_mut<T>(self, func: impl FnOnce(&mut T)) -> Self
fn tap_deref_mut<T>(self, func: impl FnOnce(&mut T)) -> Self
Deref::Target of a value. Read moreSource§fn tap_dbg(self, func: impl FnOnce(&Self)) -> Self
fn tap_dbg(self, func: impl FnOnce(&Self)) -> Self
.tap() only in debug builds, and is erased in release builds.Source§fn tap_mut_dbg(self, func: impl FnOnce(&mut Self)) -> Self
fn tap_mut_dbg(self, func: impl FnOnce(&mut Self)) -> Self
.tap_mut() only in debug builds, and is erased in release
builds.Source§fn tap_borrow_dbg<B>(self, func: impl FnOnce(&B)) -> Self
fn tap_borrow_dbg<B>(self, func: impl FnOnce(&B)) -> Self
.tap_borrow() only in debug builds, and is erased in release
builds.Source§fn tap_borrow_mut_dbg<B>(self, func: impl FnOnce(&mut B)) -> Self
fn tap_borrow_mut_dbg<B>(self, func: impl FnOnce(&mut B)) -> Self
.tap_borrow_mut() only in debug builds, and is erased in release
builds.Source§fn tap_ref_dbg<R>(self, func: impl FnOnce(&R)) -> Self
fn tap_ref_dbg<R>(self, func: impl FnOnce(&R)) -> Self
.tap_ref() only in debug builds, and is erased in release
builds.Source§fn tap_ref_mut_dbg<R>(self, func: impl FnOnce(&mut R)) -> Self
fn tap_ref_mut_dbg<R>(self, func: impl FnOnce(&mut R)) -> Self
.tap_ref_mut() only in debug builds, and is erased in release
builds.Source§fn tap_deref_dbg<T>(self, func: impl FnOnce(&T)) -> Self
fn tap_deref_dbg<T>(self, func: impl FnOnce(&T)) -> Self
.tap_deref() only in debug builds, and is erased in release
builds.