In this problem we are given a set of DNA strings and are asked to create a character table. My solution to the problem can be found here. I got a bit hung up on the problem to start with because in the description they give the following sample data and output:
Sample Dataset
ATGCTACC
CGTTTACC
ATTCGACC
AGTCTCCC
CGTCTATC
Sample Output
10110
10100
It took me a while to realise that the output is only partial, and what they are really after is:
10110
10100
10000
10111
11011
11101
Which is a character array for each non trivial position in the sequences. When I finally had this figured, the programming itself didn't take too long.
Showing posts with label Phylogeny. Show all posts
Showing posts with label Phylogeny. Show all posts
Thursday, 17 November 2016
Tuesday, 15 November 2016
Newick Format with Edge Weights
If you have already solved "Distances in Trees", then this problem will probably not take that long to complete. When I solved distances in trees, I used the Biopython module Phylo. The problem I had then was that the given trees did not contain any branch lengths, so I had to add this in the program. However in this problem the branch lengths are already included in the trees, so the new program is in fact even shorter than the original. You can find my new version of the code below and on my GitHub.
import sys
from Bio import Phylo
import io
f = open('rosalind_nkew.txt', 'r')
pairs = [i.split('\n') for i in f.read().strip().split('\n\n')]
for i, line in pairs:
x, y = line.split()
tree = Phylo.read(io.StringIO(i), 'newick')
sys.stdout.write('%s' % round(tree.distance(x,y)) + ' ')
sys.stdout.write('\n')
import sys
from Bio import Phylo
import io
f = open('rosalind_nkew.txt', 'r')
pairs = [i.split('\n') for i in f.read().strip().split('\n\n')]
for i, line in pairs:
x, y = line.split()
tree = Phylo.read(io.StringIO(i), 'newick')
sys.stdout.write('%s' % round(tree.distance(x,y)) + ' ')
sys.stdout.write('\n')
Thursday, 13 October 2016
Creating a Character Table (Finished!)
The approach I wrote about in my last post turned out to be a lot harder to implement than I initially thought, and I actually never made it past the step of splitting the tree into the possible sub-trees. After bashing my head against the problem a bit too long, I decided to try a different approach, using Biopython. The Phylo module of Biopython has a method for parsing trees in Newick format, and by using this I was also able to extract internal and external nodes of the tree in a much easier way than in my initial approach. The final version of my code can be found here on my GitHub, along with the problem description and some sample data files.
Wednesday, 12 October 2016
Creating a Character Table
Last week I finished going through the interactive edition of the book "How to Think Like a Computer Scientist". Even though I knew quite a bit of what was mentioned in the book, I learned quite a bit about Python programming and computer science in general. I would definitely recommend people with a similar background as me (coming from the biological sciences) to have a go at this book, and I especially found the parts on classes and objects useful.
When I was finished with the book I went back to working through the remaining Rosalind problems. I am currently working on "Creating a Character Table". It took me a while just to understand what they are after in this problem, but I finally figured it out and I have been able to make some progress on my program.
So, what they are after is the so called character table of an unrooted binary tree in Newick format. This table is formed of rows representing the character arrays of the tree. A character array is formed as follows:
When I was finished with the book I went back to working through the remaining Rosalind problems. I am currently working on "Creating a Character Table". It took me a while just to understand what they are after in this problem, but I finally figured it out and I have been able to make some progress on my program.
So, what they are after is the so called character table of an unrooted binary tree in Newick format. This table is formed of rows representing the character arrays of the tree. A character array is formed as follows:
- Remove one edge of the tree so that two trees are formed (the new trees can't consist of only one taxon, i.e. the split must be nontrivial).
- Assign one tree as the 0 tree (representing its taxons not having a specific trait), and the other tree as the 1 tree (representing its taxons having a specific trait). This is done arbitrarily.
- Sort the taxons lexicographically and print their corresponding number (0 or 1).
The following code is the beginning of my solution to the problem. So far it opens and reads the data file. It then iterates over the tree (in string format) and finds where the splits are, i.e. where all '),' are located in the tree. I have also started writing code for a class that can couple the name of a taxon with its assigned value and then sort these lexicograpically.
class tree_index:
def __init__(self, n, v):
self.name = n
self.value = v
def read_tree(s):
for i in range(len(s)-1):
if s[i] + s[i+1] == '),':
count = 0
for j in range(len(s)):
if s[j] == '(':
count += 1
if s[j] == ')':
count -= 1
print(count)
with open('sampledata.txt', 'r') as f:
tree = f.read().strip()
read_tree(tree)
What I want to do next is to find a way to split the tree up into two trees each time '),' appears. I then want to couple the names of the taxons to the number of the tree they belong to by using the class tree_index. If I can then add a sort functionality to the class I think the problem would be solved. I am currently working on this and will return here when I manage to find a solution.
Until then!
Wednesday, 14 September 2016
Distances in Trees
In this problem we are looking att the Newick format and how to find the distance between two nodes in a phylogenetic tree. We are given a file containing trees in Newick format and two nodes for each tree, and are asked to find the distance between those nodes.
Sample Dataset
(cat)dog;
dog cat
(dog,cat);
dog cat
Expected Output
1 2
I remember working with the Newick format before, in one of the bioinformatics courses I took, so when I started working on this problem I recalled that there were functions for the format available in Biopython. So I had a look at the documentation, and sure enough, there is a function called distance that would be suitable. However, as always, there was a slight problem. The trees given by Rosalind did not contain any branch lengths, which is what the distance function uses to calculate the distance between two nodes. To enable using this function I therefor had to assign the branches a length of 1 (done on rows 18-21). The following code (also available on Github here) yielded a result accepted by Rosalind:
import sys
from Bio import Phylo
import io
#open file and parse data
f = open('rosalind_nwck.txt','r')
pairs = [i.split('\n') for i in f.read().strip().split('\n\n')]
#for each pair:
#-parse data further with biopython
#-add branch length 1 to all branches
#-use bioputhons Phylo distance funktion to get distances
#-print result on requested format
for i, line in pairs:
x,y = line.split()
tree = Phylo.read(io.StringIO(i),'newick')
clades = tree.find_clades()
for clade in clades:
clade.branch_length = 1
sys.stdout.write('%s' % tree.distance(x,y) + ' ')
sys.stdout.write('\n')
Sample Dataset
(cat)dog;
dog cat
(dog,cat);
dog cat
Expected Output
1 2
I remember working with the Newick format before, in one of the bioinformatics courses I took, so when I started working on this problem I recalled that there were functions for the format available in Biopython. So I had a look at the documentation, and sure enough, there is a function called distance that would be suitable. However, as always, there was a slight problem. The trees given by Rosalind did not contain any branch lengths, which is what the distance function uses to calculate the distance between two nodes. To enable using this function I therefor had to assign the branches a length of 1 (done on rows 18-21). The following code (also available on Github here) yielded a result accepted by Rosalind:
import sys
from Bio import Phylo
import io
#open file and parse data
f = open('rosalind_nwck.txt','r')
pairs = [i.split('\n') for i in f.read().strip().split('\n\n')]
#for each pair:
#-parse data further with biopython
#-add branch length 1 to all branches
#-use bioputhons Phylo distance funktion to get distances
#-print result on requested format
for i, line in pairs:
x,y = line.split()
tree = Phylo.read(io.StringIO(i),'newick')
clades = tree.find_clades()
for clade in clades:
clade.branch_length = 1
sys.stdout.write('%s' % tree.distance(x,y) + ' ')
sys.stdout.write('\n')
Wednesday, 17 August 2016
Creating a Distance Matrix
This problem was fairly similar to "Counting Point Mutations" and "Error Correction in Reads". We are given a set of DNA strings and are asked to return the distance matrix of the strings. The distance between two given strings can be calculated by dividing the Hamming distance (i.e. the number of nucleotides that differ between the stings) with the length of the sequences (given that all sequences are of equal length). These values should then be printed on matrix form with 5 significant figures.
Sample Dataset
>Rosalind_9499
TTTCCATTTA
>Rosalind_0942
GATTCATTTC
>Rosalind_6568
TTTCCATTTT
>Rosalind_1833
GTTCCATTTA
Expected Output
0.00000 0.40000 0.10000 0.10000
0.40000 0.00000 0.40000 0.30000
0.10000 0.40000 0.00000 0.20000
0.10000 0.30000 0.20000 0.00000
To write this program I reused parts of the code from "Counting Point Mutations" and "Error Correction in Reads" and modified it to suit this problem. The following is the final code, which took me only 20 minutes to write. Hurray!
from Bio import SeqIO
reads = []
with open('sampledata.fasta', 'r') as f:
for record in SeqIO.parse(f, 'fasta'):
reads.append(str(record.seq))
read_len = len(reads[0])
for curr_read in reads:
distance = []
for comp_read in reads:
hamming = 0
for nt1, nt2 in zip(curr_read, comp_read):
if nt1 != nt2:
hamming += 1
distance.append(str.format('{0:.5f}', hamming / read_len))
print(*distance, sep=' ')
Thursday, 4 August 2016
Counting Phylogenetic Ancestors
This was probably the easiest problem so far. In fact, you don't even need to do any programming because the calculation is so simple. The only thing you need to realise is that for any unrooted binary tree with n leaves, the number of internal nodes is equal to n-2.
An easy way to convince yourself of this is to doodle the trees on some paper. Then you can see that a tree with 3 leaves has 1 internal node, 4 leaves have 2 internal nodes, 5 leaves have 3 internal nodes, 6 has 4, 7 has 5, 8 has 6 and so on:
An easy way to convince yourself of this is to doodle the trees on some paper. Then you can see that a tree with 3 leaves has 1 internal node, 4 leaves have 2 internal nodes, 5 leaves have 3 internal nodes, 6 has 4, 7 has 5, 8 has 6 and so on:
Monday, 1 August 2016
Completing a Tree
In this problem we are asked to find out the minimum number of edges we need to add to a graph of n nodes described by a given adjacency list in order to produce a tree. I quite quickly managed to overthink the problem and got caught up trying to build the graphs described by the adjacency list, until I finally realised there is a much simpler solution.
Sample dataset:
10
1 2
2 8
4 10
5 9
6 10
7 9
Expected output:
3
The key to this problem is to realise that a tree with n nodes contains n-1 edges. If we then look at the adjacency list, every element of this list represents a node. Thus, to obtain the number of nodes needed to produce a tree, we simply need to make the calculation n-1-elements in the list. The following Python code does just that:
data = []
with open('sampledata.txt', 'r') as f:
for line in f:
split_data = [int(x) for x in line.split()]
data.append(split_data)
n = data[0][0]
edges = data[1:]
print(n - len(edges) - 1)
Subscribe to:
Posts (Atom)
