4 CXGN::Map - classes to get information on SGN mapping information and to add new map and map version data (new_map, store, & map_version functions).
8 This class was originally written to retrieve data on genetic maps in the SGN database. However, map types multiplied and this class was re-written as a factory object producing a map object of the appropriate type - genetic, fish, individual, user, etc. These map objects are defined in the CXGN::Map:: namespace. Previous documentation mentioned the existence of a CXGN::Map::Storable class, however, this never seemed to exist and the new map interface and subclasses have been written as read/write objects.
10 The "new" function has been re-cast to act as a factory object and will produce the right type of Map object given the appropriate parameters, which are defined as follows:
14 map_id genetic or fish
15 map_version_id genetic or fish
18 individual_id indivdual_map
20 Note that much of the functionality of this class has been factored out into a CXGN::LinkageGroup object, which also exists in different incarnations for the different map types.
24 John Binns <zombieite@gmail.com>, Lukas Mueller (lam87@cornell.edu) and Isaak Y Tecle (iyt2@cornell.edu)
30 This class defines the following functions to be implemented by the subclasses, and keeps the old functions for compatibility (see deprecated functions below).
35 use CXGN
::DB
::Connection
;
36 use CXGN
::Map
::Version
;
41 Usage: my $map = CXGN::Map->new($dbh, {map_version_id=>30})
42 Desc: creates a new CXGN::Map object
44 Args: - a database handle, if possible using
45 CXGN::DB::Connection object
46 - a hashref, containing either a key map_id or a key
47 map_version_id, but not both!
55 my($dbh,$map_info)=@_;
56 my $self=bless({},$class);
57 unless(CXGN
::DB
::Connection
::is_valid_dbh
($dbh)){die"Invalid DBH";}
58 ref($map_info) eq 'HASH' or die"Must send in a dbh and hash ref with a map_id key or a map_version_id key";
59 $self->{map_version_id
}=$map_info->{map_version_id
};
60 $self->{map_id
}=$map_info->{map_id
};
62 my $map_id_t = $self->{map_id
};
63 #print STDERR "map id: $map_id_t from map object\n";
66 if($self->{map_version_id
})
68 die"You must only send in a map_id or a map_version_id, not both";
70 my $map_version_id_q=$dbh->prepare("SELECT map_version_id
73 AND current_version='t'"
75 $map_version_id_q->execute($self->{map_id
});
76 ($self->{map_version_id
})=$map_version_id_q->fetchrow_array();
78 $self->{map_version_id
} or return undef;
79 my $general_info_q=$dbh->prepare
95 inner join map using (map_id)
99 $general_info_q->execute($self->{map_version_id
});
102 $self->{map_version_id
},
103 $self->{date_loaded
},
104 $self->{current_version
},
109 $self->{population_id
},
111 $self->{has_physical
}
113 )=$general_info_q->fetchrow_array();
114 if(!$self->{map_version_id
}){return undef;}
115 my $linkage_q=$dbh->prepare('SELECT linkage_group.lg_id AS lg_id,linkage_group.map_version_id AS map_version_id,
116 lg_order,lg_name, min(position) AS north_centromere, MAX(position) AS south_centromere
118 LEFT JOIN marker_location ON (north_location_id=location_id
119 OR south_location_id=location_id)
120 WHERE linkage_group.map_version_id=?
121 GROUP BY linkage_group.lg_id, linkage_group.map_version_id,
122 lg_order, lg_name order by lg_order');
123 $linkage_q->execute($self->{map_version_id
});
124 while(my $linkage_group=$linkage_q->fetchrow_hashref())
126 push(@
{$self->{linkage_groups
}},$linkage_group);
133 my $dbh = CXGN
::DB
::Connection
->new();
134 my $map_id = $self->get_map_id();
135 print STDERR
"map id from store: $map_id\n";
137 my $sth = $dbh->prepare("UPDATE sgn.map SET
142 parent1_stock_id = ?,
143 parent2_stock_id = ?,
145 population_stock_id = ?
148 $sth->execute($self->{short_name
},
152 $self->{parent1_stock_id
},
153 $self->{parent2_stock_id
},
155 $self->{population_stock_id
},
159 print STDERR
"Storing map data... \n";
160 print STDERR
"updated map id: $map_id\n";
161 #$dbh->last_insert_id("map", "sgn");
165 print STDERR
"No map id\n";
178 print STDERR
"Short map name: $name\n";
180 $sth = $dbh->prepare("SELECT map_id
182 WHERE short_name ILIKE ?"
184 $sth->execute($name);
185 $map_id = $sth->fetchrow_array();
186 print STDERR
"Map Id: $map_id\n";
189 print STDERR
"Provide map name, please.\n";
190 die "No map name provided!\n";
194 $sth = $dbh->prepare("INSERT INTO sgn.map (short_name) VALUES (?)");
195 $sth->execute($name);
196 $map_id = $dbh->last_insert_id("map", "sgn");
197 print STDERR
"stored new Map Id: $map_id\n";
200 my ($map, $map_version_id);
202 $map_version_id = CXGN
::Map
::Version
->map_version($dbh, $map_id);
203 #$map_version_id= $self->map_version($dbh, $map_id);
204 print STDERR
"created map version_id: $map_version_id for map_id: $map_id\n";
205 $map = CXGN
::Map
->new($dbh, {map_id
=>$map_id});
206 my $new_map_id = $map->{map_id
};
207 print STDERR
"new_map function with map_id = $new_map_id.\n";
217 =head2 accessors set_short_name, get_short_name
230 return $self->{short_name
};
235 $self->{short_name
}=shift;
238 =head2 accessors set_long_name, get_long_name
251 return $self->{long_name
};
256 $self->{long_name
}=shift;
259 =head2 accessors set_abstract, get_abstract
272 return $self->{abstract
};
277 $self->{abstract
}=shift;
281 =head2 accessors get_parent_1, set_parent_1
294 return $self->{parent_1
};
299 $self->{parent_1
} = shift;
302 =head2 accessors get_parent1_stock_id, set_parent1_stock_id
305 Desc: sets the stock id of parent 1 of this map.
312 sub get_parent1_stock_id
{
314 return $self->{parent1_stock_id
};
317 sub set_parent1_stock_id
{
319 $self->{parent1_stock_id
} = shift;
322 =head2 accessors get_parent2_stock_id, set_parent2_stock_id
325 Desc: sets the stock id of the parent 2 of this map.
332 sub get_parent2_stock_id
{
334 return $self->{parent2_stock_id
};
337 sub set_parent2_stock_id
{
339 $self->{parent2_stock_id
} = shift;
342 =head2 accessors get_population_stock_id, set_population_stock_id
345 Desc: sets the population id of the map, referencing
353 sub get_population_stock_id
{
355 return $self->{population_stock_id
};
358 sub set_population_stock_id
{
360 $self->{population_stock_id
} = shift;
363 =head2 accessors get_population_id, set_population_id
374 sub get_population_id
{
376 return $self->{population_id
};
379 sub set_population_id
{
381 $self->{population_id
} = shift;
398 $self->{map_id
}=shift;
402 return $self->{map_id
};
406 =head2 accessors set_linkage_groups, get_linkage_groups
417 sub get_linkage_groups
{
419 return @
{$self->{linkage_groups
}};
422 sub set_linkage_groups
{
424 @
{$self->{linkage_groups
}}=@_;
427 =head2 function add_linkage_group
437 sub add_linkage_group
{
440 push @
{$self->{linkage_groups
}}, $lg;
444 =head2 accessors set_map_type, get_map_type
457 return $self->{map_type
};
462 $self->{map_type
}=shift;
466 =head2 function get_units
478 if ($self->get_map_type() eq "genetic") {
481 elsif ($self->get_map_type() eq "fish") {
484 elsif ($self->get_map_type() =~ /sequenc/) {
487 elsif ($self->get_map_type() =~ /qtl/i) {
500 =head1 DEPRECATED FUNCTIONS
502 These functions are still working but should not be used in new code.
504 Note that these functions only work as getters and not as setters.
508 =head2 function map_id
521 return $self->{map_id
};
524 =head2 function map_version_id
536 return $self->{map_version_id
};
539 =head2 function short_name
551 return $self->{short_name
};
554 =head2 function long_name
566 return $self->{long_name
};
569 =head2 function abstract
581 return $self->{abstract
};
584 =head2 linkage_groups
588 Ret: a reference to an array of hashrefs with linkage group info.
589 hash keys include lg_name and lg_order
598 if($self->{linkage_groups
})
600 return $self->{linkage_groups
};
612 Ret: the type of the map, either 'fish' for a fish map
613 or 'genetic' for a genetic map.
622 return $self->{map_type
};
638 return $self->{has_IL
};
654 return $self->{has_physical
};
663 Desc: a shortcut function to get at the chromosome names,
665 Ret: a list of chromosome names.
674 my $linkage_groups_ref = $self->linkage_groups();
675 my @names = map $_->{lg_name
}, @
{$linkage_groups_ref};
679 =head2 has_linkage_group
683 Ret: 1 if the string or number represents a linkage group
686 Args: a string or number describing a possible linkage
693 sub has_linkage_group
{
695 my $candidate = shift;
697 $candidate=~ s/\s*(.*)\s*/$1/;
698 foreach my $n (map $_->{lg_name
} , @
{$self->linkage_groups()}) {
699 #print STDERR "comparing $n with $candidate...\n";
700 if ($candidate =~ /^$n$/i) {
701 #print STDERR "Yip!\n";
708 =head2 function get_centromere
710 Synopsis: my ($north, $south, $center) = $map->get_centromere($lg_name)
711 Arguments: a valid linkage group name
712 Returns: a three member list, the first element corresponds
713 to the north boundary of the centromere in cM
714 the second corresponds to the south boundary of
715 the centromere in cM, the third is the arithmetic mean
716 of the two first values.
726 if (! $self->has_linkage_group($lg)) {
727 die "Not a valid linkage group for this map!\n";
730 my $lg_hash = $self->get_linkage_group_hash($lg);
731 # foreach my $k (keys %$lg_hash) {
732 # print " $k, $lg_hash->{$k}\n";
734 my $north = $lg_hash->{north_centromere
};
735 my $south = $lg_hash->{south_centromere
};
736 return ($north, $south, int(($north+$south)/2));
739 sub get_linkage_group_hash
{
742 foreach my $lg_hash (@
{$self->linkage_groups()}) {
743 if ($lg_hash->{lg_name
} eq $lg_name) {