russian_inflect 0.0.1

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 ADDED
@@ -0,0 +1,15 @@
1
+ ---
2
+ !binary "U0hBMQ==":
3
+ metadata.gz: !binary |-
4
+ YTI0NjZlOWNhN2YyODc4YTk2NDBhOGZiMTgxY2IyMDUzNDI0MzljNw==
5
+ data.tar.gz: !binary |-
6
+ MzI4MzI0OTE5NTRmMzg3NTI1YzU5ODc5NmUxNGM5ODU0ZGE2NDgwYw==
7
+ !binary "U0hBNTEy":
8
+ metadata.gz: !binary |-
9
+ MDBkMTAzN2MyZDBlNTZlYzg4MDkyODkwMzMxMzc5ZDdkMDhmMjIzNmQzZDc2
10
+ MDI1Mjg1MGVkMzZhODQ5ODI3OWU2Y2UzNGZlZDA0Y2MwODY2ZDM5ODQxOWFh
11
+ NjMyM2M3MzQ1MTE4ZGRiMDFlZjI2ZDdiODhhMWYyMDMxOWUyODk=
12
+ data.tar.gz: !binary |-
13
+ YTJlOWQwMmQ1ODE4YjE0OWIxOTAzM2RmMDUwOWFiMzk5MGExM2MyMDFmMmM3
14
+ YTQ3OWYzNDFkNzMwZDU5ZGI5YzZjM2FhOTZkNmZhOTdmYzgwNjUwYTAwMDkw
15
+ YWQzOTQxZmY4OTNhODYyNjZkZmU2YzlkZjFmZDUwZGI5ZTZiMzE=
data/.gitignore ADDED
@@ -0,0 +1,17 @@
1
+ *.gem
2
+ *.rbc
3
+ .bundle
4
+ .config
5
+ .yardoc
6
+ Gemfile.lock
7
+ InstalledFiles
8
+ _yardoc
9
+ coverage
10
+ doc/
11
+ lib/bundler/man
12
+ pkg
13
+ rdoc
14
+ spec/reports
15
+ test/tmp
16
+ test/version_tmp
17
+ tmp
data/Gemfile ADDED
@@ -0,0 +1,4 @@
1
+ source 'https://rubygems.org'
2
+
3
+ # Specify your gem's dependencies in russian_inflect.gemspec
4
+ gemspec
data/LICENSE.txt ADDED
@@ -0,0 +1,22 @@
1
+ Copyright (c) 2013 Tõnis Simo
2
+
3
+ MIT License
4
+
5
+ Permission is hereby granted, free of charge, to any person obtaining
6
+ a copy of this software and associated documentation files (the
7
+ "Software"), to deal in the Software without restriction, including
8
+ without limitation the rights to use, copy, modify, merge, publish,
9
+ distribute, sublicense, and/or sell copies of the Software, and to
10
+ permit persons to whom the Software is furnished to do so, subject to
11
+ the following conditions:
12
+
13
+ The above copyright notice and this permission notice shall be
14
+ included in all copies or substantial portions of the Software.
15
+
16
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
17
+ EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
18
+ MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
19
+ NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
20
+ LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
21
+ OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
22
+ WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
data/README.md ADDED
@@ -0,0 +1,29 @@
1
+ # RussianInflect
2
+
3
+ TODO: Write a gem description
4
+
5
+ ## Installation
6
+
7
+ Add this line to your application's Gemfile:
8
+
9
+ gem 'russian_inflect'
10
+
11
+ And then execute:
12
+
13
+ $ bundle
14
+
15
+ Or install it yourself as:
16
+
17
+ $ gem install russian_inflect
18
+
19
+ ## Usage
20
+
21
+ TODO: Write usage instructions here
22
+
23
+ ## Contributing
24
+
25
+ 1. Fork it
26
+ 2. Create your feature branch (`git checkout -b my-new-feature`)
27
+ 3. Commit your changes (`git commit -am 'Add some feature'`)
28
+ 4. Push to the branch (`git push origin my-new-feature`)
29
+ 5. Create new Pull Request
data/Rakefile ADDED
@@ -0,0 +1 @@
1
+ require "bundler/gem_tasks"
@@ -0,0 +1,94 @@
1
+ # encoding: UTF-8
2
+
3
+ class RussianInflect
4
+ RULES = YAML.load_file(File.expand_path 'rules.yml', File.dirname(__FILE__))
5
+
6
+ class UnknownCaseException < Exception;;end
7
+ class UnknownRuleException < Exception;;end
8
+
9
+ # Набор методов для нахождения и применения правил к имени, фамилии и отчеству.
10
+ class Rules
11
+ def initialize(args)
12
+ @group = args
13
+ end
14
+
15
+ def inflect(word, gcase)
16
+ type = RussianInflect.detect_type(word)
17
+ find_and_apply(word, gcase, RussianInflect::RULES["#{@group.to_s}_group"][type.to_s])
18
+ end
19
+
20
+ protected
21
+
22
+ def match?(name, rule, match_whole_word)
23
+ name = UnicodeUtils.downcase(name)
24
+ rule['test'].each do |chars|
25
+ test = match_whole_word ? name : name.slice([name.size - chars.size, 0].max .. -1)
26
+ return true if test == chars
27
+ end
28
+
29
+ false
30
+ end
31
+
32
+ # Применить правило
33
+ def apply(name, gcase, rule)
34
+ modificator_for(gcase, rule).each_char do |char|
35
+ case char
36
+ when '.'
37
+ when '-'
38
+ name = name.slice(0, name.size - 1)
39
+ else
40
+ name += char
41
+ end
42
+ end
43
+
44
+ name
45
+ end
46
+
47
+ # Найти правило и применить к имени с учетом склонения
48
+ def find_and_apply(name, gcase, rules)
49
+ rule = find_for(name, rules)
50
+ apply(name, gcase, rule)
51
+ rescue UnknownRuleException
52
+ # Если не найдено правило для имени, возвращаем неизмененное имя.
53
+ name
54
+ end
55
+
56
+ # Найти подходящее правило в исключениях или суффиксах
57
+ def find_for(name, rules)
58
+ # Сначала пытаемся найти исключения
59
+ if rules.has_key?('exceptions')
60
+ p = find(name, rules['exceptions'], true)
61
+ return p if p
62
+ end
63
+
64
+ # Не получилось, ищем в суффиксах. Если не получилось найти и в них,
65
+ # возвращаем неизмененное имя.
66
+ find(name, rules['suffixes'], false) or raise UnknownRuleException, "Cannot find rule for #{name}"
67
+ end
68
+
69
+ # Найти подходящее правило в конкретном списке правил
70
+ def find(name, rules, match_whole_word)
71
+ rules.find { |rule| match?(name, rule, match_whole_word) }
72
+ end
73
+
74
+ # Получить модификатор из указанного правиля для указанного склонения
75
+ def modificator_for(gcase, rule)
76
+ case gcase.to_sym
77
+ when NOMINATIVE
78
+ '.'
79
+ when GENITIVE
80
+ rule['mods'][0]
81
+ when DATIVE
82
+ rule['mods'][1]
83
+ when ACCUSATIVE
84
+ rule['mods'][2]
85
+ when INSTRUMENTAL
86
+ rule['mods'][3]
87
+ when PREPOSITIONAL
88
+ rule['mods'][4]
89
+ else
90
+ raise UnknownCaseException, "Unknown grammatic case: #{gcase}"
91
+ end
92
+ end
93
+ end
94
+ end
@@ -0,0 +1,70 @@
1
+ prepositions: [в, без, до, из, к, на, по, о, от, перед, при, через, у, за, над, об, под, про, для, с, со, без]
2
+
3
+ first_group:
4
+ adjective:
5
+ suffixes:
6
+ -
7
+ test: [ая]
8
+ mods: [--ой, --ой, --ую, --ой, --ой]
9
+ -
10
+ test: [яя]
11
+ mods: [--ей, --ей, --юю, --ей, --ей]
12
+ -
13
+ test: [ые, ие]
14
+ mods: [-х, -м, ., -ми, -х]
15
+ noun:
16
+ suffixes:
17
+ -
18
+ test: [а]
19
+ mods: [-и, -е, -у, -ой, -е]
20
+ -
21
+ test: [я]
22
+ mods: [-и, -е, -ю, -ей, -е]
23
+ -
24
+ test: [и]
25
+ mods: [--ок, -ам, ., -ами, -ах]
26
+
27
+ second_group:
28
+ adjective:
29
+ suffixes:
30
+ -
31
+ test: [ое, ый]
32
+ mods: [-ого, -ому, ., -ым, -ых]
33
+ -
34
+ test: [ее, ий]
35
+ mods: [-его, -ему, ., -им, -их]
36
+ noun:
37
+ suffixes:
38
+ -
39
+ test: [б, в, г, д, ж, з, к, л, м, н, п, р, с, т, ф, х, ц, ч]
40
+ mods: [а, у, ., ом, е]
41
+ -
42
+ test: [о]
43
+ mods: [-а, -у, ., м, -е]
44
+ -
45
+ test: [е]
46
+ mods: [-я, -ю, ., м, .]
47
+ -
48
+ test: [ы]
49
+ mods: [-ов, -ам, ., -ами, -ах]
50
+
51
+ third_group:
52
+ adjective:
53
+ suffixes:
54
+ -
55
+ test: [ая]
56
+ mods: [--ой, --ой, --ую, --ой, --ой]
57
+ -
58
+ test: [яя]
59
+ mods: [--ей, --ей, --юю, --ей, --ей]
60
+ -
61
+ test: [ые, ие]
62
+ mods: [-х, -м, ., -ми, -х]
63
+ noun:
64
+ suffixes:
65
+ -
66
+ test: [ь]
67
+ mods: [-и, -и, ., -ью, -и]
68
+ -
69
+ test: [мя]
70
+ mods: [-ени, --ени, ., -енем, -ени]
@@ -0,0 +1,3 @@
1
+ class RussianInflect
2
+ VERSION = "0.0.1"
3
+ end
@@ -0,0 +1,64 @@
1
+ # encoding: UTF-8
2
+
3
+ require 'yaml'
4
+ require 'unicode_utils'
5
+ require 'active_support'
6
+ require 'russian_inflect/rules'
7
+ require "russian_inflect/version"
8
+
9
+ class RussianInflect
10
+ CASES = [:nominative, :genitive, :dative, :accusative, :instrumental, :prepositional]
11
+ GROUPS = [nil, :first, :second, :third]
12
+
13
+ NOMINATIVE = :nominative # именительный
14
+ GENITIVE = :genitive # родительный
15
+ DATIVE = :dative # дательный
16
+ ACCUSATIVE = :accusative # винительный
17
+ INSTRUMENTAL = :instrumental # творительный
18
+ PREPOSITIONAL = :prepositional # предложный
19
+
20
+ attr_accessor :words, :noun, :case_group
21
+
22
+ def initialize(text, options = {})
23
+ @words = text.split
24
+ @noun = case options[:noun]
25
+ when String then options[:noun]
26
+ when Fixnum then @words[options[:noun]]
27
+ else @words[0]
28
+ end
29
+ group = options[:group].presence || self.class.detect_case_group(@noun)
30
+ @case_group = GROUPS[group]
31
+ end
32
+
33
+ def to_case(gcase)
34
+ after_prepositions = false
35
+ inflected_words = words.map do |word|
36
+ result = word
37
+ unless after_prepositions
38
+ if word.in?(RULES['prepositions'])
39
+ after_prepositions = true
40
+ else
41
+ result = Rules.new(case_group).inflect(word, gcase)
42
+ end
43
+ end
44
+ result
45
+ end
46
+ inflected_words.join(' ')
47
+ end
48
+
49
+ def self.detect_case_group(noun)
50
+ case noun
51
+ when /(а|я|и)$/i then 1
52
+ when /(о|е|ы)$/i then 2
53
+ when /(мя|ь)$/i then 3
54
+ else 2
55
+ end
56
+ end
57
+
58
+ def self.detect_type(word)
59
+ case word
60
+ when /(ая|яя|ые|ие|ый|ий|ое|ее)$/i then :adjective
61
+ else :noun
62
+ end
63
+ end
64
+ end
@@ -0,0 +1,26 @@
1
+ # encoding: UTF-8
2
+
3
+ lib = File.expand_path('../lib', __FILE__)
4
+ $LOAD_PATH.unshift(lib) unless $LOAD_PATH.include?(lib)
5
+ require 'russian_inflect/version'
6
+
7
+ Gem::Specification.new do |spec|
8
+ spec.name = "russian_inflect"
9
+ spec.version = RussianInflect::VERSION
10
+ spec.authors = ["Tõnis Simo"]
11
+ spec.email = ["anton.estum@gmail.com"]
12
+ spec.description = %q{Склонение по падежам заголовков на русском языке}
13
+ spec.summary = %q{Склоняет заданный заголовок по падежам}
14
+ spec.homepage = "https://github.com/estum/russian_inflect"
15
+ spec.license = "MIT"
16
+
17
+ spec.files = `git ls-files`.split($/)
18
+ spec.executables = spec.files.grep(%r{^bin/}) { |f| File.basename(f) }
19
+ spec.test_files = spec.files.grep(%r{^(test|spec|features)/})
20
+ spec.require_paths = ["lib"]
21
+
22
+ spec.add_dependency "activesupport", ">= 3.0.0"
23
+ spec.add_dependency "unicode_utils", "~> 1.4"
24
+ spec.add_development_dependency "bundler", "~> 1.3"
25
+ spec.add_development_dependency "rake"
26
+ end
metadata ADDED
@@ -0,0 +1,110 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: russian_inflect
3
+ version: !ruby/object:Gem::Version
4
+ version: 0.0.1
5
+ platform: ruby
6
+ authors:
7
+ - Tõnis Simo
8
+ autorequire:
9
+ bindir: bin
10
+ cert_chain: []
11
+ date: 2013-07-12 00:00:00.000000000 Z
12
+ dependencies:
13
+ - !ruby/object:Gem::Dependency
14
+ name: activesupport
15
+ requirement: !ruby/object:Gem::Requirement
16
+ requirements:
17
+ - - ! '>='
18
+ - !ruby/object:Gem::Version
19
+ version: 3.0.0
20
+ type: :runtime
21
+ prerelease: false
22
+ version_requirements: !ruby/object:Gem::Requirement
23
+ requirements:
24
+ - - ! '>='
25
+ - !ruby/object:Gem::Version
26
+ version: 3.0.0
27
+ - !ruby/object:Gem::Dependency
28
+ name: unicode_utils
29
+ requirement: !ruby/object:Gem::Requirement
30
+ requirements:
31
+ - - ~>
32
+ - !ruby/object:Gem::Version
33
+ version: '1.4'
34
+ type: :runtime
35
+ prerelease: false
36
+ version_requirements: !ruby/object:Gem::Requirement
37
+ requirements:
38
+ - - ~>
39
+ - !ruby/object:Gem::Version
40
+ version: '1.4'
41
+ - !ruby/object:Gem::Dependency
42
+ name: bundler
43
+ requirement: !ruby/object:Gem::Requirement
44
+ requirements:
45
+ - - ~>
46
+ - !ruby/object:Gem::Version
47
+ version: '1.3'
48
+ type: :development
49
+ prerelease: false
50
+ version_requirements: !ruby/object:Gem::Requirement
51
+ requirements:
52
+ - - ~>
53
+ - !ruby/object:Gem::Version
54
+ version: '1.3'
55
+ - !ruby/object:Gem::Dependency
56
+ name: rake
57
+ requirement: !ruby/object:Gem::Requirement
58
+ requirements:
59
+ - - ! '>='
60
+ - !ruby/object:Gem::Version
61
+ version: '0'
62
+ type: :development
63
+ prerelease: false
64
+ version_requirements: !ruby/object:Gem::Requirement
65
+ requirements:
66
+ - - ! '>='
67
+ - !ruby/object:Gem::Version
68
+ version: '0'
69
+ description: Склонение по падежам заголовков на русском языке
70
+ email:
71
+ - anton.estum@gmail.com
72
+ executables: []
73
+ extensions: []
74
+ extra_rdoc_files: []
75
+ files:
76
+ - .gitignore
77
+ - Gemfile
78
+ - LICENSE.txt
79
+ - README.md
80
+ - Rakefile
81
+ - lib/russian_inflect.rb
82
+ - lib/russian_inflect/rules.rb
83
+ - lib/russian_inflect/rules.yml
84
+ - lib/russian_inflect/version.rb
85
+ - russian_inflect.gemspec
86
+ homepage: https://github.com/estum/russian_inflect
87
+ licenses:
88
+ - MIT
89
+ metadata: {}
90
+ post_install_message:
91
+ rdoc_options: []
92
+ require_paths:
93
+ - lib
94
+ required_ruby_version: !ruby/object:Gem::Requirement
95
+ requirements:
96
+ - - ! '>='
97
+ - !ruby/object:Gem::Version
98
+ version: '0'
99
+ required_rubygems_version: !ruby/object:Gem::Requirement
100
+ requirements:
101
+ - - ! '>='
102
+ - !ruby/object:Gem::Version
103
+ version: '0'
104
+ requirements: []
105
+ rubyforge_project:
106
+ rubygems_version: 2.0.3
107
+ signing_key:
108
+ specification_version: 4
109
+ summary: Склоняет заданный заголовок по падежам
110
+ test_files: []