负零int

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

我需要一个整数的向量,在这里我可以区分0和-0.到目前为止,我已经想到了为这个特殊情况定义一个新的类,叫做zero_int。

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

我知道可以使用类似于 "虚拟基类 "的东西。vector<void*> 但我不知道怎么做... - 还有,指针向量中的指针所指向的对象在内存中是连续的吗?- 在这种情况下,这很重要。

如果有任何关于如何解决这个问题的建议,我将感激不尽。

c++ vector int variant negative-zero
1个回答
4
投票

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

这是不可能的,除非你不介意失去一个可能的非零的 int 值,这就给我们带来了 "显而易见 "的解决方案:将0视为-0,每一个正数都是自己的负数。

这就给我们带来了一个 "显而易见 "的解决方案:把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支持带符号的零。然而,我认为在任何情况下,用浮点来表示实数都会带来更多的问题,而不是解决问题。


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; }
};

注意: 已经写好了,但还没有测试

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