在一个C程序中,我尝试了以下操作(只是为了检查行为)

 x = 5 % (-3);
 y = (-5) % (3);
 z = (-5) % (-3); 

printf("%d ,%d ,%d", x, y, z); 

在gcc中输出为(2,-2,-2)我以为每次都会有积极的结果。模量可以是负的吗?有人能解释一下这种行为吗?


当前回答

模算子给出余数。 c中的模算子通常取分子的符号

X = 5%(-3)这里分子是正的,所以结果是2 Y =(-5) %(3)分子为负,结果为-2 Z =(-5) %(-3)这里分子是负的所以结果是-2

此外,模(余数)运算符只能用于整型,不能用于浮点数。

其他回答

C中的%操作符不是模操作符而是余数操作符。

模运算符和余数运算符不同于负值。

对于余数运算符,结果的符号与被除数(分子)的符号相同,而对于模运算符,结果的符号与除数(分母)的符号相同。

C将a % b的%操作定义为:

  a == (a / b * b) + a % b

用/表示整型除法,并截断为0。这是对0(而不是负无穷)的截断,它将%定义为余数运算符而不是模运算符。

模算子给出余数。 c中的模算子通常取分子的符号

X = 5%(-3)这里分子是正的,所以结果是2 Y =(-5) %(3)分子为负,结果为-2 Z =(-5) %(-3)这里分子是负的所以结果是-2

此外,模(余数)运算符只能用于整型,不能用于浮点数。

我认为在抽象算术中定义mod会更有用;不是作为一个运算,而是作为一个完全不同的算术类别,有不同的元素和不同的运算符。这意味着mod 3中的加法与“正常的”加法不同;这是;整数加法。

所以当你这样做的时候:

5 % -3

你试图将整数5映射到mod -3集合中的一个元素。这些是mod -3的元素:

{ 0, -2, -1 }

So:

0 => 0, 1 => -2, 2 => -1, 3 => 0, 4 => -2, 5 => -1

假设你因为某种原因不得不熬夜30个小时,那一天你还剩下几个小时?30 mod -24。

但是C语言实现的不是余,而是余数。不管怎样,关键是返回负号是有意义的。

其他答案已经在C99或更高版本中解释过,涉及负操作数的整数除法总是截断为零。

注意,在C89中,结果向上舍入还是向下舍入是由实现定义的。因为(a/b) * b + a%b在所有标准中都等于a,包含负操作数的%的结果也是在C89中实现定义的。

根据C99标准,第6.5.5节 乘法运算符,需要以下条件:

(a / b) * b + a % b = a

结论

余数运算结果的符号 到C99,和红利是一样的。

让我们看一些例子(除数/除数):

只有股息是负的

(-3 / 2) * 2  +  -3 % 2 = -3

(-3 / 2) * 2 = -2

(-3 % 2) must be -1

当只有除数为负时

(3 / -2) * -2  +  3 % -2 = 3

(3 / -2) * -2 = 2

(3 % -2) must be 1

除数和被除数都为负

(-3 / -2) * -2  +  -3 % -2 = -3

(-3 / -2) * -2 = -2

(-3 % -2) must be -1

6.5.5 Multiplicative operators Syntax multiplicative-expression: cast-expression multiplicative-expression * cast-expression multiplicative-expression / cast-expression multiplicative-expression % cast-expression Constraints Each of the operands shall have arithmetic type. The operands of the % operator shall have integer type. Semantics The usual arithmetic conversions are performed on the operands. The result of the binary * operator is the product of the operands. The result of the / operator is the quotient from the division of the first operand by the second; the result of the % operator is the remainder. In both operations, if the value of the second operand is zero, the behavior is undefined. When integers are divided, the result of the / operator is the algebraic quotient with any fractional part discarded [1]. If the quotient a/b is representable, the expression (a/b)*b + a%b shall equal a. [1]: This is often called "truncation toward zero".