learn_words 0.1.0

Sign up to get free protection for your applications and to get access to all the features.
data/MIT-LICENSE ADDED
@@ -0,0 +1,21 @@
1
+ Copyright (c) 2010 Vladimir Parfinenko
2
+
3
+ Permission is hereby granted, free of charge, to any person obtaining
4
+ a copy of this software and associated documentation files (the
5
+ "Software"), to deal in the Software without restriction, including
6
+ without limitation the rights to use, copy, modify, merge, publish,
7
+ distribute, sublicense, and/or sell copies of the Software, and to
8
+ permit persons to whom the Software is furnished to do so, subject to
9
+ the following conditions:
10
+
11
+ The above copyright notice and this permission notice shall be
12
+ included in all copies or substantial portions of the Software.
13
+
14
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
15
+ EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
16
+ MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
17
+ NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
18
+ LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
19
+ OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
20
+ WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
21
+
data/Manifest ADDED
@@ -0,0 +1,6 @@
1
+ MIT-LICENSE
2
+ Manifest
3
+ README
4
+ Rakefile
5
+ bin/learn_words
6
+ lib/learn_words.rb
data/README ADDED
@@ -0,0 +1,6 @@
1
+ Usage: learn_words FILE [--limit N] [--part M/K]
2
+
3
+ FILE format:
4
+ any number of lines with two words separated by <Tab>.
5
+ Note: if there are more than one variant for
6
+ translation, separate them by "/"
data/Rakefile ADDED
@@ -0,0 +1,13 @@
1
+ require 'rubygems'
2
+ require 'rake'
3
+ require 'echoe'
4
+
5
+ Echoe.new('learn_words', '0.1.0') do |p|
6
+ p.description = "Simple script for learning foreign language words"
7
+ p.url = "http://github.com/cypok/learn_words"
8
+ p.author = "Vladimir Parfinenko"
9
+ p.email = "vladimir.parfinenko@gmail.com"
10
+ p.ignore_pattern = ["tmp/*", "script/*"]
11
+ p.runtime_dependencies = ["highline"]
12
+ end
13
+
data/bin/learn_words ADDED
@@ -0,0 +1,4 @@
1
+ #!/usr/bin/env ruby
2
+ require 'learn_words'
3
+
4
+ LearnWords.run ARGV
@@ -0,0 +1,37 @@
1
+ # -*- encoding: utf-8 -*-
2
+
3
+ Gem::Specification.new do |s|
4
+ s.name = %q{learn_words}
5
+ s.version = "0.1.0"
6
+
7
+ s.required_rubygems_version = Gem::Requirement.new(">= 1.2") if s.respond_to? :required_rubygems_version=
8
+ s.authors = ["Vladimir Parfinenko"]
9
+ s.cert_chain = ["/Users/cypok/.gem/gem-public_cert.pem"]
10
+ s.date = %q{2010-10-07}
11
+ s.default_executable = %q{learn_words}
12
+ s.description = %q{Simple script for learning foreign language words}
13
+ s.email = %q{vladimir.parfinenko@gmail.com}
14
+ s.executables = ["learn_words"]
15
+ s.extra_rdoc_files = ["README", "bin/learn_words", "lib/learn_words.rb"]
16
+ s.files = ["MIT-LICENSE", "Manifest", "README", "Rakefile", "bin/learn_words", "lib/learn_words.rb", "learn_words.gemspec"]
17
+ s.homepage = %q{http://github.com/cypok/learn_words}
18
+ s.rdoc_options = ["--line-numbers", "--inline-source", "--title", "Learn_words", "--main", "README"]
19
+ s.require_paths = ["lib"]
20
+ s.rubyforge_project = %q{learn_words}
21
+ s.rubygems_version = %q{1.3.7}
22
+ s.signing_key = %q{/Users/cypok/.gem/gem-private_key.pem}
23
+ s.summary = %q{Simple script for learning foreign language words}
24
+
25
+ if s.respond_to? :specification_version then
26
+ current_version = Gem::Specification::CURRENT_SPECIFICATION_VERSION
27
+ s.specification_version = 3
28
+
29
+ if Gem::Version.new(Gem::VERSION) >= Gem::Version.new('1.2.0') then
30
+ s.add_runtime_dependency(%q<highline>, [">= 0"])
31
+ else
32
+ s.add_dependency(%q<highline>, [">= 0"])
33
+ end
34
+ else
35
+ s.add_dependency(%q<highline>, [">= 0"])
36
+ end
37
+ end
@@ -0,0 +1,237 @@
1
+ #!/usr/bin/env ruby
2
+
3
+ require 'rubygems'
4
+ require 'highline/import'
5
+
6
+ ###############################################################
7
+ # READING WORDS FILE
8
+ ###############################################################
9
+
10
+ class Word
11
+ attr_reader :orig, :trans, :variants_number
12
+ attr_accessor :times_asked, :times_answered, :limit
13
+
14
+ def initialize(orig, trans, limit)
15
+ @orig = orig
16
+ @trans = trans.split "/"
17
+ @variants_number = @trans.length
18
+ @times_asked = 0
19
+ @times_answered = 0
20
+ @limit = limit
21
+ end
22
+
23
+ def frequency
24
+ if @times_asked == 0
25
+ learnt? ? 1.0 : 0.0
26
+ else
27
+ @times_answered.to_f / @times_asked.to_f
28
+ end
29
+ end
30
+
31
+ def asked(answers)
32
+ @times_asked += 1
33
+ if answers.map( &:downcase ).sort == trans.map( &:downcase ).sort
34
+ @times_answered += 1
35
+ true
36
+ else
37
+ false
38
+ end
39
+ end
40
+
41
+ def favour
42
+ 3*frequency + @times_asked
43
+ end
44
+
45
+ def learnt?
46
+ @times_answered >= @limit
47
+ end
48
+
49
+ def learn!
50
+ @limit = @times_answered
51
+ end
52
+ end
53
+
54
+
55
+ class LearnWords
56
+ ###############################################################
57
+ # PROCESSING COMMAND LINE OPTIONS
58
+ ###############################################################
59
+
60
+ # TODO: use optparser !!!
61
+ # TODO: use ansicolor instead of highline !!!
62
+
63
+ USAGE = <<-STR
64
+ Usage: learn_words FILE [--limit N] [--part M/K]
65
+ STR
66
+
67
+ def self.exit_with_usage(str = nil)
68
+ puts USAGE
69
+ puts("\n" + str) unless str.nil?
70
+ exit 1
71
+ end
72
+
73
+ def self.run(args)
74
+
75
+ limit = 3
76
+ part = 1
77
+ parts_count = 1
78
+ words_file = nil
79
+
80
+ begin
81
+ if (i = args.index '--limit')
82
+ args.delete_at i
83
+ limit = args.delete_at i
84
+ raise unless limit =~ /\d+/
85
+ limit = limit.to_i
86
+ end
87
+
88
+ if (i = args.index '--part')
89
+ args.delete_at i
90
+ match = args.delete_at(i).match /(\d+)\/(\d+)/
91
+ part = match[1].to_i
92
+ parts_count = match[2].to_i
93
+ raise if parts_count == 0 or part == 0 or part > parts_count
94
+ end
95
+
96
+ raise if args.count != 1
97
+ words_file = args.first
98
+ rescue
99
+ exit_with_usage
100
+ end
101
+
102
+ words = []
103
+ begin
104
+ open(words_file) do |file|
105
+ file.lines.each do |line|
106
+ next if line.strip.empty? # pass blank lines
107
+ parts = line.split( "\t" ).map{ |x| x.strip }.delete_if{ |x| x.empty? }
108
+ words << Word.new( parts[1], parts[0], limit ) unless line.start_with? '#'
109
+ end
110
+ end
111
+ rescue Exception => e
112
+ exit_with_usage e.message
113
+ end
114
+
115
+ ###############################################################
116
+ # PART WORDS
117
+ ###############################################################
118
+
119
+ total_words_count = words.count
120
+
121
+ # words per part
122
+ wpp = words.count / parts_count
123
+ left = (part-1) * wpp
124
+ right = part * wpp
125
+ if part == parts_count
126
+ # reminder to last part
127
+ right = words.count
128
+ end
129
+ words = words[left...right]
130
+
131
+ ###############################################################
132
+ # WELCOME MESSAGE
133
+ ###############################################################
134
+
135
+ say %{ <%= color(' Learn Words ! ', GREEN+UNDERLINE) %>}
136
+ say %{ <%= color('made by Vladimir Parfinenko aka cypok', GREEN) %>}
137
+ say %{ <%= color(' some fixes by Ivan Novikov aka NIA ', GREEN) %>}
138
+ STDOUT.write "\n"
139
+ say %{Note: if there are more than one variant,}
140
+ say %{separate them by "/" or enter one by one}
141
+ STDOUT.write "\n"
142
+ say %{Type "?" to get stats, "!" to mark as learnt}
143
+ say %{and "exit" to quit}
144
+ STDOUT.write "\n"
145
+ say %{<%= color('Current limit of learning is set to #{limit}', BLUE) %>}
146
+ say %{<%= color('Total #{total_words_count} words to learn', BLUE) %>}
147
+ if parts_count != 1
148
+ say %{<%= color('Part #{part} of #{parts_count}: #{words.count} words to learn', BLUE) %>}
149
+ end
150
+ STDOUT.write "\n"
151
+
152
+ ###############################################################
153
+ # MAIN LOOP
154
+ ###############################################################
155
+
156
+ answers = []
157
+ word = nil
158
+ while true
159
+ begin
160
+ local_words = words.sort_by { rand }.find_all { |w| not w.learnt? }
161
+
162
+ break if local_words.size == 0
163
+
164
+ min_favour = local_words.map{ |x| x.favour}.min
165
+
166
+ d = 0.25
167
+ word_prev = word
168
+ word = local_words.find { |x| x.favour <= (min_favour + d) }
169
+ while word == word_prev && local_words.count > 1
170
+ local_words = local_words.sort_by { rand }
171
+ d += 0.25
172
+ word = local_words.find { |x| x.favour <= (min_favour + d) }
173
+ end
174
+
175
+ variants_msg = word.variants_number == 1 ? "" : " (#{word.variants_number} variants)"
176
+ say %{< <%= color(%q[#{word.orig}], YELLOW) %>#{variants_msg}}
177
+
178
+ answers = []
179
+ while answers.length < word.variants_number and not answers.include? "exit"
180
+ STDOUT.write "> "
181
+ answers += STDIN.readline.split( "/" ).map( &:strip )
182
+
183
+ break if ['', 'exit', '!', '?'].any? {|s| answers.include? s }
184
+ end
185
+ break if answers.include? "exit"
186
+
187
+ if answers.include? "!"
188
+ STDOUT.write "Are you sure you learnt this? (yes/no) > "
189
+ if STDIN.readline.strip == 'yes'
190
+ # mark the word as learnt
191
+ word.learn!
192
+ say %{< #{word.times_answered}/#{word.times_asked}\t<%= color('Learnt!', BLUE) %>}
193
+ else
194
+ say %{< #{word.times_answered}/#{word.times_asked}}
195
+ end
196
+ elsif answers.include? "?"
197
+ total_to_answer = words.map {|w| w.limit }.reduce(&:+)
198
+ already_answered = words.map {|w| w.times_answered }.reduce(&:+)
199
+
200
+ say %{< Already answered #{already_answered} times correctly}
201
+ say %{< There will be #{total_to_answer-already_answered} questions more}
202
+ else
203
+ if word.asked(answers)
204
+ say %{< #{word.times_answered}/#{word.times_asked}\t<%= color('OK!', GREEN) %>}
205
+ else
206
+ verb = ( word.variants_number != 1 ) ? "were" : "was"
207
+ right_strings = word.trans.map{|t| '"'+t+'"' }.join ", "
208
+ say %{< #{word.times_answered}/#{word.times_asked}\t<%= color(%q[WRONG! Right #{verb} #{right_strings}!], BOLD+RED+UNDERLINE) %>}
209
+ end
210
+ end
211
+ STDOUT.write "\n"
212
+ rescue EOFError, Interrupt
213
+ break
214
+ end
215
+ end
216
+
217
+ ###############################################################
218
+ # RESULTS
219
+ ###############################################################
220
+
221
+ STDOUT.write "\n"
222
+ say %{<%= color('Your results:', GREEN) %>}
223
+ words = words.sort do |x, y|
224
+ if x.frequency == y.frequency
225
+ x.trans <=> y.trans
226
+ else
227
+ -( x.frequency <=> y.frequency )
228
+ end
229
+ end
230
+ max_trans_length = words.map {|w| w.trans.join('/').length }.max
231
+ words.each do |word|
232
+ freq = (word.frequency*100).to_i.to_s.rjust(3)
233
+ trans = word.trans.join('/').ljust(max_trans_length, ' ')
234
+ say %{<%= color(%q[#{freq}% #{word.times_answered}/#{word.times_asked} #{trans} #{word.orig}], BLUE) %>}
235
+ end
236
+ end
237
+ end
data.tar.gz.sig ADDED
@@ -0,0 +1,2 @@
1
+ /�]j��Չ�$�[7v��Pf7�[>k_��骐����J��߱�t*Z�0�Y`�:�Jl}�7�-������P�I
2
+ /�s�h���f˜����{�4� �'���EH�٢�z�T�(nn��V�)Dѕ~a�{�-/d4�4��%O����>������ ��*-��
metadata ADDED
@@ -0,0 +1,115 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: learn_words
3
+ version: !ruby/object:Gem::Version
4
+ hash: 27
5
+ prerelease: false
6
+ segments:
7
+ - 0
8
+ - 1
9
+ - 0
10
+ version: 0.1.0
11
+ platform: ruby
12
+ authors:
13
+ - Vladimir Parfinenko
14
+ autorequire:
15
+ bindir: bin
16
+ cert_chain:
17
+ - |
18
+ -----BEGIN CERTIFICATE-----
19
+ MIIDSDCCAjCgAwIBAgIBADANBgkqhkiG9w0BAQUFADBKMRwwGgYDVQQDDBN2bGFk
20
+ aW1pci5wYXJmaW5lbmtvMRUwEwYKCZImiZPyLGQBGRYFZ21haWwxEzARBgoJkiaJ
21
+ k/IsZAEZFgNjb20wHhcNMTAwOTE1MDg0MTM2WhcNMTEwOTE1MDg0MTM2WjBKMRww
22
+ GgYDVQQDDBN2bGFkaW1pci5wYXJmaW5lbmtvMRUwEwYKCZImiZPyLGQBGRYFZ21h
23
+ aWwxEzARBgoJkiaJk/IsZAEZFgNjb20wggEiMA0GCSqGSIb3DQEBAQUAA4IBDwAw
24
+ ggEKAoIBAQCvZkpRSuCHyoPAGvQzWo6JTxJIYpPglVbJalWLUouWhcGewCFcoGpy
25
+ jSkyG1nFUa2AdfEf9x39ZJeRRN7rbH1pcWsXbyMXojWjJ6XhjPL7IlWR1U70qYKO
26
+ c27RdnFhtnd7acXkx/tPrOk/Z/MYVdl9zYXa1gT+uXIWd+M/CS8sRgjSsf3Uxty/
27
+ hObfwgNzWcBCC2iLbi+WTWrvAqO6nj9uRiktEowVH3hUQeg0RQ5PALtmwEGxlfJ6
28
+ HtcL7sKP5lGUkJ8/ZDUofOgkatJmA8V98Qpz3SSEGbPcGw9vtm2lKThwb/6BJ8mO
29
+ fsBh9jiK1ccDVCJmtSJpsIBfxgIyZz7zAgMBAAGjOTA3MAkGA1UdEwQCMAAwCwYD
30
+ VR0PBAQDAgSwMB0GA1UdDgQWBBTPzkzZ+7oNX5uWByxqDPaCcxL2izANBgkqhkiG
31
+ 9w0BAQUFAAOCAQEAd0d1BgRz8j+M599IbrQtJOE7IwcmmKM7oQ36mtfb/+MpMZtt
32
+ AI6gbwF5mO9PgWduOjsefH0YI54gjbEH5LeU+eX18WyZPjFtPPQA9oV2e87EcLMU
33
+ N9DLKwhaZrZw0Hkpj9RxguPmoOKds8sRK9OLg1iiLx42sLQ+T6eIn5g0y6QHN9fW
34
+ f8O73LNFaCcG5dfl0dQU0gjJEJ4OsgSpSob1Vxhcoz6U1XTQmj7ZUqMn5qKq9Nh0
35
+ a2F49GO07YddCacBqSjA4DZoQxVsdruI7dtOcvHYvoOB8tY7Ue9XKPcRcyyZa6XN
36
+ 78F0qvtLjR0DAnN6uYs98PR+jHE+0ckLX3D9sw==
37
+ -----END CERTIFICATE-----
38
+
39
+ date: 2010-10-07 00:00:00 +07:00
40
+ default_executable:
41
+ dependencies:
42
+ - !ruby/object:Gem::Dependency
43
+ name: highline
44
+ prerelease: false
45
+ requirement: &id001 !ruby/object:Gem::Requirement
46
+ none: false
47
+ requirements:
48
+ - - ">="
49
+ - !ruby/object:Gem::Version
50
+ hash: 3
51
+ segments:
52
+ - 0
53
+ version: "0"
54
+ type: :runtime
55
+ version_requirements: *id001
56
+ description: Simple script for learning foreign language words
57
+ email: vladimir.parfinenko@gmail.com
58
+ executables:
59
+ - learn_words
60
+ extensions: []
61
+
62
+ extra_rdoc_files:
63
+ - README
64
+ - bin/learn_words
65
+ - lib/learn_words.rb
66
+ files:
67
+ - MIT-LICENSE
68
+ - Manifest
69
+ - README
70
+ - Rakefile
71
+ - bin/learn_words
72
+ - lib/learn_words.rb
73
+ - learn_words.gemspec
74
+ has_rdoc: true
75
+ homepage: http://github.com/cypok/learn_words
76
+ licenses: []
77
+
78
+ post_install_message:
79
+ rdoc_options:
80
+ - --line-numbers
81
+ - --inline-source
82
+ - --title
83
+ - Learn_words
84
+ - --main
85
+ - README
86
+ require_paths:
87
+ - lib
88
+ required_ruby_version: !ruby/object:Gem::Requirement
89
+ none: false
90
+ requirements:
91
+ - - ">="
92
+ - !ruby/object:Gem::Version
93
+ hash: 3
94
+ segments:
95
+ - 0
96
+ version: "0"
97
+ required_rubygems_version: !ruby/object:Gem::Requirement
98
+ none: false
99
+ requirements:
100
+ - - ">="
101
+ - !ruby/object:Gem::Version
102
+ hash: 11
103
+ segments:
104
+ - 1
105
+ - 2
106
+ version: "1.2"
107
+ requirements: []
108
+
109
+ rubyforge_project: learn_words
110
+ rubygems_version: 1.3.7
111
+ signing_key:
112
+ specification_version: 3
113
+ summary: Simple script for learning foreign language words
114
+ test_files: []
115
+
metadata.gz.sig ADDED
@@ -0,0 +1,2 @@
1
+ -�HVrŪ���P
2
+ �mk� "��H���N"�֘��k��K���ׁ�2