java解惑之表达式之谜(谜题1)

本文探讨了Java中判断整数奇偶性的方法,并揭示了一个容易忽视的问题:使用取余运算符可能导致负奇数判断失误。文章提供了修正方案并深入分析了背后的原因。

谜题1:奇偶性

public static boolean isOdd(int i){

    return i % 2 == 1;

}

isOdd方法的目的是确定其惟一的参数是否为奇数,那么,这个方法是否和想象中的一样可行?

奇数可定义为被2整除余数为1的整数。表达式i%2计算的是i除以2时所产生的余数,因此看起来这个程序应该是可行的。遗憾的是,对于所有的正数来说,这个方法是没有任何问题的,但在int数值中,有一半是负数,而isOdd方法对所有负奇数的判断都会失败,都会返回false。这是java对取余操作符的定义所产生的后果。

java对取余操作符的定义为对于所有的int数值a和所有的非零int数值b,都满足下面的恒等式:

(a/b)*b + (a%b) == a。下面,我们来分析该恒等式。

从数学角度分析,对于任何偶数a和(b==2)来说,该恒等式是不正确的,若对正奇数a和(b==2)来说,等式左边的数总是比等式右边的数大(a%b)(负奇数的话则相反),也就说,我们可以利用该等式来判断奇偶数,无论a是正数、负数或者0,若将a代入后该等式成立,则a为偶数,否则a为奇数;但是在java中,“/”操作符是会自动取整的,也就是说无论a是偶数还是奇数还是0,该等式都是恒成立的,并且意味着当取余操作返回一个非零的结果时,它与左操作数具有相同的正负符号。所以当i是一个负奇数时,i%2等于-1而不是1,因此isOdd方法将错误的返回false。所以我们需要改正我们的方法:

public static boolean isOdd(int i){

    return i%2 != 0;

}

或者:

public static boolean isOdd(int i){

    return (i&1) != 0;

}

总之,无论何时使用了取余操作符,都要考虑操作数和结果的符号。该操作符的行为在其操作数非负时是一目了然的,但是当一个或者两个操作数是负数时,它的行为就不那么显而易见了。

 

 

                                                                                                                           观<<java puzzlers>>有感

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值