Warning: file_get_contents(/data/phpspider/zhask/data//catemap/6/xamarin/3.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
Java 如何使用带符号字节的模?_Java_Scala_Byte_Modulo_Signed - Fatal编程技术网

Java 如何使用带符号字节的模?

Java 如何使用带符号字节的模?,java,scala,byte,modulo,signed,Java,Scala,Byte,Modulo,Signed,我想实现以下伪代码,a是一个字节,b是一个字节 (a + b) mod 256 我将用Scala编写它,就像下面的代码片段一样,但我不认为这与Java有什么显著区别 因此,如果字节的值在0到255(包括255)之间,我可以写: (a + b) % 256 def f1(a: Byte, b: Byte): Byte = (((a + 128 + b + 128) % 256) - 128).toByte 但是Java/Scala的类型Byte是有符号的,范围从-128到127(包括)。我可

我想实现以下伪代码,
a
是一个字节,
b
是一个字节

(a + b) mod 256
我将用Scala编写它,就像下面的代码片段一样,但我不认为这与Java有什么显著区别

因此,如果字节的值在0到255(包括255)之间,我可以写:

(a + b) % 256
def f1(a: Byte, b: Byte): Byte = (((a + 128 + b + 128) % 256) - 128).toByte
但是Java/Scala的类型
Byte
是有符号的,范围从-128到127(包括)。我可以写:

(a + b) % 256
def f1(a: Byte, b: Byte): Byte = (((a + 128 + b + 128) % 256) - 128).toByte
这对我来说似乎不必要的复杂,但我不知道
%
在负值上的行为。我也不知道这个函数是否可以用xor或类似的东西来简化

如何基于类型
字节实现和简化函数?

或更一般的:

如何使用带符号字节的模?

编辑:

上面的功能f1不正确。应该是:

def f1(a: Byte, b: Byte): Byte = ((a + b + 128) % 256 - 128).toByte
正因为如此,我与简化版本的比较是错误的。因此,这种简化的方法应该有效:

def f2(a: Byte, b: Byte): Byte = (a + b).toByte

这两个值被隐式转换为
Int
值并相加。当将其转换回一个
字节时,所产生的
Int
的4个字节中的前3个将被切掉,这等于模运算。函数
f1
f2
现在返回相同的结果。使用所有256*256可能的输入变量进行测试。

这是一个简化版本:

def f2(a: Byte, b: Byte): Byte = (a + b).toByte

我编辑了问题并在那里解释了答案,因为我犯了一个问题中包含的错误。

在Java中,模运算符
%
可以产生
0
或与股息相同的符号:

-1 % 256 = -1.
此外,即使使用Java的有符号
字节
类型,位模式也始终可以解释为无符号值

100000000 = -128 (signed) = 128 (signed)
此外,执行
byte
算术mod
256
也是多余的,因为回溯到
byte
会隐式执行此操作

现在让我们看看在每种溢出情况下(有符号和无符号)会发生什么:

输出:

(6 + 70) % 256 = 76.  Unsigned: (6 + 70) % 256 = 76.
(70 + 70) % 256 = -116.  Unsigned: (70 + 70) % 256 = 140.
(-6 + -70) % 256 = -76.  Unsigned: (250 + 186) % 256 = 180.
(-120 + -120) % 256 = 16.  Unsigned: (136 + 136) % 256 = 16.
无论出现何种溢出情况,结果都是正确的。因此,在Java中,您可以简单地添加它们并将结果转换回
byte

public static byte f1(byte a, byte b)
{
    return (byte) (a + b);
}
在Scala中,等价物如您所示:

def f2(a: Byte, b: Byte): Byte = (a + b).toByte

您的方法会返回您期望的值吗?例如,如果你的
mod
的结果超过128,你将得到一个负数。是的,我希望在某些情况下返回负值。我想从二进制的角度来看,这一切都是一样的,但是在有符号的
字节
类型的上下文中,最高有效位被解释为值的符号。我认为0=>+和1=>-。我怀疑你想要的等同于
&0xFF