2

I am confused on why the code below does not work:

class ComparativeAnnotatorConfiguration(HashableNamespace):
 """
 Takes the initial configuration from the main driver script and builds paths to all files that will be produced
 by these tasks.
 """
 def __init__(self, args, gene_set, query_genome_files, target_genome_files, annot_files, transmap):
 self.work_dir = os.path.join(args.workDir, 'comparativeAnnotator', gene_set.sourceGenome, gene_set.geneSet)
 self.metrics_dir = os.path.join(args.outputDir, 'metrics')
 self.tx_set_dir = os.path.join(args.outputDir, 'tm_transcript_set')
 self.reference = self.Reference(args, query_genome_files, annot_files, self.work_dir)
 self.transmap = self.TransMap(args, query_genome_files, target_genome_files, annot_files, transmap, self.work_dir)
 class Reference(HashableNamespace):
 """
 The args object that will be passed directly to jobTree
 """
 def __init__(self, args, query_genome_files, annot_files, out_dir):
 self.__dict__.update(vars(args.jobTreeOptions)) 
 self.outDir = out_dir
 self.refGenome = query_genome_files.genome
 self.refFasta = query_genome_files.genome_fasta
 self.sizes = query_genome_files.chrom_sizes
 self.annotationGp = annot_files.gp
 self.gencodeAttributes = annot_files.attributes
 self.mode = 'reference'
 class TransMap(Reference):
 """
 The args object that will be passed directly to jobTree
 """
 def __init__(self, args, query_genome_files, target_genome_files, annot_files, transmap, out_dir):
 super(self.__class__, self).Reference.__init__(self, args, query_genome_files, annot_files, out_dir)
 self.genome = target_genome_files.genome
 self.psl = transmap.psl
 self.refPsl = annot_files.psl
 self.targetGp = transmap.gp
 self.fasta = target_genome_files.fasta
 self.mode = 'transMap'

Attempting to instantiate leads to the error:

AttributeError: 'super' object has no attribute 'Reference'

I have tried different versions such as super(TransMap, self).Reference.__init__ and Reference.__init__, but all give different versions of a NameError. How is this different than the simple case outlined here:

Using super() in nested classes

asked Feb 5, 2016 at 4:57
3
  • 2
    super(self.__class__, self).__init__ ... should be enough. The result of super is already Reference Commented Feb 5, 2016 at 5:01
  • 2
    No, never pass self.__class__ to super(). It will misbehave badly if you ever subclass that class. Commented Feb 5, 2016 at 5:04
  • Have you tried this `super(TransMap, self).__init__(#your arg) Commented Feb 5, 2016 at 5:05

3 Answers 3

3

You want this:

super(ComparativeAnnotatorConfiguration.TransMap, self).__init__(...)

This is a consequence of Python's class scoping rules: class variables are not in scope inside methods. This does not change just because your "variable" is itself a class. As far as Python is concerned, that's exactly the same thing.

In Python 3, you can write the far simpler:

super().__init__(...)

This is yet another reason to upgrade.

answered Feb 5, 2016 at 5:06
Sign up to request clarification or add additional context in comments.

Comments

0

You could use super(ChildClass, self).__init__()

class BaseClass(object):
 def __init__(self, *args, **kwargs):
 pass
class ChildClass(BaseClass):
 def __init__(self, *args, **kwargs):
 super(ChildClass, self).__init__(*args, **kwargs)

Sample Inheritance and initializing parent constructor code :

class Car(object):
 condition = "new"
 def __init__(self, model, color, mpg):
 self.model = model
 self.color = color
 self.mpg = mpg
class ElectricCar(Car):
 def __init__(self, battery_type, model, color, mpg):
 self.battery_type=battery_type
 super(ElectricCar, self).__init__(model, color, mpg)
car = ElectricCar('battery', 'ford', 'golden', 10)
print car.__dict__

Here's the output:

{'color': 'golden', 'mpg': 10, 'model': 'ford', 'battery_type': 'battery'}
answered Feb 5, 2016 at 11:22

Comments

-1
super(self.__class__, self).__init__()

will call the __init__ method of parent class.

answered Feb 5, 2016 at 5:07

2 Comments

Don't do that. It misbehaves if you subclass the current class. The first argument to super() should (almost) always be an import-time constant, not something you figure out by inspecting self.
@Kevin, yes i understand that, sorry i didn't mean that way, and yes there are other drawbacks too, of using it, and yes the best way to use directly super().__init__(...) but still thanks for making me correct

Your Answer

Draft saved
Draft discarded

Sign up or log in

Sign up using Google
Sign up using Email and Password

Post as a guest

Required, but never shown

Post as a guest

Required, but never shown

By clicking "Post Your Answer", you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.