Warning: file_get_contents(/data/phpspider/zhask/data//catemap/6/cplusplus/144.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C++ 如何对浮点数执行位运算_C++_Floating Point_Genetic Algorithm_Bitwise Operators - Fatal编程技术网

C++ 如何对浮点数执行位运算

C++ 如何对浮点数执行位运算,c++,floating-point,genetic-algorithm,bitwise-operators,C++,Floating Point,Genetic Algorithm,Bitwise Operators,我试过这个: float a = 1.4123; a = a & (1 << 3); 我让程序运行。唯一的问题是,位运算是对舍入后获得的数字的整数表示进行的 以下情况也是不允许的 float a = 1.4123; a = (void*)a & (1 << 3); float a=1.4123; a=(void*)a&(1float a=1.4123; 无符号int*inta=重新解释强制转换(&a); *inta=*inta&(1如果试图更改浮点表示

我试过这个:

float a = 1.4123;
a = a & (1 << 3);
我让程序运行。唯一的问题是,位运算是对舍入后获得的数字的整数表示进行的

以下情况也是不允许的

float a = 1.4123;
a = (void*)a & (1 << 3);
float a=1.4123;
a=(void*)a&(1
float a=1.4123;
无符号int*inta=重新解释强制转换(&a);

*inta=*inta&(1如果试图更改浮点表示中的位,可以执行以下操作:

union fp_bit_twiddler {
    float f;
    int i;
} q;
q.f = a;
q.i &= (1 << 3);
a = q.f;
联合fp位旋转器{ 浮动f; int i; }q; q、 f=a; q、 i&=(1@mobrule:

更好:

#include <stdint.h>
...
union fp_bit_twiddler {
    float f;
    uint32_t u;
} q;

/* mutatis mutandis ... */
#包括
...
联合fp_钻头旋转器{
浮动f;
uint32_t u;
}q;
/*比照*/
对于这些值,int可能是可以的,但通常应该使用 用于位移位的无符号整数,以避免算术移位的影响。以及
uint32即使在整数不是32位的系统上也能工作。

在语言级别上,没有“浮点数的位运算”。C/C++中的位运算处理数字的值表示。而C/C++中没有定义浮点数的值表示(无符号整数在这方面是一个例外,因为它们的移位被定义为好像它们存储在2的补码中)。浮点数在值表示级别没有位,这就是为什么不能对它们应用逐位运算

您所能做的就是分析浮点数占用的原始内存的位内容。为此,您需要使用下面建议的并集,或者(等效地,并且仅在C++中)将浮点对象重新解释为
无符号字符
对象的数组,如中所示

float f = 5;
unsigned char *c = reinterpret_cast<unsigned char *>(&f);
// inspect memory from c[0] to c[sizeof f - 1]
float f=5;
无符号字符*c=重新解释强制转换(&f);
//检查从c[0]到c[sizeof f-1]的内存

和请不要尝试将<代码>浮点< /Cord>对象重新解释为<代码> int 对象,正如其他答案所建议的那样。这没有什么意义,并且不能保证在遵循严格的混叠规则的编译器中工作。C++中检查内存内容的正确方法是重新解释它为“代码>数组”。[signed/unsigned]字符


另外请注意,从技术上讲,您无法保证系统上的浮点表示为IEEE754(尽管在实践中是这样,除非您明确允许它不为IEEE754,并且仅针对-0.0、±无穷大和NaN)。

看看下面的内容。灵感来自快速平方根逆:

#include <iostream>
using namespace std;

int main()
{
    float x, td = 2.0;
    int ti = *(int*) &td;
    cout << "Cast int: " << ti << endl;
    ti = ti>>4;
    x = *(float*) &ti;
    cout << "Recast float: " << x << endl;
    return 0; 
}
#包括
使用名称空间std;
int main()
{
浮点数x,td=2.0;
int ti=*(int*)&td;

cout在浮点位运算的Python实现中,用二进制表示从小数点开始无限向左和向右扩展的数字。因为在大多数体系结构中,浮点数都有符号零,所以它用于表示负数(实际上,它只是假装这样做,并使用一些技巧来实现外观)


<>我确信它可以适应C++的工作,但是必须注意在均衡指数时不要让右移位溢出。< /P> < P>不应该使用Bitwise运算符,因为浮点是硬件专用的,不管你有什么硬件的相似性。对于C++,您可以通过在浮点的“对象”包装上重载流运算符来获得位移位操作符的类似“感觉”:

// Simple object wrapper for float type as templates want classes.
class Float
{
float m_f;
public:
    Float( const float & f )
    : m_f( f )
    {
    }

    operator float() const
    {
        return m_f;
    }
};

float operator>>( const Float & left, int right )
{
    float temp = left;
    for( right; right > 0; --right )
    {
        temp /= 2.0f;
    }
    return temp;
}

float operator<<( const Float & left, int right )
{
    float temp = left;
    for( right; right > 0; --right )
    {
        temp *= 2.0f;
    }
    return temp;
}

int main( int argc, char ** argv )
{
    int a1 = 40 >> 2; 
    int a2 = 40 << 2;
    int a3 = 13 >> 2;
    int a4 = 256 >> 2;
    int a5 = 255 >> 2;

    float f1 = Float( 40.0f ) >> 2; 
    float f2 = Float( 40.0f ) << 2;
    float f3 = Float( 13.0f ) >> 2;
    float f4 = Float( 256.0f ) >> 2;
    float f5 = Float( 255.0f ) >> 2;
}
//浮点类型的简单对象包装器,因为模板需要类。
班级浮动
{
浮动m_f;
公众:
浮点数(常数浮点数和f)
:m_f(f)
{
}
运算符float()常量
{
返回m_f;
}
};
浮点运算符>>(常量浮点和左、整数右)
{
浮动温度=左侧;
for(右;右>0;--右)
{
温度/=2.0f;
}
返回温度;
}
浮点运算符>2;
int a2=40>2;
int a4=256>>2;
int a5=255>>2;
浮球f1=浮球(40.0f)>>2;
浮动f2=浮动(40.0f)>2;
浮动f4=浮动(256.0f)>>2;
浮动f5=浮动(255.0f)>>2;
}

您将有一个余数,您可以根据所需的实现将其丢弃。

FWIW,浮点上的位操作有一个真正的用例(我最近才遇到过)——为OpenGL实现编写的着色器只支持较旧版本的GLSL(1.2和更早版本不支持位运算符),并且如果将浮点数转换为整数,将导致精度损失

可以使用余数(模)和不等式检查对浮点数执行逐位运算。例如:

float A = 0.625; //value to check; ie, 160/256
float mask = 0.25; //bit to check; ie, 1/4
bool result = (mod(A, 2.0 * mask) >= mask); //non-zero if bit 0.25 is on in A
float mod(float num, float den)
{
    return num - den * floor(num / den);
}
上面假设A在[0..1)之间,掩码中只有一个“位”要检查,但它可以推广到更复杂的情况

这个想法是基于在

如果甚至没有内置的mod函数,那么也可以相当容易地实现。例如:

float A = 0.625; //value to check; ie, 160/256
float mask = 0.25; //bit to check; ie, 1/4
bool result = (mod(A, 2.0 * mask) >= mask); //non-zero if bit 0.25 is on in A
float mod(float num, float den)
{
    return num - den * floor(num / den);
}
通过使用以下命令,您可以在不存在未定义行为的情况下,对双关为的
float
类型(如果您的实现定义了它,大多数实现都定义了它)进行处理并执行逐位操作:

float a=1.4123f;
uint32_t b;
标准:memcpy(&b,&a,4);
//执行位运算

b&=1u您尝试的是哪种位运算?您想使用特定值的IEEE 754表示形式吗?是的,我想使用实现使用的任何二进制表示形式,
a=a&(1@iamrohitbanga:等式???没有有意义的“等式”在C++中,这需要对浮点类型进行位操作。它不改变一个东西;C++中也没有任何有意义的表达式需要浮点上的按位运算。或者稍微少一点冗长:<代码> RealTytCube(a)& =(1为什么不只是<代码>(int *)(空洞*)和<
float a = 1.4123f;
uint32_t b;

std::memcpy(&b, &a, 4);
// perform bitwise operation
b &= 1u << 3;
std::memcpy(&a, &b, 4);