rbbt-sent 1.0.0 → 1.0.1

Sign up to get free protection for your applications and to get access to all the features.
data/LICENSE CHANGED
@@ -11,6 +11,16 @@ the following conditions:
11
11
  The above copyright notice and this permission notice shall be
12
12
  included in all copies or substantial portions of the Software.
13
13
 
14
+ Any academic publication involving the use of this software in any way
15
+ should include a reference to the following publication:
16
+
17
+ Vazquez, M. and Carmona-Saez, P. and Nogales-Cadenas, R. and Chagoyen, M. and
18
+ Tirado, F. and Carazo, J.M. and Pascual-Montano, A.: "SENT: semantic features in
19
+ text". Nucleic Acids Research 2009, doi:10.1093/nar/gkp392
20
+
21
+ Any comercial use of the software must be notified for aproval to the
22
+ holder of the copyright, listed above.
23
+
14
24
  THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
15
25
  EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
16
26
  MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
data/bin/sent_config CHANGED
@@ -13,10 +13,10 @@ $USAGE =<<EOT
13
13
  actions:
14
14
  * configure: Set paths for data, work, and tmp directories
15
15
 
16
- * install:
16
+ * prepare:
17
17
  * analysis: Install configuration to perform analysis
18
18
 
19
- * update:
19
+ * install:
20
20
  * metadocs: Generate metadocs for all organisms
21
21
 
22
22
  * init:
@@ -48,14 +48,14 @@ class Controller < SimpleConsole::Controller
48
48
  render :action => :usage
49
49
  end
50
50
 
51
- def install
51
+ def prepare
52
52
  raise "Run #{__FILE__} configure first to configure sent" if $noconfig
53
53
 
54
54
  case params[:id]
55
55
  when "analysis"
56
56
  @tasks = %w(analysis)
57
57
  when nil
58
- redirect_to :action => :help, :id => :install
58
+ redirect_to :action => :help, :id => :prepare
59
59
  else
60
60
  @tasks = [params[:id]]
61
61
  end
@@ -65,14 +65,14 @@ class Controller < SimpleConsole::Controller
65
65
 
66
66
  end
67
67
 
68
- def update
68
+ def install
69
69
  raise "Run #{__FILE__} configure first to configure rbbt" if $noconfig
70
70
 
71
71
  case params[:id]
72
72
  when "metadocs"
73
73
  @location = File.join(Sent.datadir,'analysis')
74
74
  else
75
- redirect_to :action => :help, :id => :update
75
+ redirect_to :action => :help, :id => :install
76
76
  end
77
77
 
78
78
  $force = true if params[:force]
@@ -90,7 +90,7 @@ class View < SimpleConsole::View
90
90
  puts $USAGE
91
91
  end
92
92
 
93
- def install
93
+ def prepare
94
94
  require 'rake'
95
95
  load File.join(Sent.rootdir, 'tasks/install.rake')
96
96
 
@@ -100,7 +100,7 @@ class View < SimpleConsole::View
100
100
  }
101
101
  end
102
102
 
103
- def update
103
+ def install
104
104
  require 'rake'
105
105
 
106
106
  puts "Changing directory to #{@location}"
@@ -108,7 +108,7 @@ class View < SimpleConsole::View
108
108
 
109
109
  load "./Rakefile"
110
110
 
111
- Rake::Task['update'].invoke
111
+ Rake::Task['default'].invoke
112
112
  end
113
113
 
114
114
 
@@ -1,139 +1,97 @@
1
- require 'sent'
1
+ require 'rake_pipeline'
2
2
  require 'sent/main'
3
3
  require 'rbbt/sources/organism'
4
4
  require 'progress-monitor'
5
5
 
6
+ include Rake::Pipeline
6
7
 
7
- $list = ENV['list']
8
- $kstart = ENV['kstart'] || ENV['k']
9
- $kend = ENV['kend'] || $kstart
10
8
 
11
- rule (/summary\/(.*)/) => lambda {|n| n.sub(/summary/,'NMF') } do |t|
12
- nmf = t.name.sub(/summary/,'NMF')
9
+ def org_description(org, associations)
10
+ name = Organism.name(org)
11
+ supported_ids = Organism.supported_ids(org, :examples => true)
13
12
 
14
- Sent.analyze(nmf, t.name)
15
- FileUtils.touch t.name
13
+ <<-EOT
14
+ Name: #{ name }
15
+ Organism: #{ name }
16
+ Description: #{associations.values.flatten.length} associations for #{associations.keys.length} genes and #{associations.values.flatten.uniq.length} articles
17
+ ID Format: #{supported_ids.collect{|p| "#{ p[0] } (#{ p[1] })"}.join(", ")}
18
+ EOT
16
19
  end
17
20
 
18
- rule (/NMF\/(.*)/) => lambda {|n| n.sub(/NMF/,'matrices') } do |t|
19
- matrix = t.name.sub(/NMF/,'matrices')
20
-
21
- k = $kstart
22
- if $kstart < $kend
23
- best = 0
24
- ccc = Sent.CCC(matrix, $kstart, $kend)
25
- ccc.each_with_index{|v,i|
26
- if v.to_i > best
27
- k = $kstart.to_i + i
28
- end
29
- }
30
- end
31
21
 
32
- Sent.NMF(matrix, t.name, k.to_i, 10)
33
- FileUtils.touch t.name
34
- end
35
-
36
- rule (/matrices\/(.*)/) => lambda {|n| n.sub(/matrices/,'metadocs') } do |t|
37
- metadocs = t.name.sub(/matrices/,'metadocs')
38
-
39
- list = nil
40
- list = Open.read($list).collect{|l| l.chomp} if $list
22
+ desc "Find gene mentions in text"
23
+ step_def :mentions do
41
24
 
42
- Sent.matrix(metadocs, t.name, list)
25
+ associations = Sent.mentions(job_name)
26
+
27
+ associations.collect {|code, pmids| "%s\t%s" % [code, pmids.uniq.join('|')] } * "\n"
43
28
  end
44
29
 
45
- rule (/metadocs\/(.*)/) => lambda {|n| n.sub(/metadocs/,'associations') } do |t|
46
- assocfile = t.name.sub(/metadocs/,'associations')
30
+ desc "Join gene mention associations, entrez GeneRif associations, and GO associations"
31
+ step_def :associations do |t|
32
+ associations = Open.to_hash(StringIO.new(input), :flatten => true)
47
33
 
48
- Sent.metadocs(assocfile, t.name)
49
- end
34
+ associations.merge!(Organism.gene_literature(job_name))
35
+ associations.merge!(Organism.gene_literature_go(job_name))
50
36
 
51
- rule(/associations\/(.*)_text/) do |t|
52
- org = File.basename(t.name).sub(/_text/,'')
53
-
54
- ner = Organism.ner(org, :rner)
55
- norm = Organism.norm(org)
56
- pmids = Organism.literature(org)
57
-
58
- fout = File.open(t.name, 'w')
59
- chunks = pmids.chunk(100)
60
-
61
- Progress.monitor("Finding gene-article associations in text", 1000)
62
- chunks.each{|chunk|
63
- PubMed.get_article(chunk).each{|pmid, article|
64
- text = article.text
65
-
66
- mentions = ner.extract(text)
67
-
68
- Progress.monitor("Resolving mentions", 1000)
69
- codes = mentions.collect{|mention|
70
- matches = norm.match(mention)
71
- norm.select(matches,mention,text)
72
- }.flatten.uniq.sort
73
-
74
- codes.each{|code|
75
- fout.puts "#{ code }\t#{pmid}"
76
- }
77
-
78
- }
79
- }
80
- fout.close
81
- end
37
+ File.open(t.name + '.description', 'w') do |f| f.puts org_description(job_name, associations) end
82
38
 
83
- rule (/associations\/(.*)/) => lambda{|n| n + '_text'} do |t|
84
- org = File.basename(t.name)
39
+ associations.collect {|code, pmids| "%s\t%s" % [code, pmids.uniq.join('|')] } * "\n"
40
+ end
85
41
 
86
- fout = File.open(t.name, 'w')
87
- fout.write Open.read(t.name + '_text')
42
+ desc "Build dictionary"
43
+ step_def :dictionary do |t|
44
+ associations = Open.to_hash(StringIO.new(input), :flatten => true)
88
45
 
89
- associations = Organism.gene_literature(org)
90
- associations.each{|gene, pmids|
91
- pmids.each{|pmid|
92
- fout.puts "#{ gene }\t#{pmid}"
93
- }
94
- }
46
+ Progress.monitor("Building dictionary for #{job_name}")
47
+ term_weights, stems = Sent.dictionary(associations)
95
48
 
96
- associations = Organism.gene_literature_go(org)
97
- associations.each{|gene, pmids|
98
- pmids.each{|pmid|
99
- fout.puts "#{ gene }\t#{pmid}"
100
- }
101
- }
102
- fout.close
49
+ File.open(t.name + '.stems', 'w') do |f| f.puts stems.collect{|stem, words| "%s\t%s" % [stem, words.join("|")] } end
103
50
 
104
- name = Organism.name(org)
105
- supported_ids = Organism.supported_ids(org, :examples => true)
106
- associations = Open.to_hash(t.name, :flatten => true)
51
+ term_weights.collect {|term, weight| "%s\t%s" % [term, weight] } * "\n"
52
+ end
107
53
 
108
- description =<<-EOT
109
- Name: #{ name }
110
- Organism: #{ name }
111
- Description: #{associations.values.flatten.length} associations for #{associations.keys.length} genes and #{associations.values.flatten.uniq.length} articles
112
- ID Format: #{supported_ids.collect{|p| "#{ p[0] } (#{ p[1] })"}.join(", ")}
113
- EOT
54
+ desc "Build metadocument"
55
+ step_def :metadoc do
56
+ terms = input.collect{|l| l.split("\t").first}
57
+ associations = Open.to_hash(StringIO.new(input(:associations)), :flatten => true)
114
58
 
115
- Open.write(t.name + '.description', description)
59
+ Progress.monitor("Building metadoc for #{job_name}")
60
+ Sent.metadoc(associations, terms)
116
61
  end
117
62
 
118
- task 'clean' do
119
- FileUtils.rm Dir.glob("associations/*")
63
+ desc "Selecting gene metadocs"
64
+ step_def :matrix, [] do |t|
65
+ $org ||= ENV['organism']
66
+ $genes ||= STDIN.read.split(/\n/)
67
+ $metadoc_dir ||= step_dir(:metadoc)
68
+
69
+ metadoc_file = File.join($metadoc_dir, $org)
70
+
71
+ Sent.matrix(metadoc_file, $genes)
120
72
  end
121
73
 
122
- task 'all' do
123
- Organism.all.each{|org|
124
- `rake metadocs/#{ org }`
125
- }
74
+ desc "Performing NMF factorization"
75
+ step_def :NMF do |t|
76
+ $factors ||= ENV['factors']
77
+ Sent.NMF(input, t.name, $factors.to_i)
126
78
  end
127
79
 
128
- task 'update' do
129
- if $org
130
- FileUtils.rm Dir.glob("**/#{$org}.*") if $force
131
- Rake::Task["metadocs/#{$org}"].invoke
132
- else
133
- Rake::Task['clean'].invoke if $force
134
- Rake::Task['all'].invoke
135
- end
80
+
81
+ desc "Analyze results"
82
+ step_def :summary do
83
+ $factors ||= ENV['factors']
84
+ Sent.analyze(input_filename, output_filename, $factors)
136
85
  end
137
86
 
138
87
 
88
+ task 'all' do
89
+
90
+ Progress.monitor("Processing organisms", :announcement => Proc.new{|org| "Organism #{ org }" }, :stack_depth => 0)
91
+ Organism.all.each do |org|
92
+ Rake::Task[File.join('metadoc',org)].invoke
93
+ end
94
+
95
+ end
139
96
 
97
+ task 'default' => 'all'
data/lib/sent/main.rb CHANGED
@@ -1,3 +1,4 @@
1
+ require 'sent'
1
2
  require 'rbbt/sources/pubmed'
2
3
  require 'rbbt/util/misc'
3
4
  require 'rbbt/util/open'
@@ -9,6 +10,7 @@ require 'stemmer'
9
10
  require 'open4'
10
11
  require 'progress-monitor'
11
12
  require 'yaml'
13
+ require 'base64'
12
14
 
13
15
  # Produce Stem lists, used by the Web Service
14
16
  class String
@@ -41,6 +43,16 @@ class String
41
43
  reset_stem_list
42
44
  end
43
45
 
46
+ def try3times
47
+ try = 0
48
+ begin
49
+ yield
50
+ rescue
51
+ try += 1
52
+ retry if try <= 3
53
+ end
54
+ end
55
+
44
56
 
45
57
  module Sent
46
58
 
@@ -55,7 +67,8 @@ module Sent
55
67
  stdin.close
56
68
 
57
69
  Process.wait pid
58
- raise ProcessAborted, "Error in R process" if $?.exitstatus != 0
70
+
71
+ raise Sent::ProcessAbortedError, "Error in R process: #{stdout.read + stderr.read}" if $?.exitstatus != 0
59
72
  result = stdout.read + stderr.read
60
73
  stdout.close
61
74
  stderr.close
@@ -64,71 +77,99 @@ module Sent
64
77
  result
65
78
  end
66
79
 
67
- def self.metadocs(assocfile, output, low=0.001, hi=0.65, max=3000)
68
-
69
- associations = Open.to_hash(assocfile, :flatten => true, :sep => "\t|,")
80
+ def self.mentions(org)
81
+ ner = Organism.ner(org, :rner)
82
+ norm = Organism.norm(org)
83
+ pmids = Organism.literature(org)
84
+
85
+ chunks = pmids.chunk(100)
86
+
87
+ pmids = {}
88
+ Progress.monitor("Finding gene-article associations in text", :step => 1000)
89
+ chunks.each{|chunk|
90
+ try3times do
91
+ PubMed.get_article(chunk).each{|pmid, article|
92
+ text = article.text
93
+
94
+ mentions = ner.extract(text)
95
+
96
+ Progress.monitor("Resolving mentions", :step => 1000)
97
+ codes = mentions.collect{|mention|
98
+ matches = norm.match(mention)
99
+ norm.select(matches,mention,text)
100
+ }.flatten.uniq.sort
101
+
102
+ codes.each{|code|
103
+ pmids[code] ||= []
104
+ pmids[code] << pmid
105
+ }
106
+ }
107
+ end
108
+ }
109
+ pmids
110
+ end
70
111
 
112
+ def self.dictionary(associations, options = {})
113
+ dict_options = {:low => 0.001, :hi => 0.65, :limit => 3000}.merge options
71
114
  dict = Dictionary::TF_IDF.new
72
115
 
73
116
  String.reset_stem_list
74
117
 
75
- Progress.monitor("Building Dictionary for #{File.basename(output)}", 1000)
76
- associations.each{|gene, pmids|
77
- text = PubMed.get_article(pmids).collect{|p| p[1].text}.join("\n")
78
- dict.add(BagOfWords.count(text.bigrams))
79
- }
80
-
81
- # At least 3 genes must have a word to be chosen
82
- hard_min = 3 * 100 / associations.keys.length
83
- hi = hard_min if hi < hard_min
84
-
85
- d = dict.weights(:low => low, :hi => hi, :limit => max)
86
- Open.write(output + '.dict', d.sort.collect{|p| p.join("\t")}.join("\n"))
87
- terms = d.keys.sort
118
+ associations.each do |gene, pmids|
119
+ try3times do
120
+ text = PubMed.get_article(pmids).collect{|pmid, article| article.text }.join("\n")
121
+ dict.add(BagOfWords.count(text.bigrams))
122
+ end
123
+ end
88
124
 
89
- fout = File.open(output, 'w')
90
- fout.puts("\t" + terms.join("\t"))
125
+ term_weigths = dict.weights(dict_options)
126
+ terms = term_weigths.keys.sort
91
127
 
92
- Progress.monitor("Building Metadoc for #{File.basename(output)}", 1000)
93
- associations.each{|gene, pmids|
94
- text = PubMed.get_article(pmids).collect{|p| p[1].text}.join("\n")
95
- fout.puts(([gene] + BagOfWords.features(text, terms)).join("\t"))
96
- }
97
- fout.close
128
+ stems = String.stem_list(terms.collect{|p| p.split(/ /) }.flatten.uniq)
98
129
 
99
- Open.write(output + '.stems', String.stem_list(terms.collect{|p| p.split(/ /)}.flatten.uniq).collect{|k,v| "#{ k }\t#{v.join("\t")}"}.join("\n"))
130
+ [term_weigths, stems]
131
+ end
132
+
133
+
134
+ def self.metadoc(associations, terms)
135
+ "%s\t%s\n" % ["Entity", terms.sort * "\t"] +
136
+ associations.collect do |gene, pmids|
137
+ try3times do
138
+ text = PubMed.get_article(pmids).collect{|pmid, article| article.text }.join("\n")
139
+ "%s\t%s" % [gene, BagOfWords.features(text, terms.sort).join("\t")]
140
+ end
141
+ end * "\n"
100
142
  end
101
143
 
102
- def self.matrix(metadocs, output, list=nil)
103
- list ||= []
104
-
105
- if list.empty?
106
- FileUtils.cp metadocs, output
107
- else
108
- `head -n 1 #{ metadocs } > #{ output }`
109
- `grep '^\\(#{list.join('\\|')}\\)[[:space:]]' #{ metadocs } >> #{output}`
110
- raise Sent::NoGenesError, "No Genes Matched" if $? != 0
144
+ def self.matrix(metadoc_file, genes)
145
+
146
+ matrix = ""
147
+ File.open(metadoc_file) do |f|
148
+ matrix += f.gets
149
+ f.read.each_line do |line|
150
+ gene = line.match(/^(.*?)\t/)[1]
151
+ matrix += line if genes.include? gene
152
+ end
111
153
  end
112
154
 
113
- dict = metadocs + '.dict'
114
- run_R("SENT.prepare.matrix('#{ output }', '#{ output }', '#{metadocs + '.dict'}')")
155
+ matrix
115
156
  end
116
157
 
117
-
118
158
  @@bionmf_wsdl = "http://bionmf.dacya.ucm.es/WebService/BioNMFWS.wsdl"
119
159
  def self.NMF(matrix, out, k, executions = 10)
120
160
  driver = SOAP::WSDLDriverFactory.new( @@bionmf_wsdl).create_rpc_driver
121
161
 
122
162
  # Upload matrix
123
163
  nmf_matrix = driver.upload_matrix(
124
- File.open(matrix).read, # matrix
125
- false, # binary
126
- true, # column labels
127
- true, # row labels
128
- true, # transpose
129
- "No", # positive
130
- "No", # normalization
164
+ matrix, # matrix
165
+ false, # binary
166
+ true, # column labels
167
+ true, # row labels
168
+ true, # transpose
169
+ "No", # positive
170
+ "No", # normalization
131
171
  "matrix") # Suggested name
172
+
132
173
  # Send several executions in parallel
133
174
  while !driver.done(nmf_matrix)
134
175
  sleep(5)
@@ -149,14 +190,14 @@ module Sent
149
190
  job_id = driver.standardNMF(
150
191
  nmf_matrix, # Matrix job
151
192
  "Standard", # Algorithm
152
- k, # Factor Start
153
- k, # Factor End
154
- 1, # Runs
155
- 2000, # Iterations
156
- 40, # Stop criteria
157
- 0, # Not used (nsnmf smoothness)
158
- false, # extra info
159
- '') # Suggested name
193
+ k, # Factor Start
194
+ k, # Factor End
195
+ 1, # Runs
196
+ 2000, # Iterations
197
+ 40, # Stop criteria
198
+ 0, # Not used (nsnmf smoothness)
199
+ false, # extra info
200
+ '') # Suggested name
160
201
 
161
202
  while !driver.done(job_id)
162
203
  sleep(5)
@@ -168,12 +209,15 @@ module Sent
168
209
  end
169
210
 
170
211
  results = driver.results(job_id)
171
- fw = File.open(out + ".matrix_w.#{num}",'w')
172
- fw.write(driver.result(results[0]).sub(/\t(.*)\t$/,'\1'))
173
- fw.close
174
- fh = File.open(out + ".matrix_h.#{num}",'w')
175
- fh.write(driver.result(results[1]).sub(/\t(.*)\t$/,'\1'))
176
- fh.close
212
+
213
+ File.open(out + ".matrix_w.#{num}",'w') do |f|
214
+ f.write Base64.decode64 driver.result(results[0]) #.sub(/\t(.*)\t$/,'\1')
215
+ end
216
+
217
+ File.open(out + ".matrix_h.#{num}",'w') do |f|
218
+ f.write Base64.decode64 driver.result(results[1]) #.sub(/\t(.*)\t$/,'\1')
219
+ end
220
+
177
221
  driver.clean(job_id)
178
222
  rescue Sent::ProcessAbortedError
179
223
  puts "Process aborted for #{ num }"
@@ -228,7 +272,7 @@ module Sent
228
272
  if error
229
273
  raise Exception, "Error in NMF:\n" + error
230
274
  end
231
-
275
+
232
276
  run_R("SENT.join.results('#{ out }')")
233
277
 
234
278
  FileUtils.rm Dir.glob(out + '.matrix_*.*')
@@ -275,7 +319,7 @@ module Sent
275
319
  def self.analyze(prefix, output, clusters = nil, num_words = 15)
276
320
 
277
321
  FileUtils.rm Dir.glob(output + '*.words') + Dir.glob(output + '*.genes')
278
- run_R("SENT.analyze('#{ prefix }', '#{ output }', '#{clusters}', '#{num_words}')")
322
+ run_R("SENT.analyze('#{ prefix }', '#{ output }', #{clusters || 'NULL'}, #{num_words})")
279
323
  words = Dir.glob(output + '*.words').sort.collect{|f| Open.read(f).split(/\n/)}
280
324
  genes = Dir.glob(output + '*.genes').sort.collect{|f| Open.read(f).split(/\n/)}
281
325
 
@@ -284,7 +328,7 @@ module Sent
284
328
  groups << {:words => p[0], :genes => p[1]}
285
329
  }
286
330
 
287
- Open.write(output + '.summary', groups.to_yaml)
331
+ groups
288
332
  end
289
333
 
290
334
  def self.literature_index(pmids, outfile)
metadata CHANGED
@@ -1,7 +1,12 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: rbbt-sent
3
3
  version: !ruby/object:Gem::Version
4
- version: 1.0.0
4
+ prerelease: false
5
+ segments:
6
+ - 1
7
+ - 0
8
+ - 1
9
+ version: 1.0.1
5
10
  platform: ruby
6
11
  authors:
7
12
  - Miguel Vazquez
@@ -9,79 +14,105 @@ autorequire:
9
14
  bindir: bin
10
15
  cert_chain: []
11
16
 
12
- date: 2009-11-09 00:00:00 +01:00
17
+ date: 2010-05-21 00:00:00 +02:00
13
18
  default_executable: sent_config
14
19
  dependencies:
15
20
  - !ruby/object:Gem::Dependency
16
21
  name: rake
17
- type: :runtime
18
- version_requirement:
19
- version_requirements: !ruby/object:Gem::Requirement
22
+ prerelease: false
23
+ requirement: &id001 !ruby/object:Gem::Requirement
20
24
  requirements:
21
25
  - - ">="
22
26
  - !ruby/object:Gem::Version
27
+ segments:
28
+ - 0
23
29
  version: "0"
24
- version:
30
+ type: :runtime
31
+ version_requirements: *id001
25
32
  - !ruby/object:Gem::Dependency
26
33
  name: simpleconsole
27
- type: :runtime
28
- version_requirement:
29
- version_requirements: !ruby/object:Gem::Requirement
34
+ prerelease: false
35
+ requirement: &id002 !ruby/object:Gem::Requirement
30
36
  requirements:
31
37
  - - ">="
32
38
  - !ruby/object:Gem::Version
39
+ segments:
40
+ - 0
33
41
  version: "0"
34
- version:
42
+ type: :runtime
43
+ version_requirements: *id002
35
44
  - !ruby/object:Gem::Dependency
36
45
  name: rbbt
37
- type: :runtime
38
- version_requirement:
39
- version_requirements: !ruby/object:Gem::Requirement
46
+ prerelease: false
47
+ requirement: &id003 !ruby/object:Gem::Requirement
40
48
  requirements:
41
49
  - - ">="
42
50
  - !ruby/object:Gem::Version
51
+ segments:
52
+ - 0
43
53
  version: "0"
44
- version:
54
+ type: :runtime
55
+ version_requirements: *id003
45
56
  - !ruby/object:Gem::Dependency
46
57
  name: ferret
47
- type: :runtime
48
- version_requirement:
49
- version_requirements: !ruby/object:Gem::Requirement
58
+ prerelease: false
59
+ requirement: &id004 !ruby/object:Gem::Requirement
50
60
  requirements:
51
61
  - - ">="
52
62
  - !ruby/object:Gem::Version
63
+ segments:
64
+ - 0
53
65
  version: "0"
54
- version:
66
+ type: :runtime
67
+ version_requirements: *id004
55
68
  - !ruby/object:Gem::Dependency
56
69
  name: stemmer
57
- type: :runtime
58
- version_requirement:
59
- version_requirements: !ruby/object:Gem::Requirement
70
+ prerelease: false
71
+ requirement: &id005 !ruby/object:Gem::Requirement
60
72
  requirements:
61
73
  - - ">="
62
74
  - !ruby/object:Gem::Version
75
+ segments:
76
+ - 0
63
77
  version: "0"
64
- version:
78
+ type: :runtime
79
+ version_requirements: *id005
65
80
  - !ruby/object:Gem::Dependency
66
81
  name: progress-monitor
67
- type: :runtime
68
- version_requirement:
69
- version_requirements: !ruby/object:Gem::Requirement
82
+ prerelease: false
83
+ requirement: &id006 !ruby/object:Gem::Requirement
70
84
  requirements:
71
85
  - - ">="
72
86
  - !ruby/object:Gem::Version
87
+ segments:
88
+ - 0
73
89
  version: "0"
74
- version:
90
+ type: :runtime
91
+ version_requirements: *id006
75
92
  - !ruby/object:Gem::Dependency
76
93
  name: open4
94
+ prerelease: false
95
+ requirement: &id007 !ruby/object:Gem::Requirement
96
+ requirements:
97
+ - - ">="
98
+ - !ruby/object:Gem::Version
99
+ segments:
100
+ - 0
101
+ version: "0"
77
102
  type: :runtime
78
- version_requirement:
79
- version_requirements: !ruby/object:Gem::Requirement
103
+ version_requirements: *id007
104
+ - !ruby/object:Gem::Dependency
105
+ name: simplews
106
+ prerelease: false
107
+ requirement: &id008 !ruby/object:Gem::Requirement
80
108
  requirements:
81
109
  - - ">="
82
110
  - !ruby/object:Gem::Version
111
+ segments:
112
+ - 0
83
113
  version: "0"
84
- version:
114
+ type: :runtime
115
+ version_requirements: *id008
85
116
  description: Use literature mining to find semantic features to describe clusers of genes
86
117
  email: miguel.vazquez@fdi.ucm.es
87
118
  executables:
@@ -114,18 +145,20 @@ required_ruby_version: !ruby/object:Gem::Requirement
114
145
  requirements:
115
146
  - - ">="
116
147
  - !ruby/object:Gem::Version
148
+ segments:
149
+ - 0
117
150
  version: "0"
118
- version:
119
151
  required_rubygems_version: !ruby/object:Gem::Requirement
120
152
  requirements:
121
153
  - - ">="
122
154
  - !ruby/object:Gem::Version
155
+ segments:
156
+ - 0
123
157
  version: "0"
124
- version:
125
158
  requirements: []
126
159
 
127
160
  rubyforge_project:
128
- rubygems_version: 1.3.5
161
+ rubygems_version: 1.3.6
129
162
  signing_key:
130
163
  specification_version: 3
131
164
  summary: Semantic Features in Text