@@ -320,11 +320,10 @@ Base.isempty(f::FactorIterator) = f.n == 1
320320# Uses a variety of algorithms depending on the size of n to find a factor.
321321# https://en.algorithmica.org/hpc/algorithms/factorization
322322# Cache of small factors for small numbers (n < 2^16)
323- # Trial division of small (< 2^16) precomputed primes
324- # Pollard rho's algorithm with Richard P. Brent optimizations
323+ # Trial division of small (< 2^16) precomputed primes and
324+ # Lenstra elliptic curve algorithm
325325# https://en.wikipedia.org/wiki/Trial_division
326- # https://en.wikipedia.org/wiki/Pollard%27s_rho_algorithm
327- # http://maths-people.anu.edu.au/~brent/pub/pub051.html
326+ # https://en.wikipedia.org/wiki/Lenstra_elliptic-curve_factorization
328327#
329328
330329"""
@@ -668,7 +667,7 @@ given by `f`. This method may be preferable to [`totient(::Integer)`](@ref)
668667when the factorization can be reused for other purposes.
669668"""
670669function totient (f:: Factorization{T} ) where T <: Integer
671- if iszero ( sign ( f))
670+ if ! isempty (f) && first ( first ( f)) == 0
672671 throw (ArgumentError (" ϕ(0) is not defined" ))
673672 end
674673 result = one (T)
@@ -687,16 +686,8 @@ positive integers less than or equal to ``n`` that are relatively prime to
687686The totient function of `n` when `n` is negative is defined to be
688687`totient(abs(n))`.
689688"""
690- function totient (n:: T ) where T<: Integer
691- n = abs (n)
692- if n == 0
693- throw (ArgumentError (" ϕ(0) is not defined" ))
694- end
695- result = one (T)
696- for (p, k) in eachfactor (n)
697- result *= p^ (k- 1 ) * (p - 1 )
698- end
699- result
689+ function totient (n:: Integer )
690+ totient (factor (abs (n)))
700691end
701692
702693# add: checked add (when makes sense), result of same type as first argument
@@ -984,90 +975,4 @@ julia> prevprimes(10, 10)
984975prevprimes (start:: T , n:: Integer ) where {T<: Integer } =
985976 collect (T, Iterators. take (prevprimes (start), n))
986977
987- """
988- divisors(n::Integer) -> Vector
989-
990- Return a vector with the positive divisors of `n`.
991-
992- For a nonzero integer `n` with prime factorization `n = p₁^k₁ ⋯ pₘ^kₘ`, `divisors(n)`
993- returns a vector of length (k₁ + 1)⋯(kₘ + 1) containing the divisors of `n` in
994- lexicographic (rather than numerical) order.
995-
996- `divisors(-n)` is equivalent to `divisors(n)`.
997-
998- For convenience, `divisors(0)` returns `[]`.
999-
1000- # Example
1001-
1002- ```jldoctest; filter = r"(\\ s+#.*)?"
1003- julia> divisors(60)
1004- 12-element Vector{Int64}:
1005- 1 # 1
1006- 2 # 2
1007- 4 # 2 * 2
1008- 3 # 3
1009- 6 # 3 * 2
1010- 12 # 3 * 2 * 2
1011- 5 # 5
1012- 10 # 5 * 2
1013- 20 # 5 * 2 * 2
1014- 15 # 5 * 3
1015- 30 # 5 * 3 * 2
1016- 60 # 5 * 3 * 2 * 2
1017-
1018- julia> divisors(-10)
1019- 4-element Vector{Int64}:
1020- 1
1021- 2
1022- 5
1023- 10
1024-
1025- julia> divisors(0)
1026- Int64[]
1027- ```
1028- """
1029- function divisors (n:: T ) where {T<: Integer }
1030- n = abs (n)
1031- if iszero (n)
1032- return T[]
1033- elseif isone (n)
1034- return [n]
1035- else
1036- return divisors (factor (n))
1037- end
1038- end
1039-
1040- """
1041- divisors(f::Factorization) -> Vector
1042-
1043- Return a vector with the positive divisors of the number whose factorization is `f`.
1044- Divisors are sorted lexicographically, rather than numerically.
1045- """
1046- function divisors (f:: Factorization{T} ) where T
1047- sgn = sign (f)
1048- if iszero (sgn) # n == 0
1049- return T[]
1050- elseif isempty (f) || length (f) == 1 && sgn < 0 # n == 1 or n == -1
1051- return [one (T)]
1052- end
1053-
1054- i = m = 1
1055- fs = rest (f, 1 + (sgn < 0 ))
1056- divs = Vector {T} (undef, prod (x -> x. second + 1 , fs))
1057- divs[i] = one (T)
1058-
1059- for (p, k) in fs
1060- i = 1
1061- for _ in 1 : k
1062- for j in i: (i+ m- 1 )
1063- divs[j+ m] = divs[j] * p
1064- end
1065- i += m
1066- end
1067- m += i - 1
1068- end
1069-
1070- return divs
1071- end
1072-
1073978end # module
0 commit comments