mrd_prime 0.1.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +7 -0
- data/.gitignore +23 -0
- data/.rspec +3 -0
- data/.travis.yml +6 -0
- data/Gemfile +7 -0
- data/README.md +62 -0
- data/Rakefile +6 -0
- data/bin/console +14 -0
- data/bin/setup +8 -0
- data/lib/mrd_prime.rb +79 -0
- data/lib/mrd_prime/version.rb +3 -0
- data/mrd_prime.gemspec +27 -0
- metadata +72 -0
checksums.yaml
ADDED
@@ -0,0 +1,7 @@
|
|
1
|
+
---
|
2
|
+
SHA256:
|
3
|
+
metadata.gz: d17143e5a145a9c98fc99c910d98bfb27a9fe6a097998ce57685e14a6a0e28db
|
4
|
+
data.tar.gz: 8f3ad79e530c346e598298c94605a39f8c4460e7eef05e5a6bc3c86465fba9ee
|
5
|
+
SHA512:
|
6
|
+
metadata.gz: 6f18db85331ff59361692fb557ce7811fdd443e07a86eb20493f295d0d64ab25e7d4cfcfa78641a6fc70f638f69fe72d0dd185cccefdb1556e2b5f63ed2b2fd9
|
7
|
+
data.tar.gz: f77022bba5faa89d1778316cf06fe5ffb720088bcd6b23990af4deed6a71db6092f85caaf466e7e27dd90da53effa651d321f3953374c3d9b039f7de875fcff4
|
data/.gitignore
ADDED
@@ -0,0 +1,23 @@
|
|
1
|
+
/.bundle/
|
2
|
+
/.yardoc
|
3
|
+
/_yardoc/
|
4
|
+
/coverage/
|
5
|
+
/doc/
|
6
|
+
/pkg/
|
7
|
+
/spec/reports/
|
8
|
+
/tmp/
|
9
|
+
|
10
|
+
# rspec failure tracking
|
11
|
+
.rspec_status
|
12
|
+
|
13
|
+
.vscode/*
|
14
|
+
!.vscode/settings.json
|
15
|
+
!.vscode/tasks.json
|
16
|
+
!.vscode/launch.json
|
17
|
+
!.vscode/extensions.json
|
18
|
+
*.code-workspace
|
19
|
+
|
20
|
+
# Local History for Visual Studio Code
|
21
|
+
.history/
|
22
|
+
|
23
|
+
Gemfile.lock
|
data/.rspec
ADDED
data/.travis.yml
ADDED
data/Gemfile
ADDED
data/README.md
ADDED
@@ -0,0 +1,62 @@
|
|
1
|
+
# MrdPrime
|
2
|
+
|
3
|
+
Miller-Rabin Prime Number Determination.
|
4
|
+
|
5
|
+
A small number(~2^81) makes a definitive decision.
|
6
|
+
A large number will fallback to `OpenSSL::BN::prime?`.
|
7
|
+
|
8
|
+
### About the amount of calculation
|
9
|
+
|
10
|
+
In order to reduce the amount of calculation, a decision is made using the minimum amount of calculation.
|
11
|
+
For example, just testing on 2 will determine up to 2047.
|
12
|
+
Testing on 2 and 3, gives a decision up to 1373653.
|
13
|
+
|
14
|
+
https://en.wikipedia.org/wiki/Miller%E2%80%93Rabin_primality_test#Testing_against_small_sets_of_bases
|
15
|
+
"if n < 3,317,044,064,679,887,385,961,981,
|
16
|
+
it is enough to test a = 2, 3, 5, 7, 11, 13, 17, 19, 23, 29, 31, 37, and 41.
|
17
|
+
and the result will be deterministic."
|
18
|
+
|
19
|
+
## Installation
|
20
|
+
|
21
|
+
Add this line to your application's Gemfile:
|
22
|
+
|
23
|
+
```
|
24
|
+
gem 'mrd_prime'
|
25
|
+
```
|
26
|
+
|
27
|
+
And then execute:
|
28
|
+
|
29
|
+
```
|
30
|
+
$ bundle install
|
31
|
+
```
|
32
|
+
|
33
|
+
Or install it yourself as:
|
34
|
+
|
35
|
+
```
|
36
|
+
$ gem install mrd_prime
|
37
|
+
```
|
38
|
+
|
39
|
+
## Usage
|
40
|
+
|
41
|
+
```
|
42
|
+
require 'mrd_prime'
|
43
|
+
|
44
|
+
small_number = (2**79 + 23)
|
45
|
+
|
46
|
+
puts( small_number.mrd_prime? ) #=> true
|
47
|
+
```
|
48
|
+
|
49
|
+
If you want to use the name `prime?`, you can alias it.
|
50
|
+
|
51
|
+
```rb
|
52
|
+
class Integer
|
53
|
+
alias_method :prime?, :mrd_prime?
|
54
|
+
end
|
55
|
+
|
56
|
+
puts( (2**79 + 23).prime? ) #=> true
|
57
|
+
```
|
58
|
+
|
59
|
+
## Contributing
|
60
|
+
|
61
|
+
Bug reports and pull requests are welcome on GitHub at https://github.com/Matsuyanagi/mrd_prime .
|
62
|
+
|
data/Rakefile
ADDED
data/bin/console
ADDED
@@ -0,0 +1,14 @@
|
|
1
|
+
#!/usr/bin/env ruby
|
2
|
+
|
3
|
+
require "bundler/setup"
|
4
|
+
require "mrd_prime"
|
5
|
+
|
6
|
+
# You can add fixtures and/or initialization code here to make experimenting
|
7
|
+
# with your gem easier. You can also use a different console, if you like.
|
8
|
+
|
9
|
+
# (If you use this, don't forget to add pry to your Gemfile!)
|
10
|
+
# require "pry"
|
11
|
+
# Pry.start
|
12
|
+
|
13
|
+
require "irb"
|
14
|
+
IRB.start(__FILE__)
|
data/bin/setup
ADDED
data/lib/mrd_prime.rb
ADDED
@@ -0,0 +1,79 @@
|
|
1
|
+
require "mrd_prime/version"
|
2
|
+
|
3
|
+
require 'openssl'
|
4
|
+
|
5
|
+
class Integer
|
6
|
+
# Returns true if +self+ is a prime number, else returns false.
|
7
|
+
#
|
8
|
+
# https://en.wikipedia.org/wiki/Miller%E2%80%93Rabin_primality_test
|
9
|
+
# https://oeis.org/A014233/list
|
10
|
+
#
|
11
|
+
# "if n < 3,317,044,064,679,887,385,961,981,
|
12
|
+
# it is enough to test a = 2, 3, 5, 7, 11, 13, 17, 19, 23, 29, 31, 37, and 41.
|
13
|
+
# and the result will be deterministic."
|
14
|
+
#
|
15
|
+
def mrd_prime?
|
16
|
+
|
17
|
+
return false if self < 2
|
18
|
+
return true if self < 4
|
19
|
+
return false if self.even?
|
20
|
+
|
21
|
+
prime_and_max = {
|
22
|
+
2 => 8321, # 2047. Strong pseudoprimes to base 2, [ 2047(=23x89), 3277(=29x113), 4033(=37x109), 4681(=31x151), 8321(=53x157) ] ~ 4681 is divided by a small prime number.
|
23
|
+
3 => 1373653,
|
24
|
+
5 => 25326001,
|
25
|
+
7 => 3215031751,
|
26
|
+
11 => 2152302898747,
|
27
|
+
13 => 3474749660383,
|
28
|
+
17 => 341550071728321,
|
29
|
+
19 => 341550071728321,
|
30
|
+
23 => 3825123056546413051,
|
31
|
+
29 => 3825123056546413051,
|
32
|
+
31 => 3825123056546413051,
|
33
|
+
37 => 318665857834031151167461,
|
34
|
+
41 => 3317044064679887385961981,
|
35
|
+
}
|
36
|
+
|
37
|
+
last_p = 1
|
38
|
+
prime_and_max.each do |p,m|
|
39
|
+
return true if self == p
|
40
|
+
return false if self % p == 0
|
41
|
+
last_p = p
|
42
|
+
end
|
43
|
+
return true if self < last_p * last_p
|
44
|
+
|
45
|
+
p_1 = self - 1
|
46
|
+
|
47
|
+
d = p_1
|
48
|
+
while d.even?
|
49
|
+
d >>= 1
|
50
|
+
end
|
51
|
+
|
52
|
+
prime_and_max.each do |a,m|
|
53
|
+
x = a.pow( d, self )
|
54
|
+
|
55
|
+
if x == 1
|
56
|
+
return true if self < m
|
57
|
+
next
|
58
|
+
end
|
59
|
+
|
60
|
+
td = d
|
61
|
+
while td != p_1 && x != p_1
|
62
|
+
x = x.pow( 2, self )
|
63
|
+
td <<= 1
|
64
|
+
end
|
65
|
+
|
66
|
+
if td == p_1
|
67
|
+
return false
|
68
|
+
else
|
69
|
+
return true if x == p_1 && self < m
|
70
|
+
end
|
71
|
+
|
72
|
+
end
|
73
|
+
|
74
|
+
# OpenSSL fallback
|
75
|
+
# return true
|
76
|
+
return OpenSSL::BN.new( self ).prime?
|
77
|
+
end
|
78
|
+
end
|
79
|
+
|
data/mrd_prime.gemspec
ADDED
@@ -0,0 +1,27 @@
|
|
1
|
+
require_relative 'lib/mrd_prime/version'
|
2
|
+
|
3
|
+
Gem::Specification.new do |spec|
|
4
|
+
spec.name = "mrd_prime"
|
5
|
+
spec.version = MrdPrime::VERSION
|
6
|
+
spec.authors = ["Matsuyanagi"]
|
7
|
+
spec.email = ["1475814+Matsuyanagi@users.noreply.github.com"]
|
8
|
+
|
9
|
+
spec.summary = %q{A definitive Miller-Rabin prime determination test for small numbers.}
|
10
|
+
spec.description = %q{A definitive Miller-Rabin prime determination test for small numbers (~2^81). For large numbers, fall back to OpenSSL::BN.}
|
11
|
+
spec.homepage = "https://github.com/Matsuyanagi/mrd_prime"
|
12
|
+
spec.required_ruby_version = Gem::Requirement.new(">= 2.3.0")
|
13
|
+
spec.license = "MIT"
|
14
|
+
|
15
|
+
spec.metadata["homepage_uri"] = spec.homepage
|
16
|
+
spec.metadata["source_code_uri"] = "https://github.com/Matsuyanagi/mrd_prime"
|
17
|
+
spec.metadata["changelog_uri"] = "https://github.com/Matsuyanagi/mrd_prime"
|
18
|
+
|
19
|
+
# Specify which files should be added to the gem when it is released.
|
20
|
+
# The `git ls-files -z` loads the files in the RubyGem that have been added into git.
|
21
|
+
spec.files = Dir.chdir(File.expand_path('..', __FILE__)) do
|
22
|
+
`git ls-files -z`.split("\x0").reject { |f| f.match(%r{^(test|spec|features)/}) }
|
23
|
+
end
|
24
|
+
|
25
|
+
spec.require_paths = ["lib"]
|
26
|
+
spec.add_dependency 'openssl', '~> 2'
|
27
|
+
end
|
metadata
ADDED
@@ -0,0 +1,72 @@
|
|
1
|
+
--- !ruby/object:Gem::Specification
|
2
|
+
name: mrd_prime
|
3
|
+
version: !ruby/object:Gem::Version
|
4
|
+
version: 0.1.0
|
5
|
+
platform: ruby
|
6
|
+
authors:
|
7
|
+
- Matsuyanagi
|
8
|
+
autorequire:
|
9
|
+
bindir: bin
|
10
|
+
cert_chain: []
|
11
|
+
date: 2020-08-07 00:00:00.000000000 Z
|
12
|
+
dependencies:
|
13
|
+
- !ruby/object:Gem::Dependency
|
14
|
+
name: openssl
|
15
|
+
requirement: !ruby/object:Gem::Requirement
|
16
|
+
requirements:
|
17
|
+
- - "~>"
|
18
|
+
- !ruby/object:Gem::Version
|
19
|
+
version: '2'
|
20
|
+
type: :runtime
|
21
|
+
prerelease: false
|
22
|
+
version_requirements: !ruby/object:Gem::Requirement
|
23
|
+
requirements:
|
24
|
+
- - "~>"
|
25
|
+
- !ruby/object:Gem::Version
|
26
|
+
version: '2'
|
27
|
+
description: A definitive Miller-Rabin prime determination test for small numbers
|
28
|
+
(~2^81). For large numbers, fall back to OpenSSL::BN.
|
29
|
+
email:
|
30
|
+
- 1475814+Matsuyanagi@users.noreply.github.com
|
31
|
+
executables: []
|
32
|
+
extensions: []
|
33
|
+
extra_rdoc_files: []
|
34
|
+
files:
|
35
|
+
- ".gitignore"
|
36
|
+
- ".rspec"
|
37
|
+
- ".travis.yml"
|
38
|
+
- Gemfile
|
39
|
+
- README.md
|
40
|
+
- Rakefile
|
41
|
+
- bin/console
|
42
|
+
- bin/setup
|
43
|
+
- lib/mrd_prime.rb
|
44
|
+
- lib/mrd_prime/version.rb
|
45
|
+
- mrd_prime.gemspec
|
46
|
+
homepage: https://github.com/Matsuyanagi/mrd_prime
|
47
|
+
licenses:
|
48
|
+
- MIT
|
49
|
+
metadata:
|
50
|
+
homepage_uri: https://github.com/Matsuyanagi/mrd_prime
|
51
|
+
source_code_uri: https://github.com/Matsuyanagi/mrd_prime
|
52
|
+
changelog_uri: https://github.com/Matsuyanagi/mrd_prime
|
53
|
+
post_install_message:
|
54
|
+
rdoc_options: []
|
55
|
+
require_paths:
|
56
|
+
- lib
|
57
|
+
required_ruby_version: !ruby/object:Gem::Requirement
|
58
|
+
requirements:
|
59
|
+
- - ">="
|
60
|
+
- !ruby/object:Gem::Version
|
61
|
+
version: 2.3.0
|
62
|
+
required_rubygems_version: !ruby/object:Gem::Requirement
|
63
|
+
requirements:
|
64
|
+
- - ">="
|
65
|
+
- !ruby/object:Gem::Version
|
66
|
+
version: '0'
|
67
|
+
requirements: []
|
68
|
+
rubygems_version: 3.1.4
|
69
|
+
signing_key:
|
70
|
+
specification_version: 4
|
71
|
+
summary: A definitive Miller-Rabin prime determination test for small numbers.
|
72
|
+
test_files: []
|