Skip to content

Commit b8f4521

Browse files
authored
Made gcd a free function
1 parent 4fbcb11 commit b8f4521

File tree

1 file changed

+30
-33
lines changed

1 file changed

+30
-33
lines changed

Sources/IntegerUtilities/GCD.swift

Lines changed: 30 additions & 33 deletions
Original file line numberDiff line numberDiff line change
@@ -9,39 +9,36 @@
99
//
1010
//===----------------------------------------------------------------------===//
1111

12-
extension BinaryInteger {
12+
/// The greatest common divisor of `a` and `b`.
13+
///
14+
/// If both inputs are zero, the result is zero. If one input is zero, the
15+
/// result is the absolute value of the other input.
16+
///
17+
/// [wiki]: https://en.wikipedia.org/wiki/Greatest_common_divisor
18+
@inlinable
19+
public func gcd<T: BinaryInteger>(_ a: T, _ b: T) -> T {
20+
var x = a.magnitude
21+
var y = b.magnitude
1322

14-
/// The greatest common divisor of `a` and `b`.
15-
///
16-
/// If both inputs are zero, the result is zero. If one input is zero, the
17-
/// result is the absolute value of the other input.
18-
///
19-
/// [wiki]: https://en.wikipedia.org/wiki/Greatest_common_divisor
20-
@inlinable
21-
public static func gcd(_ a: Self, _ b: Self) -> Self {
22-
var x = a.magnitude
23-
var y = b.magnitude
24-
25-
if x == 0 { return Self(y) }
26-
if y == 0 { return Self(x) }
27-
28-
let xtz = x.trailingZeroBitCount
29-
let ytz = y.trailingZeroBitCount
30-
31-
x >>= xtz
32-
y >>= ytz
33-
34-
// The binary GCD algorithm
35-
//
36-
// At the top of the loop both x and y are odd. Each pass removes at least
37-
// one low-order bit from the larger of the two, so the number of iterations
38-
// is bounded by the sum of the bit-widths of the inputs.
39-
while x != 0 {
40-
if x < y { swap(&x, &y) }
41-
x -= y
42-
x >>= x.trailingZeroBitCount
43-
}
44-
45-
return Self(y << min(xtz, ytz))
23+
if x == 0 { return T(y) }
24+
if y == 0 { return T(x) }
25+
26+
let xtz = x.trailingZeroBitCount
27+
let ytz = y.trailingZeroBitCount
28+
29+
x >>= xtz
30+
y >>= ytz
31+
32+
// The binary GCD algorithm
33+
//
34+
// At the top of the loop both x and y are odd. Each pass removes at least
35+
// one low-order bit from the larger of the two, so the number of iterations
36+
// is bounded by the sum of the bit-widths of the inputs.
37+
while x != 0 {
38+
if x < y { swap(&x, &y) }
39+
x -= y
40+
x >>= x.trailingZeroBitCount
4641
}
42+
43+
return T(y << min(xtz, ytz))
4744
}

0 commit comments

Comments
 (0)