bio 0.7.0 → 0.7.1

Sign up to get free protection for your applications and to get access to all the features.
@@ -1,8 +1,14 @@
1
1
  #
2
- # bio/db/pdb/model.rb - model class for PDB
2
+ # = bio/db/pdb/model.rb - model class for PDB
3
3
  #
4
- # Copyright (C) 2004 Alex Gutteridge <alexg@ebi.ac.uk>
4
+ # Copyright:: Copyright (C) 2004, 2006
5
+ # Alex Gutteridge <alexg@ebi.ac.uk>
6
+ # Naohisa Goto <ng@bioruby.org>
7
+ # License:: LGPL
5
8
  #
9
+ # $Id: model.rb,v 1.7 2006/01/20 13:54:08 ngoto Exp $
10
+ #
11
+ #--
6
12
  # This library is free software; you can redistribute it and/or
7
13
  # modify it under the terms of the GNU Lesser General Public
8
14
  # License as published by the Free Software Foundation; either
@@ -16,8 +22,12 @@
16
22
  # You should have received a copy of the GNU Lesser General Public
17
23
  # License along with this library; if not, write to the Free Software
18
24
  # Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
25
+ #++
26
+ #
27
+ # = Bio::PDB::Model
28
+ #
29
+ # Please refer Bio::PDB::Model.
19
30
  #
20
- # $Id: model.rb,v 1.2 2005/09/26 13:00:08 k Exp $
21
31
 
22
32
  require 'bio/db/pdb'
23
33
 
@@ -25,82 +35,124 @@ module Bio
25
35
 
26
36
  class PDB
27
37
 
28
- #Model class
38
+ # Bio::PDB::Model is a class to store a model.
39
+ #
40
+ # The object would contain some chains (Bio::PDB::Chain objects).
29
41
  class Model
30
42
 
31
43
  include Utils
32
44
  include AtomFinder
33
45
  include ResidueFinder
34
46
  include ChainFinder
47
+
48
+ include HetatmFinder
49
+ include HeterogenFinder
50
+
35
51
  include Enumerable
36
52
  include Comparable
37
53
 
38
- attr_reader :model_serial, :structure, :solvent
39
- attr_writer :model_serial
40
-
41
- def initialize(model_serial = nil, structure = nil)
42
-
43
- @model_serial = model_serial
44
-
45
- @structure = structure
46
-
47
- @chains = Array.new
48
- @solvent = Chain.new('',self)
54
+ # Creates a new Model object
55
+ def initialize(serial = nil, structure = nil)
49
56
 
57
+ @serial = serial
58
+ @structure = structure
59
+ @chains = []
60
+ @chains_hash = {}
61
+ @solvents = Chain.new('', self)
50
62
  end
51
-
52
- #Adds a chain
63
+
64
+ # chains in this model
65
+ attr_reader :chains
66
+
67
+ # (OBSOLETE) solvents (water, HOH) in this model
68
+ attr_reader :solvents
69
+
70
+ # serial number of this model. (Integer or nil)
71
+ attr_accessor :serial
72
+
73
+ # for backward compatibility
74
+ alias model_serial serial
75
+
76
+ # (reserved for future extension)
77
+ attr_reader :structure
78
+
79
+ # Adds a chain to this model
53
80
  def addChain(chain)
54
- raise "Expecting a Bio::PDB::Chain" if not chain.is_a? Bio::PDB::Chain
81
+ raise "Expecting a Bio::PDB::Chain" unless chain.is_a? Bio::PDB::Chain
55
82
  @chains.push(chain)
56
- self
83
+ if @chains_hash[chain.chain_id] then
84
+ $stderr.puts "Warning: chain_id #{chain.chain_id.inspect} is already used" if $VERBOSE
85
+ else
86
+ @chains_hash[chain.chain_id] = chain
87
+ end
88
+ self
89
+ end
90
+
91
+ # rehash chains hash
92
+ def rehash
93
+ begin
94
+ chains_bak = @chains
95
+ chains_hash_bak = @chains_hash
96
+ @chains = []
97
+ @chains_hash = {}
98
+ chains_bak.each do |chain|
99
+ self.addChain(chain)
100
+ end
101
+ rescue RuntimeError
102
+ @chains = chains_bak
103
+ @chains_hash = chains_hash_bak
104
+ raise
105
+ end
106
+ self
57
107
  end
58
108
 
59
- #adds a solvent molecule
109
+ # (OBSOLETE) Adds a solvent molecule to this model
60
110
  def addSolvent(solvent)
61
- raise "Expecting a Bio::PDB::Residue" if not solvent.is_a? Bio::PDB::Residue
62
- @solvent.addResidue(solvent)
111
+ raise "Expecting a Bio::PDB::Residue" unless solvent.is_a? Bio::PDB::Residue
112
+ @solvents.addResidue(solvent)
63
113
  end
64
114
 
115
+ # (OBSOLETE) not recommended to use this method
65
116
  def removeSolvent
66
- @solvent = nil
117
+ @solvents = nil
67
118
  end
68
119
 
69
- #Chain iterator
70
- def each
71
- @chains.each{ |chain| yield chain }
120
+ # Iterates over each chain
121
+ def each(&x) #:yields: chain
122
+ @chains.each(&x)
72
123
  end
73
- #Alias to override ChainFinder#each_chain
124
+ # Alias to override ChainFinder#each_chain
74
125
  alias each_chain each
75
126
 
76
- #Sorts models based on serial number
127
+ # Operator aimed to sort models based on serial number
77
128
  def <=>(other)
78
- return @mode_serial <=> other.model_serial
129
+ return @serial <=> other.model_serial
79
130
  end
80
131
 
81
- #Keyed access to chains
132
+ # Keyed access to chains
82
133
  def [](key)
83
- chain = @chains.find{ |chain| key == chain.id }
134
+ #chain = @chains.find{ |chain| key == chain.id }
135
+ @chains_hash[key]
84
136
  end
85
137
 
86
- #stringifies to chains
138
+ # stringifies to chains
87
139
  def to_s
88
140
  string = ""
89
141
  if model_serial
90
- string = "MODEL #{model_serial}" #Should use proper formatting
142
+ string = "MODEL #{model_serial}\n" #Should use proper formatting
91
143
  end
92
144
  @chains.each{ |chain| string << chain.to_s }
93
- if solvent
94
- string << @solvent.to_s
95
- end
145
+ #if solvent
146
+ # string << @solvent.to_s
147
+ #end
96
148
  if model_serial
97
- string << "ENDMDL"
149
+ string << "ENDMDL\n"
98
150
  end
99
151
  return string
100
152
  end
101
153
 
102
154
  end #class Model
103
155
 
104
- end
156
+ end #class PDB
105
157
 
106
- end
158
+ end #module Bio
@@ -1,9 +1,14 @@
1
1
  #
2
- # bio/db/pdb/pdb.rb - PDB database class for PDB file format
2
+ # = bio/db/pdb/pdb.rb - PDB database class for PDB file format
3
3
  #
4
- # Copyright (C) 2003,2004 GOTO Naohisa <ngoto@gen-info.osaka-u.ac.jp>
5
- # Copyright (C) 2004 Alex Gutteridge <alexg@ebi.ac.uk>
4
+ # Copyright:: Copyright (C) 2003-2006
5
+ # GOTO Naohisa <ngoto@gen-info.osaka-u.ac.jp>
6
+ # Alex Gutteridge <alexg@ebi.ac.uk>
7
+ # License:: LGPL
6
8
  #
9
+ # $Id: pdb.rb,v 1.13 2006/01/20 13:54:08 ngoto Exp $
10
+ #
11
+ #--
7
12
  # This library is free software; you can redistribute it and/or
8
13
  # modify it under the terms of the GNU Lesser General Public
9
14
  # License as published by the Free Software Foundation; either
@@ -17,12 +22,20 @@
17
22
  # You should have received a copy of the GNU Lesser General Public
18
23
  # License along with this library; if not, write to the Free Software
19
24
  # Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
25
+ #++
20
26
  #
21
- # $Id: pdb.rb,v 1.6 2005/12/18 17:37:14 ngoto Exp $
27
+ # = About Bio::PDB
22
28
  #
23
-
24
- # *** CAUTION ***
25
- # This is pre-alpha version. Specs shall be changed frequently.
29
+ # Please refer document of Bio::PDB class.
30
+ #
31
+ # = References
32
+ #
33
+ # * ((<URL:http://www.rcsb.org/pdb/>))
34
+ # * PDB File Format Contents Guide Version 2.2 (20 December 1996)
35
+ # ((<URL:http://www.rcsb.org/pdb/file_formats/pdb/pdbguide2.2/guide2.2_frame.html>))
36
+ #
37
+ # = *** CAUTION ***
38
+ # This is beta version. Specs shall be changed frequently.
26
39
  #
27
40
 
28
41
  require 'bio/db/pdb'
@@ -30,20 +43,37 @@ require 'bio/data/aa'
30
43
 
31
44
  module Bio
32
45
 
33
- #This is the main PDB class which takes care of parsing, annotations
34
- #and is the entry way to the co-ordinate data held in models
35
- class PDB #< DB
46
+ # This is the main PDB class which takes care of parsing, annotations
47
+ # and is the entry way to the co-ordinate data held in models.
48
+ #
49
+ # There are many related classes.
50
+ #
51
+ # Bio::PDB::Model
52
+ # Bio::PDB::Chain
53
+ # Bio::PDB::Residue
54
+ # Bio::PDB::Heterogen
55
+ # Bio::PDB::Record::ATOM
56
+ # Bio::PDB::Record::HETATM
57
+ # Bio::PDB::Record::*
58
+ # Bio::PDB::Coordinate
59
+ #
60
+ class PDB
36
61
 
37
62
  include Utils
38
63
  include AtomFinder
39
64
  include ResidueFinder
40
65
  include ChainFinder
41
66
  include ModelFinder
67
+
68
+ include HetatmFinder
69
+ include HeterogenFinder
70
+
42
71
  include Enumerable
43
72
 
73
+ # delimiter for reading via Bio::FlatFile
44
74
  DELIMITER = RS = nil # 1 file 1 entry
45
75
 
46
- #Modules required by the field definitions
76
+ # Modules required by the field definitions
47
77
  module DataType
48
78
 
49
79
  Pdb_Continuation = nil
@@ -154,10 +184,20 @@ module Bio
154
184
  end #module ConstLikeMethod
155
185
  end #module DataType
156
186
 
187
+ # The ancestor of every single PDB record class.
188
+ # It inherits <code>Struct</code> class.
189
+ # Basically, each line of a PDB file corresponds to
190
+ # an instance of each corresponding child class.
191
+ # If continuation exists, multiple lines may correspond to
192
+ # single instance.
193
+ #
157
194
  class Record < Struct
158
195
  include DataType
159
196
  extend DataType::ConstLikeMethod
160
197
 
198
+ # Internal use only.
199
+ #
200
+ # parse filed definitions.
161
201
  def self.parse_field_definitions(ary)
162
202
  symbolhash = {}
163
203
  symbolary = []
@@ -192,7 +232,12 @@ module Bio
192
232
  [ symbolhash, symbolary, cont ]
193
233
  end
194
234
  private_class_method :parse_field_definitions
195
-
235
+
236
+ # Creates new class by given field definition
237
+ # The difference from new_direct() is the class
238
+ # created by the method does lazy evaluation.
239
+ #
240
+ # Internal use only.
196
241
  def self.def_rec(*ary)
197
242
  symbolhash, symbolary, cont = parse_field_definitions(ary)
198
243
 
@@ -210,6 +255,7 @@ module Bio
210
255
  klass
211
256
  end #def self.def_rec
212
257
 
258
+ # creates new class which inherits given class.
213
259
  def self.new_inherit(klass)
214
260
  newklass = Class.new(klass)
215
261
  newklass.module_eval {
@@ -220,6 +266,9 @@ module Bio
220
266
  newklass
221
267
  end
222
268
 
269
+ # Creates new class by given field definition.
270
+ #
271
+ # Internal use only.
223
272
  def self.new_direct(*ary)
224
273
  symbolhash, symbolary, cont = parse_field_definitions(ary)
225
274
  if cont
@@ -242,11 +291,14 @@ module Bio
242
291
  klass
243
292
  end #def self.new_direct
244
293
 
294
+ # symbols
245
295
  def self.symbols
246
296
  #p self
247
297
  @symbols
248
298
  end
249
299
 
300
+ # Returns true if this record has a field type which allows
301
+ # continuations.
250
302
  def self.continue?
251
303
  @cont
252
304
  end
@@ -265,8 +317,11 @@ module Bio
265
317
  end
266
318
  end
267
319
 
268
- #Return original string for this record (usually just @str, but
269
- #sometimes add on the continuation data from other lines
320
+ # Return original string (except that "\n" are truncated)
321
+ # for this record (usually just @str, but
322
+ # sometimes add on the continuation data from other lines.
323
+ # Returns an array of string.
324
+ #
270
325
  def original_data
271
326
  if defined?(@cont_data) then
272
327
  [ @str, *@cont_data ]
@@ -275,7 +330,11 @@ module Bio
275
330
  end
276
331
  end
277
332
 
278
- # initialize from the string
333
+ # initialize this record from the given string.
334
+ # <em>str</em> must be a line (in PDB format).
335
+ #
336
+ # You can add continuation lines later using
337
+ # <code>add_continuation</code> method.
279
338
  def initialize_from_string(str)
280
339
  @str = str
281
340
  @record_name = fetch_record_name(str)
@@ -283,8 +342,17 @@ module Bio
283
342
  self
284
343
  end
285
344
 
286
- #Called when we need to access the data, takes the string
287
- #and the array of FieldDefs and parses it out
345
+ #--
346
+ # Called when we need to access the data, takes the string
347
+ # and the array of FieldDefs and parses it out.
348
+ #++
349
+
350
+ # In order to speeding up processing of PDB file format,
351
+ # fields have not been parsed before calling this method.
352
+ #
353
+ # Normally, it is automatically called and you don't explicitly
354
+ # need to call it .
355
+ #
288
356
  def do_parse
289
357
  return self if @parsed
290
358
  str = @str
@@ -330,17 +398,19 @@ module Bio
330
398
  self
331
399
  end
332
400
 
401
+ # fetches record name
333
402
  def fetch_record_name(str)
334
403
  str[0..5].strip
335
404
  end
336
405
  private :fetch_record_name
337
406
 
407
+ # fetches record name
338
408
  def self.fetch_record_name(str)
339
409
  str[0..5].strip
340
410
  end
341
411
  private_class_method :fetch_record_name
342
412
 
343
- # If given str can be the continuation of the current record, then
413
+ # If given <em>str</em> can be the continuation of the current record,
344
414
  # then return the order number of the continuation associated with
345
415
  # the Pdb_Continuation field definition.
346
416
  # Otherwise, returns -1.
@@ -349,16 +419,20 @@ module Bio
349
419
  end
350
420
  private :fetch_cont
351
421
 
422
+ # Record name of this record, e.g. "HEADER", "ATOM".
352
423
  def record_name
353
- @record_name or self.class.to_s.split(/\:\:/)[-1]
424
+ @record_name or self.class.to_s.split(/\:\:/)[-1].to_s.upcase
354
425
  end
355
426
  # keeping compatibility with old version
356
427
  alias record_type record_name
357
428
 
429
+ # Internal use only.
430
+ #
358
431
  # Adds continuation data to the record from str if str is
359
432
  # really the continuation of current record.
360
433
  # Returns self (= not nil) if str is the continuation.
361
434
  # Otherwaise, returns false.
435
+ #
362
436
  def add_continuation(str)
363
437
  #Check that this record can continue
364
438
  #and that str has the same type and definition
@@ -387,11 +461,19 @@ module Bio
387
461
  hash
388
462
  end
389
463
 
464
+ # same as Struct#inspect.
465
+ #
466
+ # Note that <code>do_parse</code> is automatically called
467
+ # before <code>inspect</code>.
468
+ #
469
+ # (Warning: The do_parse might sweep hidden bugs in PDB classes.)
390
470
  def inspect
391
- #do_parse
471
+ do_parse
392
472
  super
393
473
  end
394
474
 
475
+ #--
476
+ #
395
477
  # definitions
396
478
  # contains all the rules for parsing each field
397
479
  # based on format V 2.2, 16-DEC-1996
@@ -405,13 +487,17 @@ module Bio
405
487
 
406
488
  # XXXXXX =
407
489
  # new([ start, end, type of data, symbol to access ], ...)
490
+ #
491
+ #++
408
492
 
493
+ # HEADER record class
409
494
  HEADER =
410
495
  def_rec([ 11, 50, Pdb_String, :classification ], #Pdb_String(40)
411
496
  [ 51, 59, Pdb_Date, :depDate ],
412
497
  [ 63, 66, Pdb_IDcode, :idCode ]
413
498
  )
414
499
 
500
+ # OBSLTE record class
415
501
  OBSLTE =
416
502
  def_rec([ 9, 10, Pdb_Continuation, nil ],
417
503
  [ 12, 20, Pdb_Date, :repDate ],
@@ -426,42 +512,50 @@ module Bio
426
512
  [ 67, 70, Pdb_IDcode, :rIdCode ]
427
513
  )
428
514
 
515
+ # TITLE record class
429
516
  TITLE =
430
517
  def_rec([ 9, 10, Pdb_Continuation, nil ],
431
518
  [ 11, 70, Pdb_String, :title ]
432
519
  )
433
520
 
521
+ # CAVEAT record class
434
522
  CAVEAT =
435
523
  def_rec([ 9, 10, Pdb_Continuation, nil ],
436
524
  [ 12, 15, Pdb_IDcode, :idcode ],
437
525
  [ 20, 70, Pdb_String, :comment ]
438
526
  )
439
527
 
528
+ # COMPND record class
440
529
  COMPND =
441
530
  def_rec([ 9, 10, Pdb_Continuation, nil ],
442
531
  [ 11, 70, Pdb_Specification_list, :compound ]
443
532
  )
444
533
 
534
+ # SOURCE record class
445
535
  SOURCE =
446
536
  def_rec([ 9, 10, Pdb_Continuation, nil ],
447
537
  [ 11, 70, Pdb_Specification_list, :srcName ]
448
538
  )
449
539
 
540
+ # KEYWDS record class
450
541
  KEYWDS =
451
542
  def_rec([ 9, 10, Pdb_Continuation, nil ],
452
543
  [ 11, 70, Pdb_List, :keywds ]
453
544
  )
454
545
 
546
+ # EXPDTA record class
455
547
  EXPDTA =
456
548
  def_rec([ 9, 10, Pdb_Continuation, nil ],
457
549
  [ 11, 70, Pdb_SList, :technique ]
458
550
  )
459
551
 
552
+ # AUTHOR record class
460
553
  AUTHOR =
461
554
  def_rec([ 9, 10, Pdb_Continuation, nil ],
462
555
  [ 11, 70, Pdb_List, :authorList ]
463
556
  )
464
557
 
558
+ # REVDAT record class
465
559
  REVDAT =
466
560
  def_rec([ 8, 10, Pdb_Integer, :modNum ],
467
561
  [ 11, 12, Pdb_Continuation, nil ],
@@ -474,6 +568,7 @@ module Bio
474
568
  [ 61, 66, Pdb_LString(6), :record ]
475
569
  )
476
570
 
571
+ # SPRSDE record class
477
572
  SPRSDE =
478
573
  def_rec([ 9, 10, Pdb_Continuation, nil ],
479
574
  [ 12, 20, Pdb_Date, :sprsdeDate ],
@@ -494,6 +589,7 @@ module Bio
494
589
  # 'REMARK' is defined below
495
590
  REMARK = nil
496
591
 
592
+ # DBREF record class
497
593
  DBREF =
498
594
  def_rec([ 8, 11, Pdb_IDcode, :idCode ],
499
595
  [ 13, 13, Pdb_Character, :chainID ],
@@ -510,6 +606,7 @@ module Bio
510
606
  [ 68, 68, Pdb_AChar, :dbinsEnd ]
511
607
  )
512
608
 
609
+ # SEQADV record class
513
610
  SEQADV =
514
611
  def_rec([ 8, 11, Pdb_IDcode, :idCode ],
515
612
  [ 13, 15, Pdb_Residue_name, :resName ],
@@ -523,6 +620,7 @@ module Bio
523
620
  [ 50, 70, Pdb_LString, :conflict ]
524
621
  )
525
622
 
623
+ # SEQRES record class
526
624
  SEQRES =
527
625
  def_rec(#[ 9, 10, Pdb_Integer, :serNum ],
528
626
  [ 9, 10, Pdb_Continuation, nil ],
@@ -543,6 +641,7 @@ module Bio
543
641
  [ 68, 70, Pdb_Residue_name, :resName ]
544
642
  )
545
643
 
644
+ # MODRS record class
546
645
  MODRES =
547
646
  def_rec([ 8, 11, Pdb_IDcode, :idCode ],
548
647
  [ 13, 15, Pdb_Residue_name, :resName ],
@@ -553,6 +652,7 @@ module Bio
553
652
  [ 30, 70, Pdb_String, :comment ]
554
653
  )
555
654
 
655
+ # HET record class
556
656
  HET =
557
657
  def_rec([ 8, 10, Pdb_LString(3), :hetID ],
558
658
  [ 13, 13, Pdb_Character, :ChainID ],
@@ -562,18 +662,21 @@ module Bio
562
662
  [ 31, 70, Pdb_String, :text ]
563
663
  )
564
664
 
665
+ # HETNAM record class
565
666
  HETNAM =
566
667
  def_rec([ 9, 10, Pdb_Continuation, nil ],
567
668
  [ 12, 14, Pdb_LString(3), :hetID ],
568
669
  [ 16, 70, Pdb_String, :text ]
569
670
  )
570
671
 
672
+ # HETSYN record class
571
673
  HETSYN =
572
674
  def_rec([ 9, 10, Pdb_Continuation, nil ],
573
675
  [ 12, 14, Pdb_LString(3), :hetID ],
574
676
  [ 16, 70, Pdb_SList, :hetSynonyms ]
575
677
  )
576
678
 
679
+ # FORMUL record class
577
680
  FORMUL =
578
681
  def_rec([ 9, 10, Pdb_Integer, :compNum ],
579
682
  [ 13, 15, Pdb_LString(3), :hetID ],
@@ -582,6 +685,7 @@ module Bio
582
685
  [ 20, 70, Pdb_String, :text ]
583
686
  )
584
687
 
688
+ # HELIX record class
585
689
  HELIX =
586
690
  def_rec([ 8, 10, Pdb_Integer, :serNum ],
587
691
  #[ 12, 14, Pdb_LString(3), :helixID ],
@@ -599,6 +703,7 @@ module Bio
599
703
  [ 72, 76, Pdb_Integer, :length ]
600
704
  )
601
705
 
706
+ # SHEET record class
602
707
  SHEET =
603
708
  def_rec([ 8, 10, Pdb_Integer, :strand ],
604
709
  #[ 12, 14, Pdb_LString(3), :sheetID ],
@@ -625,6 +730,7 @@ module Bio
625
730
  [ 70, 70, Pdb_AChar, :prevICode ]
626
731
  )
627
732
 
733
+ # TURN record class
628
734
  TURN =
629
735
  def_rec([ 8, 10, Pdb_Integer, :seq ],
630
736
  #[ 12, 14, Pdb_LString(3), :turnId ],
@@ -640,6 +746,7 @@ module Bio
640
746
  [ 41, 70, Pdb_String, :comment ]
641
747
  )
642
748
 
749
+ # SSBOND record class
643
750
  SSBOND =
644
751
  def_rec([ 8, 10, Pdb_Integer, :serNum ],
645
752
  [ 12, 14, Pdb_LString(3), :pep1 ], # "CYS"
@@ -654,6 +761,7 @@ module Bio
654
761
  [ 67, 72, Pdb_SymOP, :sym2 ]
655
762
  )
656
763
 
764
+ # LINK record class
657
765
  LINK =
658
766
  def_rec([ 13, 16, Pdb_Atom, :name1 ],
659
767
  [ 17, 17, Pdb_Character, :altLoc1 ],
@@ -671,6 +779,7 @@ module Bio
671
779
  [ 67, 72, Pdb_SymOP, :sym2 ]
672
780
  )
673
781
 
782
+ # HYDBND record class
674
783
  HYDBND =
675
784
  def_rec([ 13, 16, Pdb_Atom, :name1 ],
676
785
  [ 17, 17, Pdb_Character, :altLoc1 ],
@@ -693,6 +802,7 @@ module Bio
693
802
  [ 67, 72, Pdb_SymOP, :sym2 ]
694
803
  )
695
804
 
805
+ # SLTBRG record class
696
806
  SLTBRG =
697
807
  def_rec([ 13, 16, Pdb_Atom, :atom1 ],
698
808
  [ 17, 17, Pdb_Character, :altLoc1 ],
@@ -710,6 +820,7 @@ module Bio
710
820
  [ 67, 72, Pdb_SymOP, :sym2 ]
711
821
  )
712
822
 
823
+ # CISPEP record class
713
824
  CISPEP =
714
825
  def_rec([ 8, 10, Pdb_Integer, :serNum ],
715
826
  [ 12, 14, Pdb_LString(3), :pep1 ],
@@ -724,6 +835,7 @@ module Bio
724
835
  [ 54, 59, Pdb_Real('6.2'), :measure ]
725
836
  )
726
837
 
838
+ # SITE record class
727
839
  SITE =
728
840
  def_rec([ 8, 10, Pdb_Integer, :seqNum ],
729
841
  [ 12, 14, Pdb_LString(3), :siteID ],
@@ -746,6 +858,7 @@ module Bio
746
858
  [ 61, 61, Pdb_AChar, :iCode4 ]
747
859
  )
748
860
 
861
+ # CRYST1 record class
749
862
  CRYST1 =
750
863
  def_rec([ 7, 15, Pdb_Real('9.3'), :a ],
751
864
  [ 16, 24, Pdb_Real('9.3'), :b ],
@@ -757,6 +870,8 @@ module Bio
757
870
  [ 67, 70, Pdb_Integer, :z ]
758
871
  )
759
872
 
873
+ # ORIGX1 record class
874
+ #
760
875
  # ORIGXn n=1, 2, or 3
761
876
  ORIGX1 =
762
877
  def_rec([ 11, 20, Pdb_Real('10.6'), :On1 ],
@@ -765,9 +880,13 @@ module Bio
765
880
  [ 46, 55, Pdb_Real('10.5'), :Tn ]
766
881
  )
767
882
 
883
+ # ORIGX2 record class
768
884
  ORIGX2 = new_inherit(ORIGX1)
885
+ # ORIGX3 record class
769
886
  ORIGX3 = new_inherit(ORIGX1)
770
887
 
888
+ # SCALE1 record class
889
+ #
771
890
  # SCALEn n=1, 2, or 3
772
891
  SCALE1 =
773
892
  def_rec([ 11, 20, Pdb_Real('10.6'), :Sn1 ],
@@ -776,9 +895,13 @@ module Bio
776
895
  [ 46, 55, Pdb_Real('10.5'), :Un ]
777
896
  )
778
897
 
898
+ # SCALE2 record class
779
899
  SCALE2 = new_inherit(SCALE1)
900
+ # SCALE3 record class
780
901
  SCALE3 = new_inherit(SCALE1)
781
902
 
903
+ # MTRIX1 record class
904
+ #
782
905
  # MTRIXn n=1,2, or 3
783
906
  MTRIX1 =
784
907
  def_rec([ 8, 10, Pdb_Integer, :serial ],
@@ -789,9 +912,12 @@ module Bio
789
912
  [ 60, 60, Pdb_Integer, :iGiven ]
790
913
  )
791
914
 
915
+ # MTRIX2 record class
792
916
  MTRIX2 = new_inherit(MTRIX1)
917
+ # MTRIX3 record class
793
918
  MTRIX3 = new_inherit(MTRIX1)
794
919
 
920
+ # TVECT record class
795
921
  TVECT =
796
922
  def_rec([ 8, 10, Pdb_Integer, :serial ],
797
923
  [ 11, 20, Pdb_Real('10.5'), :t1 ],
@@ -800,11 +926,13 @@ module Bio
800
926
  [ 41, 70, Pdb_String, :text ]
801
927
  )
802
928
 
929
+ # MODEL record class
803
930
  MODEL =
804
931
  def_rec([ 11, 14, Pdb_Integer, :serial ]
805
932
  )
806
933
  # ChangeLog: model_serial are changed to serial
807
934
 
935
+ # ATOM record class
808
936
  ATOM =
809
937
  new_direct([ 7, 11, Pdb_Integer, :serial ],
810
938
  [ 13, 16, Pdb_Atom, :name ],
@@ -823,6 +951,7 @@ module Bio
823
951
  [ 79, 80, Pdb_LString(2), :charge ]
824
952
  )
825
953
 
954
+ # ATOM record class
826
955
  class ATOM
827
956
 
828
957
  include Utils
@@ -830,11 +959,21 @@ module Bio
830
959
 
831
960
  # for backward compatibility
832
961
  alias occ occupancy
962
+ # for backward compatibility
833
963
  alias bfac tempFactor
834
964
 
835
965
  # residue the atom belongs to.
836
966
  attr_accessor :residue
837
967
 
968
+ # SIGATM record
969
+ attr_accessor :sigatm
970
+
971
+ # ANISOU record
972
+ attr_accessor :anisou
973
+
974
+ # TER record
975
+ attr_accessor :ter
976
+
838
977
  #Returns a Coordinate class instance of the xyz positions
839
978
  def xyz
840
979
  Coordinate[ x, y, z ]
@@ -870,8 +1009,27 @@ module Bio
870
1009
  @parsed = true
871
1010
  self
872
1011
  end
1012
+
1013
+ def to_s
1014
+ sprintf("%-6s%5d %-4s%-1s%3s %-1s%4d%-1s %8.3f%8.3f%8.3f%6.2f%6.2f %-4s%2s%-2s\n",
1015
+ self.record_name,
1016
+ self.serial,
1017
+ self.name,
1018
+ self.altLoc,
1019
+ self.resName,
1020
+ self.chainID,
1021
+ self.resSeq,
1022
+ self.iCode,
1023
+ self.x, self.y, self.z,
1024
+ self.occupancy,
1025
+ self.tempFactor,
1026
+ self.segID,
1027
+ self.element,
1028
+ self.charge)
1029
+ end
873
1030
  end #class ATOM
874
1031
 
1032
+ # SIGATM record class
875
1033
  SIGATM =
876
1034
  def_rec([ 7, 11, Pdb_Integer, :serial ],
877
1035
  [ 13, 16, Pdb_Atom, :name ],
@@ -890,6 +1048,7 @@ module Bio
890
1048
  [ 79, 80, Pdb_LString(2), :charge ]
891
1049
  )
892
1050
 
1051
+ # ANISOU record class
893
1052
  ANISOU =
894
1053
  def_rec([ 7, 11, Pdb_Integer, :serial ],
895
1054
  [ 13, 16, Pdb_Atom, :name ],
@@ -909,6 +1068,13 @@ module Bio
909
1068
  [ 79, 80, Pdb_LString(2), :charge ]
910
1069
  )
911
1070
 
1071
+ # ANISOU record class
1072
+ class ANISOU
1073
+ # SIGUIJ record
1074
+ attr_accessor :siguij
1075
+ end #class ANISOU
1076
+
1077
+ # SIGUIJ record class
912
1078
  SIGUIJ =
913
1079
  def_rec([ 7, 11, Pdb_Integer, :serial ],
914
1080
  [ 13, 16, Pdb_Atom, :name ],
@@ -928,6 +1094,7 @@ module Bio
928
1094
  [ 79, 80, Pdb_LString(2), :charge ]
929
1095
  )
930
1096
 
1097
+ # TER record class
931
1098
  TER =
932
1099
  def_rec([ 7, 11, Pdb_Integer, :serial ],
933
1100
  [ 18, 20, Pdb_Residue_name, :resName ],
@@ -954,12 +1121,19 @@ module Bio
954
1121
  # [ 79, 80, Pdb_LString(2), :charge ]
955
1122
  # )
956
1123
 
1124
+ # HETATM record class
957
1125
  HETATM = new_inherit(ATOM)
958
1126
 
1127
+ # HETATM record class.
1128
+ # It inherits ATOM class.
1129
+ class HETATM; end
1130
+
1131
+ # ENDMDL record class
959
1132
  ENDMDL =
960
1133
  def_rec([ 2, 1, Pdb_Integer, :serial ] # dummy field (always 0)
961
1134
  )
962
1135
 
1136
+ # CONECT record class
963
1137
  CONECT =
964
1138
  def_rec([ 7, 11, Pdb_Integer, :serial ],
965
1139
  [ 12, 16, Pdb_Integer, :serial ],
@@ -974,6 +1148,7 @@ module Bio
974
1148
  [ 57, 61, Pdb_Integer, :serial ]
975
1149
  )
976
1150
 
1151
+ # MASTER record class
977
1152
  MASTER =
978
1153
  def_rec([ 11, 15, Pdb_Integer, :numRemark ],
979
1154
  [ 16, 20, Pdb_Integer, "0" ],
@@ -989,27 +1164,32 @@ module Bio
989
1164
  [ 66, 70, Pdb_Integer, :numSeq ]
990
1165
  )
991
1166
 
1167
+ # JRNL record classes
992
1168
  class Jrnl < self
993
1169
  # subrecord of JRNL
994
1170
  # 13, 16
1171
+ # JRNL AUTH record class
995
1172
  AUTH =
996
1173
  def_rec([ 13, 16, Pdb_String, :sub_record ], # "AUTH"
997
1174
  [ 17, 18, Pdb_Continuation, nil ],
998
1175
  [ 20, 70, Pdb_List, :authorList ]
999
1176
  )
1000
1177
 
1178
+ # JRNL TITL record class
1001
1179
  TITL =
1002
1180
  def_rec([ 13, 16, Pdb_String, :sub_record ], # "TITL"
1003
1181
  [ 17, 18, Pdb_Continuation, nil ],
1004
1182
  [ 20, 70, Pdb_LString, :title ]
1005
1183
  )
1006
1184
 
1185
+ # JRNL EDIT record class
1007
1186
  EDIT =
1008
1187
  def_rec([ 13, 16, Pdb_String, :sub_record ], # "EDIT"
1009
1188
  [ 17, 18, Pdb_Continuation, nil ],
1010
1189
  [ 20, 70, Pdb_List, :editorList ]
1011
1190
  )
1012
1191
 
1192
+ # JRNL REF record class
1013
1193
  REF =
1014
1194
  def_rec([ 13, 16, Pdb_String, :sub_record ], # "REF"
1015
1195
  [ 17, 18, Pdb_Continuation, nil ],
@@ -1020,12 +1200,14 @@ module Bio
1020
1200
  [ 63, 66, Pdb_Integer, :year ]
1021
1201
  )
1022
1202
 
1203
+ # JRNL PUBL record class
1023
1204
  PUBL =
1024
1205
  def_rec([ 13, 16, Pdb_String, :sub_record ], # "PUBL"
1025
1206
  [ 17, 18, Pdb_Continuation, nil ],
1026
1207
  [ 20, 70, Pdb_LString, :pub ]
1027
1208
  )
1028
1209
 
1210
+ # JRNL REFN record class
1029
1211
  REFN =
1030
1212
  def_rec([ 13, 16, Pdb_String, :sub_record ], # "REFN"
1031
1213
  [ 20, 23, Pdb_LString(4), "ASTM" ],
@@ -1037,21 +1219,25 @@ module Bio
1037
1219
  )
1038
1220
 
1039
1221
  # default or unknown record
1040
- # ''
1222
+ #
1041
1223
  Default =
1042
1224
  def_rec([ 13, 16, Pdb_String, :sub_record ]) # ""
1043
1225
 
1226
+ # definitions (hash)
1044
1227
  Definition = create_definition_hash
1045
1228
  end #class JRNL
1046
1229
 
1230
+ # REMARK record classes for REMARK 1
1047
1231
  class Remark1 < self
1048
1232
  # 13, 16
1233
+ # REMARK 1 REFERENCE record class
1049
1234
  EFER =
1050
1235
  def_rec([ 8, 10, Pdb_Integer, :remarkNum ], # "1"
1051
1236
  [ 12, 20, Pdb_String, :sub_record ], # "REFERENCE"
1052
1237
  [ 22, 70, Pdb_Integer, :refNum ]
1053
1238
  )
1054
1239
 
1240
+ # REMARK 1 AUTH record class
1055
1241
  AUTH =
1056
1242
  def_rec([ 8, 10, Pdb_Integer, :remarkNum ], # "1"
1057
1243
  [ 13, 16, Pdb_String, :sub_record ], # "AUTH"
@@ -1059,6 +1245,7 @@ module Bio
1059
1245
  [ 20, 70, Pdb_List, :authorList ]
1060
1246
  )
1061
1247
 
1248
+ # REMARK 1 TITL record class
1062
1249
  TITL =
1063
1250
  def_rec([ 8, 10, Pdb_Integer, :remarkNum ], # "1"
1064
1251
  [ 13, 16, Pdb_String, :sub_record ], # "TITL"
@@ -1066,6 +1253,7 @@ module Bio
1066
1253
  [ 20, 70, Pdb_LString, :title ]
1067
1254
  )
1068
1255
 
1256
+ # REMARK 1 EDIT record class
1069
1257
  EDIT =
1070
1258
  def_rec([ 8, 10, Pdb_Integer, :remarkNum ], # "1"
1071
1259
  [ 13, 16, Pdb_String, :sub_record ], # "EDIT"
@@ -1073,6 +1261,7 @@ module Bio
1073
1261
  [ 20, 70, Pdb_LString, :editorList ]
1074
1262
  )
1075
1263
 
1264
+ # REMARK 1 REF record class
1076
1265
  REF =
1077
1266
  def_rec([ 8, 10, Pdb_Integer, :remarkNum ], # "1"
1078
1267
  [ 13, 16, Pdb_LString(3), :sub_record ], # "REF"
@@ -1084,6 +1273,7 @@ module Bio
1084
1273
  [ 63, 66, Pdb_Integer, :year ]
1085
1274
  )
1086
1275
 
1276
+ # REMARK 1 PUBL record class
1087
1277
  PUBL =
1088
1278
  def_rec([ 8, 10, Pdb_Integer, :remarkNum ], # "1"
1089
1279
  [ 13, 16, Pdb_String, :sub_record ], # "PUBL"
@@ -1091,6 +1281,7 @@ module Bio
1091
1281
  [ 20, 70, Pdb_LString, :pub ]
1092
1282
  )
1093
1283
 
1284
+ # REMARK 1 REFN record class
1094
1285
  REFN =
1095
1286
  def_rec([ 8, 10, Pdb_Integer, :remarkNum ], # "1"
1096
1287
  [ 13, 16, Pdb_String, :sub_record ], # "REFN"
@@ -1102,14 +1293,17 @@ module Bio
1102
1293
  [ 68, 70, Pdb_LString(4), :coden ]
1103
1294
  )
1104
1295
 
1296
+ # default (or unknown) record class for REMARK 1
1105
1297
  Default =
1106
1298
  def_rec([ 8, 10, Pdb_Integer, :remarkNum ], # "1"
1107
1299
  [ 13, 16, Pdb_String, :sub_record ] # ""
1108
1300
  )
1109
1301
 
1302
+ # definitions (hash)
1110
1303
  Definition = create_definition_hash
1111
1304
  end #class Remark1
1112
1305
 
1306
+ # REMARK record classes for REMARK 2
1113
1307
  class Remark2 < self
1114
1308
  # 29, 38 == 'ANGSTROMS.'
1115
1309
  ANGSTROMS =
@@ -1135,16 +1329,21 @@ module Bio
1135
1329
  )
1136
1330
  end #class Remark2
1137
1331
 
1332
+ # REMARK record class for REMARK n (n>=3)
1138
1333
  RemarkN =
1139
1334
  def_rec([ 8, 10, Pdb_Integer, :remarkNum ],
1140
1335
  [ 12, 70, Pdb_LString, :text ]
1141
1336
  )
1142
1337
 
1338
+ # default (or unknown) record class
1143
1339
  Default = def_rec([ 8, 70, Pdb_LString, :text ])
1144
1340
 
1341
+ # definitions (hash)
1145
1342
  Definition = create_definition_hash
1146
1343
 
1147
- # because END is a reserved word of Ruby, it is separately
1344
+ # END record class.
1345
+ #
1346
+ # Because END is a reserved word of Ruby, it is separately
1148
1347
  # added to the hash
1149
1348
  End =
1150
1349
  def_rec([ 2, 1, Pdb_Integer, :serial ]) # dummy field (always 0)
@@ -1195,6 +1394,7 @@ module Bio
1195
1394
  'TER' => true,
1196
1395
  }
1197
1396
 
1397
+ # Creates a new Bio::PDB object from given <em>str</em>.
1198
1398
  def initialize(str)
1199
1399
  #Aha! Our entry into the world of PDB parsing, we initialise a PDB
1200
1400
  #object with the whole PDB file as a string
@@ -1211,9 +1411,11 @@ module Bio
1211
1411
  cont = false
1212
1412
 
1213
1413
  #Empty current model
1214
- cModel = Bio::PDB::Model.new
1215
- cChain = Bio::PDB::Chain.new
1216
- cResidue = Bio::PDB::Residue.new
1414
+ cModel = Model.new
1415
+ cChain = nil #Chain.new
1416
+ cResidue = nil #Residue.new
1417
+ cLigand = nil #Heterogen.new
1418
+ c_atom = nil
1217
1419
 
1218
1420
  #Goes through each line and replace that line with a PDB::Record
1219
1421
  @data.collect! do |line|
@@ -1236,87 +1438,107 @@ module Bio
1236
1438
  end
1237
1439
 
1238
1440
  # Do something for ATOM and HETATM
1239
- case key
1240
- when 'ATOM'
1241
- residueID = "#{f.resSeq}#{f.iCode.strip}".strip
1242
- #p f
1243
-
1244
- if f.chainID == cChain.id
1441
+ if key == 'ATOM' or key == 'HETATM' then
1442
+ if cChain and f.chainID == cChain.id
1245
1443
  chain = cChain
1246
- elsif !(chain = cModel[f.chainID])
1247
- #If we don't have chain, add a new chain
1248
- newChain = Chain.new(f.chainID, cModel)
1249
- cModel.addChain(newChain)
1250
- cChain = newChain
1251
- chain = newChain
1252
- end
1253
-
1254
- if !newChain and residueID == cResidue.id
1255
- residue = cResidue
1256
- elsif newChain or !(residue = chain[residueID])
1257
- newResidue = Residue.new(f.resName, f.resSeq, f.iCode, chain)
1258
- chain.addResidue(newResidue)
1259
- cResidue = newResidue
1260
- residue = newResidue
1261
- end
1262
-
1263
- f.residue = residue
1264
- residue.addAtom(f)
1265
-
1266
- when 'HETATM'
1267
-
1268
- #Each model has a special solvent chain
1269
- #any chain id with the solvent is lost
1270
- #I can fix this if really needed
1271
- if f.resName == 'HOH'
1272
- solvent = Residue.new(f.resName, f.resSeq, f.iCode,
1273
- cModel.solvent, true)
1274
- #p solvent
1275
- f.residue = solvent
1276
- solvent.addAtom(f)
1277
- cModel.addSolvent(solvent)
1278
-
1279
1444
  else
1280
-
1281
- #Make residue we add 'LIGAND' to the id if it's a HETATM
1282
- #I think this is neccessary because some PDB files reuse
1283
- #numbers for HETATMS
1284
- residueID = "#{f.resSeq}#{f.iCode.strip}".strip
1285
- residueID = "LIGAND" + residueID
1286
- #p f
1287
- #p residueID
1288
-
1289
- if f.chainID == cChain.id
1290
- chain = cChain
1291
- elsif !(chain = cModel[f.chainID])
1292
- #If we don't have chain, add a new chain
1445
+ if chain = cModel[f.chainID]
1446
+ cChain = chain unless cChain
1447
+ else
1448
+ # If we don't have chain, add a new chain
1293
1449
  newChain = Chain.new(f.chainID, cModel)
1294
1450
  cModel.addChain(newChain)
1295
1451
  cChain = newChain
1296
1452
  chain = newChain
1297
1453
  end
1454
+ end
1455
+ end
1456
+
1457
+ case key
1458
+ when 'ATOM'
1459
+ c_atom = f
1460
+ residueID = Residue.get_residue_id_from_atom(f)
1298
1461
 
1299
- if !newChain and residueID == cResidue.id
1300
- residue = cResidue
1301
- elsif newChain or !(residue = chain[residueID])
1302
- newResidue = Residue.new(f.resName, f.resSeq, f.iCode,
1303
- chain, true)
1304
- chain.addLigand(newResidue)
1462
+ if cResidue and residueID == cResidue.id
1463
+ residue = cResidue
1464
+ else
1465
+ if residue = chain.get_residue_by_id(residueID)
1466
+ cResidue = residue unless cResidue
1467
+ else
1468
+ # add a new residue
1469
+ newResidue = Residue.new(f.resName, f.resSeq, f.iCode, chain)
1470
+ chain.addResidue(newResidue)
1305
1471
  cResidue = newResidue
1306
1472
  residue = newResidue
1307
1473
  end
1474
+ end
1475
+
1476
+ f.residue = residue
1477
+ residue.addAtom(f)
1478
+
1479
+ when 'HETATM'
1480
+ c_atom = f
1481
+ residueID = Heterogen.get_residue_id_from_atom(f)
1308
1482
 
1309
- f.residue = residue
1310
- residue.addAtom(f)
1311
-
1483
+ if cLigand and residueID == cLigand.id
1484
+ ligand = cLigand
1485
+ else
1486
+ if ligand = chain.get_heterogen_by_id(residueID)
1487
+ cLigand = ligand unless cLigand
1488
+ else
1489
+ # add a new heterogen
1490
+ newLigand = Heterogen.new(f.resName, f.resSeq, f.iCode, chain)
1491
+ chain.addLigand(newLigand)
1492
+ cLigand = newLigand
1493
+ ligand = newLigand
1494
+ #Each model has a special solvent chain. (for compatibility)
1495
+ if f.resName == 'HOH'
1496
+ cModel.addSolvent(newLigand)
1497
+ end
1498
+ end
1312
1499
  end
1313
1500
 
1501
+ f.residue = ligand
1502
+ ligand.addAtom(f)
1503
+
1314
1504
  when 'MODEL'
1315
- if cModel.model_serial
1505
+ c_atom = nil
1506
+ if cModel.model_serial or cModel.chains.size > 0 then
1316
1507
  self.addModel(cModel)
1317
1508
  end
1318
- model_serial = line[6,5]
1319
- cModel = Model.new(model_serial)
1509
+ cModel = Model.new(f.serial)
1510
+
1511
+ when 'TER'
1512
+ if c_atom
1513
+ c_atom.ter = f
1514
+ else
1515
+ #$stderr.puts "Warning: stray TER?"
1516
+ end
1517
+ when 'SIGATM'
1518
+ if c_atom
1519
+ #$stderr.puts "Warning: duplicated SIGATM?" if c_atom.sigatm
1520
+ c_atom.sigatm = f
1521
+ else
1522
+ #$stderr.puts "Warning: stray SIGATM?"
1523
+ end
1524
+ when 'ANISOU'
1525
+ if c_atom
1526
+ #$stderr.puts "Warning: duplicated ANISOU?" if c_atom.anisou
1527
+ c_atom.anisou = f
1528
+ else
1529
+ #$stderr.puts "Warning: stray ANISOU?"
1530
+ end
1531
+ when 'SIGUIJ'
1532
+ if c_atom and c_atom.anisou
1533
+ #$stderr.puts "Warning: duplicated SIGUIJ?" if c_atom.anisou.siguij
1534
+ c_atom.anisou.siguij = f
1535
+ else
1536
+ #$stderr.puts "Warning: stray SIGUIJ?"
1537
+ end
1538
+
1539
+ else
1540
+ c_atom = nil
1541
+
1320
1542
  end
1321
1543
  f
1322
1544
  end #each
@@ -1325,34 +1547,54 @@ module Bio
1325
1547
  @data.compact!
1326
1548
  end #def initialize
1327
1549
 
1328
- attr_reader :data, :hash
1550
+ # all records in this entry as an array.
1551
+ attr_reader :data
1552
+
1553
+ # all records in this entry as an hash accessed by record names.
1554
+ attr_reader :hash
1329
1555
 
1330
- #Adds a Bio::Model to the current strucutre
1556
+ # models in this entry (array).
1557
+ attr_reader :models
1558
+
1559
+ # Adds a <code>Bio::Model</code> object to the current strucutre.
1560
+ # Adds a model to the current structure.
1561
+ # Returns self.
1331
1562
  def addModel(model)
1332
1563
  raise "Expecting a Bio::PDB::Model" if not model.is_a? Bio::PDB::Model
1333
1564
  @models.push(model)
1334
1565
  self
1335
1566
  end
1336
1567
 
1337
- #Iterates over the models
1568
+ # Iterates over each model.
1569
+ # Iterates over each of the models in the structure.
1570
+ # Returns <code>self</code>.
1338
1571
  def each
1339
1572
  @models.each{ |model| yield model }
1573
+ self
1340
1574
  end
1341
- #Alias needed for Bio::PDB::ModelFinder
1575
+ # Alias needed for Bio::PDB::ModelFinder
1342
1576
  alias each_model each
1343
1577
 
1344
- #Provides keyed access to the models based on serial number
1345
- #returns nil if it's not there (should it raise an exception?)
1578
+ # Provides keyed access to the models based on serial number
1579
+ # returns nil if it's not there
1346
1580
  def [](key)
1347
1581
  @models.find{ |model| key == model.model_serial }
1348
1582
  end
1349
-
1583
+ #--
1584
+ # (should it raise an exception?)
1585
+ #++
1586
+
1587
+ #--
1350
1588
  #Stringifies to a list of atom records - we could add the annotation
1351
1589
  #as well if needed
1590
+ #++
1591
+
1592
+ # Returns a string of Bio::PDB::Models. This propogates down the heirarchy
1593
+ # till you get to Bio::PDB::Record::ATOM which are outputed in PDB format
1352
1594
  def to_s
1353
1595
  string = ""
1354
1596
  @models.each{ |model| string << model.to_s }
1355
- string << "END"
1597
+ string << "END\n"
1356
1598
  return string
1357
1599
  end
1358
1600
 
@@ -1389,12 +1631,30 @@ module Bio
1389
1631
  end
1390
1632
  private :make_grouping
1391
1633
 
1392
- def record(name)
1393
- @hash[name]
1634
+ # Gets all records whose record type is _name_.
1635
+ # Returns an array of <code>Bio::PDB::Record::*</code> objects.
1636
+ #
1637
+ # if _name_ is nil, returns hash storing all record data.
1638
+ #
1639
+ # Example:
1640
+ # p pdb.record('HETATM')
1641
+ # p pdb.record['HETATM']
1642
+ #
1643
+ def record(name = nil)
1644
+ name ? @hash[name] : @hash
1394
1645
  end
1395
1646
 
1647
+ #--
1396
1648
  # PDB original methods
1397
1649
  #Returns a hash of the REMARK records based on the remarkNum
1650
+ #++
1651
+
1652
+ # Gets REMARK records.
1653
+ # If no arguments, it returns all REMARK records as a hash.
1654
+ # If remark number is specified, returns only corresponding REMARK records.
1655
+ # If number == 1 or 2 ("REMARK 1" or "REMARK 2"), returns an array
1656
+ # of Bio::PDB::Record instances. Otherwise, returns an array of strings.
1657
+ #
1398
1658
  def remark(nn = nil)
1399
1659
  unless defined?(@remark)
1400
1660
  h = make_hash(self.record('REMARK'), :remarkNum)
@@ -1409,7 +1669,11 @@ module Bio
1409
1669
  nn ? @remark[nn] : @remark
1410
1670
  end
1411
1671
 
1412
- #Returns a hash of journal entries
1672
+ # Gets JRNL records.
1673
+ # If no arguments, it returns all JRNL records as a hash.
1674
+ # If sub record name is specified, it returns only corresponding records
1675
+ # as an array of Bio::PDB::Record instances.
1676
+ #
1413
1677
  def jrnl(sub_record = nil)
1414
1678
  unless defined?(@jrnl)
1415
1679
  @jrnl = make_hash(self.record('JRNL'), :sub_record)
@@ -1417,8 +1681,18 @@ module Bio
1417
1681
  sub_record ? @jrnl[sub_record] : @jrnl
1418
1682
  end
1419
1683
 
1684
+ #--
1420
1685
  #Finding methods - just grabs the record with the appropriate id
1421
1686
  #or returns and array of all of them
1687
+ #++
1688
+
1689
+ # Gets HELIX records.
1690
+ # If no arguments are given, it returns all HELIX records.
1691
+ # (Returns an array of <code>Bio::PDB::Record::HELIX</code> instances.)
1692
+ # If <em>helixID</em> is given, it only returns records
1693
+ # corresponding to given <em>helixID</em>.
1694
+ # (Returns an <code>Bio::PDB::Record::HELIX</code> instance.)
1695
+ #
1422
1696
  def helix(helixID = nil)
1423
1697
  if helixID then
1424
1698
  self.record('HELIX').find { |f| f.helixID == helixID }
@@ -1427,6 +1701,13 @@ module Bio
1427
1701
  end
1428
1702
  end
1429
1703
 
1704
+ # Gets TURN records.
1705
+ # If no arguments are given, it returns all TURN records.
1706
+ # (Returns an array of <code>Bio::PDB::Record::TURN</code> instances.)
1707
+ # If <em>turnId</em> is given, it only returns a record
1708
+ # corresponding to given <em>turnId</em>.
1709
+ # (Returns an <code>Bio::PDB::Record::TURN</code> instance.)
1710
+ #
1430
1711
  def turn(turnId = nil)
1431
1712
  if turnId then
1432
1713
  self.record('TURN').find { |f| f.turnId == turnId }
@@ -1435,6 +1716,11 @@ module Bio
1435
1716
  end
1436
1717
  end
1437
1718
 
1719
+ # Gets SHEET records.
1720
+ # If no arguments are given, it returns all SHEET records
1721
+ # as an array of arrays of <code>Bio::PDB::Record::SHEET</code> instances.
1722
+ # If <em>sheetID</em> is given, it returns an array of
1723
+ # <code>Bio::PDB::Record::SHEET</code> instances.
1438
1724
  def sheet(sheetID = nil)
1439
1725
  unless defined?(@sheet)
1440
1726
  @sheet = make_grouping(self.record('SHEET'), :sheetID)
@@ -1446,11 +1732,20 @@ module Bio
1446
1732
  end
1447
1733
  end
1448
1734
 
1735
+ # Gets SSBOND records.
1449
1736
  def ssbond
1450
1737
  self.record('SSBOND')
1451
1738
  end
1452
1739
 
1453
- #Get seqres - we get this to return a nice Bio::Seq object
1740
+ #--
1741
+ # Get seqres - we get this to return a nice Bio::Seq object
1742
+ #++
1743
+
1744
+ # Amino acid or nucleic acid sequence of backbone residues in "SEQRES".
1745
+ # If <em>chainID</em> is given, it returns corresponding sequence
1746
+ # as an array of string.
1747
+ # Otherwise, returns a hash which contains all sequences.
1748
+ #
1454
1749
  def seqres(chainID = nil)
1455
1750
  unless defined?(@seqres)
1456
1751
  h = make_hash(self.record('SEQRES'), :chainID)
@@ -1458,14 +1753,27 @@ module Bio
1458
1753
  h.each do |k, a|
1459
1754
  a.collect! { |f| f.resName }
1460
1755
  a.flatten!
1461
- a.collect!{ |aa|
1462
- #aa is three letter code: i.e. ALA
1463
- #need to look up with Ala
1464
- aa = aa.capitalize
1465
- aa = AminoAcid.names.invert[aa]
1466
- aa = 'X' if aa.nil?
1467
- }
1468
- newHash[k] = Bio::Sequence::AA.new(a.to_s)
1756
+ # determine nuc or aa?
1757
+ tmp = Hash.new(0)
1758
+ a[0,13].each { |x| tmp[x.to_s.strip.size] += 1 }
1759
+ if tmp[3] >= tmp[1] then
1760
+ # amino acid sequence
1761
+ a.collect! do |aa|
1762
+ #aa is three letter code: i.e. ALA
1763
+ #need to look up with Ala
1764
+ aa = aa.capitalize
1765
+ (Bio::AminoAcid.three2one(aa) or 'X')
1766
+ end
1767
+ seq = Bio::Sequence::AA.new(a.to_s)
1768
+ else
1769
+ # nucleic acid sequence
1770
+ a.collect! do |na|
1771
+ na = na.strip
1772
+ na.size == 1 ? na : 'n'
1773
+ end
1774
+ seq = Bio::Sequence::NA.new(a.to_s)
1775
+ end
1776
+ newHash[k] = seq
1469
1777
  end
1470
1778
  @seqres = newHash
1471
1779
  end
@@ -1476,6 +1784,10 @@ module Bio
1476
1784
  end
1477
1785
  end
1478
1786
 
1787
+ # Gets DBREF records.
1788
+ # Returns an array of Bio::PDB::Record::DBREF objects.
1789
+ #
1790
+ # If <em>chainID</em> is given, it returns corresponding DBREF records.
1479
1791
  def dbref(chainID = nil)
1480
1792
  if chainID then
1481
1793
  self.record('DBREF').find_all { |f| f.chainID == chainID }
@@ -1484,28 +1796,38 @@ module Bio
1484
1796
  end
1485
1797
  end
1486
1798
 
1799
+ # Keywords in "KEYWDS".
1800
+ # Returns an array of string.
1487
1801
  def keywords
1488
1802
  self.record('KEYWDS').collect { |f| f.keywds }.flatten
1489
1803
  end
1490
1804
 
1805
+ # Classification in "HEADER".
1491
1806
  def classification
1492
1807
  self.record('HEADER').first.classification
1493
1808
  end
1494
1809
 
1810
+ #--
1495
1811
  # Bio::DB methods
1812
+ #++
1813
+
1814
+ # PDB identifier written in "HEADER". (e.g. 1A00)
1496
1815
  def entry_id
1497
1816
  @id = self.record('HEADER').first.idCode unless @id
1498
1817
  @id
1499
1818
  end
1500
1819
 
1820
+ # Same as <tt>Bio::PDB#entry_id</tt>.
1501
1821
  def accession
1502
1822
  self.entry_id
1503
1823
  end
1504
1824
 
1825
+ # Title of this entry in "TITLE".
1505
1826
  def definition
1506
1827
  self.record('TITLE').first.title
1507
1828
  end
1508
1829
 
1830
+ # Current modification number in "REVDAT".
1509
1831
  def version
1510
1832
  self.record('REVDAT').first.modNum
1511
1833
  end
@@ -1514,169 +1836,3 @@ module Bio
1514
1836
 
1515
1837
  end #module Bio
1516
1838
 
1517
- =begin
1518
-
1519
- = Caution
1520
-
1521
- This is a test version, specs of these class shall be changed.
1522
-
1523
- = Bio::PDB < Bio::DB
1524
-
1525
- PDB File format class.
1526
-
1527
- --- Bio::PDB.new(str)
1528
-
1529
- Creates new object.
1530
-
1531
- --- Bio::PDB#entry_id
1532
-
1533
- PDB identifier written in "HEADER". (e.g. 1A00)
1534
-
1535
- --- Bio::PDB#accession
1536
-
1537
- Same as Bio::PDB#entry_id
1538
-
1539
- --- Bio::PDB#version
1540
-
1541
- Current modification number in "REVDAT".
1542
-
1543
- --- Bio::PDB#definition
1544
-
1545
- Title of this entry in "TITLE".
1546
-
1547
- --- Bio::PDB#keywords
1548
-
1549
- Keywords in "KEYWDS".
1550
- Returns an array of string.
1551
-
1552
- --- Bio::PDB#classification
1553
-
1554
- Classification in "HEADER".
1555
-
1556
- --- Bio::PDB#record(name)
1557
-
1558
- Gets all records whose record type is 'name'.
1559
- Returns an array of Bio::PDB::Record.
1560
-
1561
- --- Bio::PDB#remark(number = nil)
1562
-
1563
- Gets REMARK records.
1564
- If no arguments, it returns all REMARK records as a hash.
1565
- If remark number is specified, returns only corresponding REMARK records.
1566
- If number == 1 or 2 ("REMARK 1" or "REMARK 2"), returns an array
1567
- of Bio::PDB::Record instances. Otherwise, returns an array of strings.
1568
-
1569
- --- Bio::PDB#jrnl(sub_record = nil)
1570
-
1571
- Gets JRNL records.
1572
- If no arguments, it returns all JRNL records as a hash.
1573
- If sub record name is specified, it returns only corresponding records
1574
- as an array of Bio::PDB::Record instances.
1575
-
1576
- --- Bio::PDB#seqres(chainID = nil)
1577
-
1578
- Amino acid or nucleic acid sequence of backbone residues in "SEQRES".
1579
- If chainID is given, it returns corresponding sequence as an array of string.
1580
- Otherwise, returns a hash which contains all sequences.
1581
-
1582
- --- Bio::PDB#helix(helixID = nil)
1583
-
1584
- Gets HELIX records.
1585
- If no arguments are given, it returns all HELIX records.
1586
- (Returns an array of Bio::PDB::Record instances.)
1587
- If helixID is given, it only returns records corresponding to given helixID.
1588
- (Returns an Bio::PDB::Record instance.)
1589
-
1590
- --- Bio::PDB#sheet(sheetID = nil)
1591
-
1592
- Gets SHEET records.
1593
- If no arguments are given, it returns all SHEET records as an array of
1594
- arrays of Bio::PDB::Record instances.
1595
- If sheetID is given, it returns an array of Bio::PDB::Record instances.
1596
-
1597
- --- Bio::PDB#turn(turnId = nil)
1598
-
1599
- Gets TURN records.
1600
- If no arguments are given, it returns all TURN records.
1601
- (Returns an array of Bio::PDB::Record instances.)
1602
- If turnId is given, it only returns a record corresponding to given turnId.
1603
- (Returns an Bio::PDB::Record instance.)
1604
-
1605
- --- Bio::PDB.addModel(model)
1606
-
1607
- Adds a model to the current structure
1608
- Returns self
1609
-
1610
- --- Bio::PDB.each
1611
-
1612
- Iterates over each of the models in the structure
1613
- Returns Bio::PDB::Models
1614
-
1615
- --- Bio::PDB[](key)
1616
-
1617
- Returns the model with the given key as serial number
1618
-
1619
- --- Bio::PDB.to_s
1620
-
1621
- Returns a string of Bio::PDB::Models. This propogates down the heirarchy
1622
- till you get to Bio::PDB::Atoms which are outputed in PDB format
1623
-
1624
-
1625
- = Bio::PDB::Record < Hash
1626
-
1627
- A class for single PDB record.
1628
- Basically, each line of a PDB file corresponds to an instance of the class.
1629
- If continuation exists, multiple lines may correspond to single instance.
1630
-
1631
- --- Bio::PDB::Record.new(line)
1632
-
1633
- Internal use only.
1634
- Creates a new instance.
1635
-
1636
- --- Bio::PDB::Record#add_continuation(line)
1637
-
1638
- Internal use only.
1639
- If continuation is allowed and 'line' is a continuation of this record,
1640
- it adds 'line' and returns self.
1641
- Otherwise, returns false.
1642
-
1643
- --- Bio::PDB::Record#original_data
1644
-
1645
- Original text (except that "\n" are truncated) of this record.
1646
- Returns an array of string.
1647
-
1648
- --- Bio::PDB::Record#record_type
1649
-
1650
- Record type of this record, e.g. "HEADER", "ATOM".
1651
-
1652
- --- Bio::PDB::Record#do_parse
1653
-
1654
- In order to speeding up processing of PDB File format,
1655
- fields have not been parsed before calling this method.
1656
-
1657
- If you want to use this class as a hash (not so recommended),
1658
- you must call this method once.
1659
-
1660
- When accessing via rec.xxxxx style (described below),
1661
- do_parse is automatically called.
1662
-
1663
- Returns self
1664
-
1665
- --- Bio::PDB::Record#"anything"
1666
-
1667
- Same as Bio::PDB::Record#[](:anything) after do_parse.
1668
- For example, r.helixID is same as r.do_parse; r[:helixID] .
1669
-
1670
-
1671
- = Bio::PDB::FieldDef
1672
-
1673
- Internal use only.
1674
- Format definition of each record.
1675
-
1676
- = References
1677
-
1678
- * ((<URL:http://www.rcsb.org/pdb/>))
1679
- * PDB File Format Contents Guide Version 2.2 (20 December 1996)
1680
- ((<URL:http://www.rcsb.org/pdb/docs/format/pdbguide2.2/guide2.2_frame.html>))
1681
-
1682
- =end