Danil Chapovalov | 33b83fd | 2019-09-18 15:48:23 +0200 | [diff] [blame] | 1 | /* |
| 2 | * Copyright 2019 The WebRTC Project Authors. All rights reserved. |
| 3 | * |
| 4 | * Use of this source code is governed by a BSD-style license |
| 5 | * that can be found in the LICENSE file in the root of the source |
| 6 | * tree. An additional intellectual property rights grant can be found |
| 7 | * in the file PATENTS. All contributing project authors may |
| 8 | * be found in the AUTHORS file in the root of the source tree. |
| 9 | */ |
| 10 | |
| 11 | #ifndef RTC_BASE_NUMERICS_DIVIDE_ROUND_H_ |
| 12 | #define RTC_BASE_NUMERICS_DIVIDE_ROUND_H_ |
| 13 | |
| 14 | #include <type_traits> |
| 15 | |
| 16 | #include "rtc_base/checks.h" |
| 17 | #include "rtc_base/numerics/safe_compare.h" |
| 18 | |
| 19 | namespace webrtc { |
| 20 | |
| 21 | template <typename Dividend, typename Divisor> |
| 22 | inline auto constexpr DivideRoundUp(Dividend dividend, Divisor divisor) { |
| 23 | static_assert(std::is_integral<Dividend>(), ""); |
| 24 | static_assert(std::is_integral<Divisor>(), ""); |
| 25 | RTC_DCHECK_GE(dividend, 0); |
| 26 | RTC_DCHECK_GT(divisor, 0); |
| 27 | |
| 28 | auto quotient = dividend / divisor; |
| 29 | auto remainder = dividend % divisor; |
| 30 | return quotient + (remainder > 0 ? 1 : 0); |
| 31 | } |
| 32 | |
| 33 | template <typename Dividend, typename Divisor> |
| 34 | inline auto constexpr DivideRoundToNearest(Dividend dividend, Divisor divisor) { |
| 35 | static_assert(std::is_integral<Dividend>(), ""); |
| 36 | static_assert(std::is_integral<Divisor>(), ""); |
Danil Chapovalov | 33b83fd | 2019-09-18 15:48:23 +0200 | [diff] [blame] | 37 | RTC_DCHECK_GT(divisor, 0); |
| 38 | |
Danil Chapovalov | f4b21da | 2022-12-20 14:53:35 +0000 | [diff] [blame] | 39 | if (dividend < Dividend{0}) { |
| 40 | auto half_of_divisor = divisor / 2; |
| 41 | auto quotient = dividend / divisor; |
| 42 | auto remainder = dividend % divisor; |
| 43 | if (rtc::SafeGt(-remainder, half_of_divisor)) { |
| 44 | --quotient; |
| 45 | } |
| 46 | return quotient; |
| 47 | } |
| 48 | |
Danil Chapovalov | 33b83fd | 2019-09-18 15:48:23 +0200 | [diff] [blame] | 49 | auto half_of_divisor = (divisor - 1) / 2; |
| 50 | auto quotient = dividend / divisor; |
| 51 | auto remainder = dividend % divisor; |
Danil Chapovalov | f4b21da | 2022-12-20 14:53:35 +0000 | [diff] [blame] | 52 | if (rtc::SafeGt(remainder, half_of_divisor)) { |
| 53 | ++quotient; |
| 54 | } |
| 55 | return quotient; |
Danil Chapovalov | 33b83fd | 2019-09-18 15:48:23 +0200 | [diff] [blame] | 56 | } |
| 57 | |
| 58 | } // namespace webrtc |
| 59 | |
| 60 | #endif // RTC_BASE_NUMERICS_DIVIDE_ROUND_H_ |