1

我需要一个整数向量,我可以在其中区分 0 和 -0。到目前为止,我已经想出了为这种特殊情况定义一个名为 zero_int 的新类的想法。

但是,现在我不能将普通整数和 zero_int 都推到同一个向量中。解决方案 std::variant 的大小为 8 个字节,我需要为每个变量保留 4 个大小。定义一个虚拟基类 my_int 并将 zero_int 设置为其派生类会将 zero_int 的大小增加到 32 个字节...

我知道可以使用类似 avector<void*>但我不知道如何使用的东西.. - 另外,指针向量中的指针指向的对象是否在内存中连续?- 这在这种情况下很重要。

我将不胜感激有关如何解决此问题的任何建议

4

2 回答 2

4

解决方案 std::variant 的大小为 8 字节,我需要为每个变量保留 4 的大小。

这是不可能的,除非您不介意丢失一个可能的非零int值。

这给我们带来了“显而易见”的解决方案:将 0 视为 -0,将每个正数视为自身减一。

    vec[i]:  -5 -4 -3 -2 -1  0 +1 +2 +3 +4 +5
my "value":  -5 -4 -3 -2 -1 -0 +0 +1 +2 +3 +4

(或者反过来做,这样可以让你在正负范围内对称;随便你。)

让任何包装你的向量的类以适合你的项目的任何方式处理这个“映射”。


指针向量中的指针指向的对象是否在内存中连续?

不。

你不想在这里有更多的间接性。


有人会建议使用浮点,因为 IEEE 754 支持有符号零。但是,我认为在任何情况下切换到浮点来表示实数可能会带来比它解决的问题更多的问题。

于 2020-06-11T18:16:17.820 回答
0

我会考虑使用无符号类型并将最高位显式管理为符号位:

class my_int {
public:
    my_int(int v) { set(v); }
    explicit operator int() const { return get(); }
    bool is_negative() const { return value & sign_bit; }
private:
    const static unsigned sign_bit =
        1u << (std::numeric_limits<unsigned>::digits - 1);
    unsigned value;
    void set(int v) { value = v < 0 ? (-v) & sign_bit : v;
    }
    int get() const { return value & sign_bit ? -(value & ~sign_bit) : value; }
};

注意:已编写但未经测试。

于 2020-06-11T19:10:38.613 回答