在字节宽枚举中保留两个 7 位结构

问题描述 投票:0回答:1

我有两个结构体,它们都只需要 7 位来表示自己:

#[repr(transparent)]
struct TypeFlags(u8);

// TypeFlags has capabilities that are invalid for Control
impl std::ops::BitOr for TypeFlags {
    type Output = Self;

    fn bitor(self, rhs: Self) -> Self::Output {
        Self(self.0 | rhs.0)
    }
}

#[repr(transparent)]
struct Control(u8);

由于两种类型仅需要 7 位,因此可以创建仅占用一个字节的“任一”类型。

// problem: the compiler sets aside
// a "flag" byte for the enum variant.
// size = 2
enum Either {
    Type(TypeFlags),
    Ctrl(Control)
}

// problem: pattern matching is painful
struct PackedEither(u8);

是否有我可以利用的枚举的子字节优化,或者我是否必须在像

PackedEither
这样的结构上手动实现位标志?

rust byte
1个回答
0
投票

编译器无法进行该优化,但为了论证起见,我们假设编译器要进行优化,并假设

TypeFlags
存储为
0b0xxx_xxxx
Control
存储为
0b1xxx_xxx

现在问题来了:
在 Rust 中,我们可以匹配对

Either
的引用并获取对所包含值的引用:

fn unwrap_control_ref(either: &Either) -> &Control {
    let Either::Ctrl(control) = some_either_reference else {
        panic!("was a `Either::Type`");
    };
    control
}

现在编译器必须生成引用

Control
值的代码,但是,它不会将其存储在内存中的任何位置,它只存储“
Control | 0b1000_0000
”。

遗憾的是,即使我们将

Control
的范围更改为
128..256
并使用标准库内部属性,它也不会像我们想要的那样使用 nieche

© www.soinside.com 2019 - 2024. All rights reserved.