Quando importare i nomi nello spazio dei nomi globale? (usando x: y, da x import y ecc.)

8

Ho iniziato a programmare in varie lingue per circa 10 anni. E non ho ancora capito quando è una buona idea importare qualcosa nello spazio dei nomi globale ( using x::y in C ++, from x import y in Python ecc.), Quindi non lo faccio quasi mai.

Sembra quasi sempre una cattiva idea per me, se non altro perché limita il set di nomi di variabili che posso usare. Ad esempio: Dove utilizzare using namespace std; o using std::string; in C ++, non potrei più usare string come nome di variabile, cosa che a volte faccio (ad esempio per le funzioni di utilità stringa).

Ma mi chiedo: ci sono alcune situazioni in cui l'importazione di un nome nello spazio dei nomi globale ha davvero senso? Qualunque regola empirica?

    
posta futlib 10.02.2013 - 18:44
fonte

4 risposte

11

In C ++, è generalmente disapprovato, specialmente using namespace std . Quel std namespace ha così tanti nomi, molti dei quali sono algoritmi molto generici, puoi ottenere delle sorprese estremamente spiacevoli quando using namespace std . Qualcosa come using std::cout; non è poi così male. Ma mai, mai, using nulla nello spazio dei nomi globale in un file di intestazione. Questo è un attacco di squadra di fuoco.

    
risposta data 10.02.2013 - 18:48
fonte
4

Dovresti farlo quando semplifica il tuo codice. Non dovresti farlo quando causerebbe conflitti di denominazione, o quando potrebbe essere successivamente inserito in ambiti dove causerebbe conflitti di denominazione, come un file di intestazione.

Alcune persone pensano che dovrebbe essere raro. Penso che (al di fuori dei file di intestazione) non utilizzarlo dovrebbe essere raro, perché il prefisso dello spazio dei nomi in genere non aggiunge alcuna informazione utile, come usare il nome completo di qualcuno ogni volta che li indirizzi.

Lasciami dire così. Quando vedi string come nome di classe, pensi automaticamente std::string o mycustom::string ? È come il vecchio adagio. Quando senti il suono degli zoccoli, pensi che i cavalli, non le zebre. In altre parole, using namespace std non è quasi mai un grosso problema. using namespace mycustom di solito non è un grosso problema, a meno che non contenga un conflitto con std , nel qual caso il tuo spazio dei nomi personalizzato è quello per cui vuoi sempre richiedere il prefisso.

    
risposta data 11.02.2013 - 00:50
fonte
3

Lavorando in Python, utilizzo costantemente da x import y (as z), per avere nomi chiari e concisi per fare riferimento alle importazioni.

Dalle importazioni hanno un valore inestimabile in una base di codice con una gerarchia di spazio dei nomi profonda. Questo è particolarmente vero quando lo standard di stile per il codebase è PEP 8 , che limita la lunghezza della linea a meno di 80 caratteri.

Ad esempio, prendi in considerazione:

import foo

foo.bar.baz.baf.perform_task(foo.bar.baz.quux.SOME_CONSTANT, foo.bar.alice.bob.preferred_hash_function, '42', foo.bar.magic_numbers.MY_SALT)

Che potrebbe invece essere scritto:

from foo.bar import baf
from foo.bar.alice import bob
from foo.bar.baz.quux import SOME_CONSTANT
from foo.bar.magic_numbers import MY_SALT

baf.perform_task(SOME_CONSTANT, bob.preferred_hash_function, '42', MY_SALT)

Poiché gli identificatori Python sono sensibili al maiuscolo e al minuscolo , non eseguiremo dei nomi indipendentemente da quanti importiamo.

Se vogliamo usare lo stesso nome nel nostro modulo come uno dei moduli che vogliamo importare, possiamo usare un alias per l'importazione:

from foo.bar.alice import bob as carol

def bob(x, y):
    print "running bob function"
    return carol(x, y, 42)
    
risposta data 13.02.2013 - 00:05
fonte
0

Dipende dal programmatore quando usarlo. IMHO è meglio non usarli affatto, specialmente nei file di intestazione. Ma ci sono diversi casi in cui lo uso

  • Quando voglio introdurre qualcosa in un altro spazio dei nomi, ad es.

    namespace cg
    {
      namespace details
      {
        //lots of stuff
        void some_cool_foo()
        {
          //uses a lot stuff from details, here because I don't want prefix everything with details::
        }
      }
      using details::some_cool_foo;
    }
    
  • Per abilitare ADL per alcuni algoritmi da un altro spazio dei nomi

    namespace n1
    {
    //some general foo
    }
    namespace n2
    {
      using n1::foo;
    //some struct
    }
    namespace n3
    {
      using n1::foo;
    //some struct
    }
    

Se non desidero scrivere nomi lunghi di spazi dei nomi in .cpp, posso sempre fare alias

namespace bl = boost::lambda;
namespace fs = boost::filesystem;
    
risposta data 02.03.2013 - 12:17
fonte

Leggi altre domande sui tag