2012-07-14 20 views
18

Eventuali duplicati:
Making a method private in a python subclass
Private Variables and Methods in PythonMetodo protetto in python

Come posso definire un metodo in una classe di pitone che è protetto e solo sottoclassi possono vederlo?

Questo è il mio codice:

class BaseType(Model): 
    def __init__(self): 
     Model.__init__(self, self.__defaults()) 


    def __defaults(self): 
     return {'name': {}, 
       'readonly': {}, 
       'constraints': {'value': UniqueMap()}, 
       'cType': {} 
     } 


    cType = property(lambda self: self.getAttribute("cType"), lambda self, data:    self.setAttribute('cType', data)) 
    name = property(lambda self: self.getAttribute("name"), lambda self, data: self.setAttribute('name', data)) 
    readonly = property(lambda self: self.getAttribute("readonly"), 
         lambda self, data: self.setAttribute('readonly', data)) 

    constraints = property(lambda self: self.getAttribute("constraints")) 

    def getJsCode(self): 
     pass 

    def getCsCode(self): 
     pass 


    def generateCsCode(self, template=None, constraintMap=None, **kwargs): 
     if not template: 
      template = self.csTemplate 

     if not constraintMap: constraintMap = {} 
     atts = "" 

     constraintMap.update(constraintMap) 

     for element in self.getNoneEmptyAttributes(): 
      if not AbstractType.constraintMap.has_key(element[0].lower()): 
       continue 
      attTemplate = Template(AbstractType.constraintMap[element[0].lower()]['cs']) 
      attValue = str(element[1]['value']) 
      atts += "%s " % attTemplate.substitute({'value': attValue}) 

     kwargs.update(dict(attributes=atts)) 

     return template.substitute(kwargs) 



class MainClass(BaseType, Model): 
    def __init__(self): 
     #Only Model will initialize 
     Model.__init__(self, self.__defaults()) 
     BaseType.__init__(self) 

    def __defaults(self): 
     return {'name': {}, 
       'fields': {'value': UniqueMap()}, 
       'innerClass': {'value': UniqueMap()}, 
       'types': {} 
     } 

    fields = property(lambda self: self.getAttribute("fields")) 
    innerClass = property(lambda self: self.getAttribute("innerClass")) 
    types = property(lambda self: self.getAttribute("types")) 


    @staticmethod 
    def isType(iType): 
    #  return type(widget) in WidgetSelector.widgets.itervalues() 
     return isinstance(iType, AbstractType) 

    def addType(self, type): 
     if not MainClass.isType(type): 
      raise Exception, "Unknown widget type %s" % type 
     self.types[type.name] = type 

voglio che appena sottoclassi BaseType vedono il metodo della BaseTypegenerateCsCode.

+0

@jamylak No No no no no Voglio solo dire come definire un metodo protetto, so di sottolineatura – Pooya

+0

Perché meno ??? perché? è il mio problema e ho cercato molto e non ho trovato nulla – Pooya

+1

@Pooya: hai la tua risposta: non lo fai in Python. Descrivi il problema più grande e possiamo aiutarti a trovare una soluzione appropriata per Python. –

risposta

55

Python non supporta la protezione dell'accesso come fa C++/Java/C#. Tutto è pubblico. Il motto è: "Siamo tutti adulti qui". Documenta le tue lezioni e insisti affinché i tuoi collaboratori leggano e seguano la documentazione.

La cultura in Python è che i nomi che iniziano con caratteri di sottolineatura significano "non usarli a meno che tu non sappia davvero che dovresti". Potresti scegliere di iniziare i metodi "protetti" con caratteri di sottolineatura. Ma tieni presente che questa è solo una convenzione, non cambia il modo in cui è possibile accedere al metodo.

I nomi che iniziano con caratteri di sottolineatura doppio (__name) vengono storpiati, in modo che le gerarchie di ereditarietà possano essere create senza timore di conflitti di nomi. Alcune persone li usano per metodi "privati", ma, ancora una volta, non cambia il modo in cui è possibile accedere al metodo.

La strategia migliore è quella di abituarsi a un modello in cui tutto il codice in un singolo processo deve essere scritto per andare d'accordo.

+0

sì Conosco _ e __ ma voglio sapere come rendere protetto il mio metodo, esattamente come protetto in java – Pooya

+29

La risposta è molto semplice, ed è stata fornita: Non puoi in Python. –

10

Non è possibile. Python intenzionalmente non supporta il controllo degli accessi. Per convenzione, i metodi che iniziano con un carattere di sottolineatura sono privati ​​e si dovrebbe indicare chiaramente nella documentazione chi deve utilizzare il metodo.

+3

Per convenzione, un carattere di sottolineatura è considerato protetto e due caratteri di sottolineatura sono considerati privati. –

+0

@l__flex__l: i doppi underscore iniziali per gli attributi di istanza invocano il nome mangling con semantica molto specifica. Non è una convenzione, è parte della definizione della lingua. Secondo PEP 8, una sottolineatura principale è un "indicatore di uso interno debole". Non penso ci sia alcuna analogia utile con i modificatori di accesso "protetti" e "privati" del C++. –

+3

Nel PEP 8 consultare la sezione "Progettazione per l'ereditarietà". In particolare il paragrafo che inizia con "Un'altra categoria di attributi sono quelli che fanno parte della" sottoclasse API "(spesso chiamata **" protetta "** in altre lingue)". Per me, quella sezione descrive gli attributi protetti. Anche molti altri credono così [come questo ragazzo] (http://radek.io/2011/07/21/private-protected-and-public-in-python/). So che gli articoli su Internet non sono mai una prova. Ma, abbastanza persone sono d'accordo su questo in modo che per definizione sia una convenzione, no? –

Problemi correlati