假设我有Long someLong = 1004L
。我可以使用哪种有效方法将其四舍五入为1000L
?请注意,我实际上并不知道someLong == 1004L
,所以我不能简单地做someLong -= 4L;
。我需要一个通用的方法。我还希望能够舍入到每个5
而不是每个10
,例如,一个函数舍入到1005L
(因为如果我们以5
进行舍入,那么它将舍入为下降)。
更多示例..可能是我有1926L
,我想四舍五入为5
,这意味着我需要1925L
。或者我需要四舍五入到10
,这意味着我需要1930L
。
这很简单。
如果您想始终舍入:
您所需的公式是:
someLong-someLong%10
这是因为someLong%10
是someLong
的余数除以10。如果从原始数字中获得此值,则会得到所需的向下取整的值。
一般化也很简单:如果需要,您可以使用100,甚至13。
如果要在另一个方向上四舍五入(例如,始终向上或始终向中间四舍五入,那么首先向此数字中添加内容,然后始终向下四舍五入。
如果您想四舍五入:
然后您首先需要添加9,然后始终向下舍入。
someLong+9-(someLong+9)%10
如果您想总是四舍五入到中间:
...您也想四舍五入到最近的倍数。然后,您首先添加所需间隔的half,然后始终向下舍入。例如,对于10,它是:
someLong+5-(someLong+5)%10
如果您要使用value
的语义将step
舍入到BigDecimal.ROUND_HALF_UP
的最接近倍数(如果恰好在两步之间的一半处,请四舍五入),则必要的计算是:
val += step/2;
val -= val%step;
尝试一下:
double a=1002l;
double b=a/10;
a=Math.round(b)*10;
System.out.println("Double round of value : "+a);
将四舍五入到k
的最接近倍数的通用函数将是(仅适用于正数):
public static long round(long toRound, long k) {
long times = toRound / k;
long reminder = toRound % k;
if (reminder < k / 2) {
return k * times;
} else {
return k * (times + 1);
}
}
和无分支变量(reminder < k / 2
=> (2 * reminder / k) < 1
:
public static long round(long toRound, long k) {
long times = toRound / k;
long reminder = toRound % k;
return k * (times + ((2 * reminder) / k));
}
以下示例满足了您的需求:
public static void main(String[] args) {
Long n = 1004L;
Long n2 = 1005L;
n = round(n);
n2 = round(n2);
System.out.println(n);
System.out.println(n2);
}
private static Long round(Long n) {
if (n%10 <=4) {
return n -=n%10;
} else {
return n += (10-n%10);
}
}
myFloor(long n, int m) {
return n - (n % m);
}
myRound(long n, int m) {
int i = (n % m) >= (m / 2) ? m : 0;
return n + i - (n % m);
}
所以m
可能是10 , 5 , ...