4

F# 中的位移位运算符被记录为当您将位移动到值的末尾时不进行旋转。您可以在 F# Interactive 中看到这一点:

> 让 a = 128uy
- 一个 <<< 1;;

val a : 字节 = 128uy
验证它:字节 = 0uy

也就是说,我们将高位移出 128 的顶部,得到 0。

如果 F# 旋转位而不是将它们从末尾移开,我们将得到 1,因为MSB位置的 1 位将向下旋转到LSB

然而,如果你对第二条语句做一个小的改动,你会得到一个令人惊讶的结果:

> 让 a = 128uy
- 一个 <<< 8;;

val a : 字节 = 128uy
验证它:字节 = 128uy

现在它看起来已经完成了字节中的位的完整旋转!

为什么是这样?

4

1 回答 1

3

这里发生的是 F# 在进行移位之前对移位运算符右侧的值进行模运算。对于无符号字节,它使用mod8,因为 F# 字节中有 8 位。因为 8 mod8 是 0,所以它根本不移动字节中的位。

如果您稍微使用一下这些值,您可以更清楚地看到这一点:

> 让 a = 4uy
- 一个 <<< 1;;

val a : 字节 = 4uy
验证它:字节 = 8uy

> 一 <<< 9;;
验证它:字节 = 8uy
> 一 <<< 17;;
验证它:字节 = 8uy

我们在所有三种情况下都得到相同的结果,因为它们在mod8 中是等价的表达式。

右移 ( >>>) 也会发生同样的事情,并且行为不限于字节。

于 2013-07-02T22:50:25.917 回答