2015-02-28 2 views
1

Я очень новичок в объектно-ориентированном программировании, и у меня возникают проблемы с тем, как управлять связью между классами, у которых есть связанные данные.Методы вызова с использованием родительского класса

Я пытаюсь представить некоторую геномную информацию о серии организмов, которые я в конечном итоге собираюсь сравнить. Таким образом, у меня есть Species класс:

class Species(object): 
    def __init__(self, species_name, genes={}, contigs={}): 
     self.species_name = species_name 
     self.genes = genes 
     self.contigs = contigs 

Тогда я хотел бы иметь Gene класс,

class Gene(object): 
    def __init__(self, locus_tag, annotation, dna_seq, aa_seq): 
     self.locus_tag = locus_tag 
     self.annotation = annotation 
     self.dna_seq = dna_seq 
     self.aa_seq = aa_seq 

Идея заключается в том, что genes метод Species будет словарь Gene объектов, где ключ locus_tagGene. Я думаю, что знаю, как реализовать эту часть.

Но одна из вещей, которые я хотел бы быть в состоянии сделать, это вызвать функцию на Gene объект, который требует зная, что Species это в (он будет выводить структуру файла, который включает в себя species_name и locus_tag, но они исходя из двух различных классов. Проще всего я могу думать о том, чтобы добавить species_name непосредственно к Gene класса, но так как каждый Gene будет находиться в пределах Species, это кажется излишним.

Я даже не уверен, где для начала - я довольно много искал, но другие вопросы, которые я нашел, либо не актуальны, либо я недостаточно понимаю, чтобы понять Леванс.

+0

Имеет ли каждый экземпляр '' 'Species''' уникальное имя? – wwii

+0

Как примечание стороны. Никогда не используйте изменяемые объекты в качестве аргументов по умолчанию. Если вам необходимо предоставить изменяемый аргумент по умолчанию, выполните следующие действия. 'def __init __ (self, species_name, genes = None, contigs = None):' и 'self.genes = гены, если гены не являются None else {}'. – Dunes

+0

@wwii да, каждый вид уникален. Могут быть гены, имена которых одинаковы, но их locus_tag будет уникальным. – kevbonham

ответ

1

Создание Gene объектов, а затем создать Species объект, передавая словарь для genes, а затем обновить Gene объектов, установив экземпляр Species к нему, например, так:

for gene in genes: 
    gene.species = species 

После этого каждый Gene экземпляра (gene) может ссылаться на свой объект Species, выполнив self.species или, например, self.species.species_name, чтобы получить имя.

+0

Я предполагаю, что везде вы написали «Серии», здесь вы имели в виду «Виды»? Итак, если я правильно понимаю это своего рода бесконечно вложенное? Поэтому я мог бы в принципе сделать «gene.species.genes [locus_tag] .species.genes ...' etc ad infinitum? – kevbonham

+1

@kevbonham: да, я имел в виду «Виды» - я обновил ответ. Вы действительно можете продолжать назначать, но, вероятно, это лучше для вашего кода, если вы этого не сделаете. Однако это будет работать, поскольку вы все еще имеете дело с объектами, и вы можете назначить их. –

1

Как правило, я не делаю то, что вы описали. Он создает круговую ссылку, которой следует избегать, когда это возможно. Объекты должны иметь иерархическую взаимосвязь. Вы должны попытаться найти способ сохранить ген и ссылку на вид вместе, где вам может потребоваться сериализация.

Для того, чтобы сериализовать ген, вы можете написать функцию, которая принимает вид и ген в качестве аргументов. например.

# if using python 2 (I think you might be) 
from __future__ import print_function 

class Species(object): 
    def __init__(self, species_name, genes={}, contigs={}): 
     self.species_name = species_name 
     self.genes = genes 
     self.contigs = contigs 

    def serialise(self, fileobj): 
     for gene in self.genes.values(): 
      self.serialise_gene(gene, fileobj) 

    def serialise_gene(self, gene, fileobj): 
     print(self.name, gene.locus_tag, sep=", ", file=fileobj) 
     # prints "name, locus_tag" to the file 

s = Species("homo erectus") 
with open("some_file.txt", "w") as f: 
    s.serialise(f) 
+0

В конечном счете, эти вещи будут записаны в базу данных (все равно нужно узнать, как это работает). Если я правильно понимаю вас, вы говорите, что в моем классе «Gene», если я хочу найти имя вида, я должен попасть в базу данных (в вашем случае «fileobj»), а не в другой класс, чтобы знаете отношения? – kevbonham

Смежные вопросы