我如何在 cout 中使用位移位?
How do I use bitwise shifts with cout?
我正在尝试做类似的事情:
#include <iostream>
int main()
{
std::cout << 1 << 5 << std::endl;
}
我期望 32(1 左移 5),但我得到 15。
我正在尝试使用这样的宏:
#define BIT_SHIFT(x,y) x << y
...
cout << BIT_SHIFT(1, 5) << std::endl;
这就发生了。
为什么?我该如何解决这个问题?
只需使用括号:
#include <iostream>
int main()
{
std::cout << (1 << 5) << std::endl;
}
std::cout << 1 << 5
表示 "push to output stream first integer literal 1
, followed by integer 5
"。但是,添加括号会改变计算顺序,首先计算 1 << 5
,导致 std::cout << 32 << std::endl;
表达式。
使用括号:
std::cout << (1 << 5) << std::endl;
原因是输出 ostream& operator<<(ostream&, const T&)
重载链接了 return 值以再次调用该函数。
如果使用括号,则先计算移位值,然后传递给重载输出运算符。
I am trying to use this in a macro: ...
因此上面说你的宏定义应该是这样的:
#define BIT_SHIFT(x,y) ((x) << (y))
您可能想知道为什么现在要多一个括号。这只是更安全的编写宏。想想有人试图像这样使用您的宏:
cout << BIT_SHIFT(1, 5*2) << std::endl;
I'm trying to do something similar to this:
#include <iostream>
int main()
{
std::cout << 1 << 5 << std::endl;
}
你是对的。您正在尝试做类似的事情。但是,这个问题与宏无关(我的意思是,这也是一个问题,但稍后会详细介绍)。问题是你的目标不是你的意思。你不是说std::cout << 1 << 5 << std::endl;
,你是说std::cout << (1 << 5) << std::endl;
,不同的是第一个分解成这样:
std::cout << 1;
std::cout << 5;
std::cout << std::endl;
而你想要的是这样的:
int i = 1 << 5;
std::cout << i;
std::cout << std::endl;
或者类似的东西。
答案很简单:要么在 cout
语句中使用括号,要么将其放在宏中(更好的选择):
// either
cout << (BIT_SHIFT(1, 5)) << std::endl;
// or
#define BIT_SHIFT(x,y) (x << y)
...
cout << BIT_SHIFT(1, 5) << std::endl;
此外,正如其他人所建议的,如果您愿意,您甚至可以更进一步:
#define BIT_SHIFT(x,y) ((x) << (y))
...
cout << BIT_SHIFT(1, 5) << std::endl;
这样,即使您在 x
或 y
中做一些奇怪的事情,您的代码也不会中断。
我正在尝试做类似的事情:
#include <iostream>
int main()
{
std::cout << 1 << 5 << std::endl;
}
我期望 32(1 左移 5),但我得到 15。
我正在尝试使用这样的宏:
#define BIT_SHIFT(x,y) x << y
...
cout << BIT_SHIFT(1, 5) << std::endl;
这就发生了。
为什么?我该如何解决这个问题?
只需使用括号:
#include <iostream>
int main()
{
std::cout << (1 << 5) << std::endl;
}
std::cout << 1 << 5
表示 "push to output stream first integer literal 1
, followed by integer 5
"。但是,添加括号会改变计算顺序,首先计算 1 << 5
,导致 std::cout << 32 << std::endl;
表达式。
使用括号:
std::cout << (1 << 5) << std::endl;
原因是输出 ostream& operator<<(ostream&, const T&)
重载链接了 return 值以再次调用该函数。
如果使用括号,则先计算移位值,然后传递给重载输出运算符。
I am trying to use this in a macro: ...
因此上面说你的宏定义应该是这样的:
#define BIT_SHIFT(x,y) ((x) << (y))
您可能想知道为什么现在要多一个括号。这只是更安全的编写宏。想想有人试图像这样使用您的宏:
cout << BIT_SHIFT(1, 5*2) << std::endl;
I'm trying to do something similar to this:
#include <iostream> int main() { std::cout << 1 << 5 << std::endl; }
你是对的。您正在尝试做类似的事情。但是,这个问题与宏无关(我的意思是,这也是一个问题,但稍后会详细介绍)。问题是你的目标不是你的意思。你不是说std::cout << 1 << 5 << std::endl;
,你是说std::cout << (1 << 5) << std::endl;
,不同的是第一个分解成这样:
std::cout << 1;
std::cout << 5;
std::cout << std::endl;
而你想要的是这样的:
int i = 1 << 5;
std::cout << i;
std::cout << std::endl;
或者类似的东西。
答案很简单:要么在 cout
语句中使用括号,要么将其放在宏中(更好的选择):
// either
cout << (BIT_SHIFT(1, 5)) << std::endl;
// or
#define BIT_SHIFT(x,y) (x << y)
...
cout << BIT_SHIFT(1, 5) << std::endl;
此外,正如其他人所建议的,如果您愿意,您甚至可以更进一步:
#define BIT_SHIFT(x,y) ((x) << (y))
...
cout << BIT_SHIFT(1, 5) << std::endl;
这样,即使您在 x
或 y
中做一些奇怪的事情,您的代码也不会中断。