Olen aina käyttänyt tätä menetelmää:

from sys import argv 

ja käytä argv vain argv kanssa. Tämän käyttö on kuitenkin tapana:

import sys 

ja argv: n käyttämisestä sys.argv

Toinen menetelmä tekee koodista itsedokumentoitavan ja pidän (todella) kiinni siitä. Mutta mieluummin ensimmäinen menetelmä on se, että se on nopea, koska tuomme vain tarvittavan toiminnon eikä koko moduulia (joka sisältää enemmän hyödyttömiä toimintoja, jotka python tuhlaa aikaa niiden tuomiseen). Huomaa, että tarvitsen vain argv: n ja kaikki muut sys: n toiminnot ovat minulle hyödyttömiä.

Joten kysymykseni ovat. Tekeekö ensimmäinen menetelmä todella käsikirjoituksen nopeasti? Mikä menetelmä on suosituin? Miksi?

Kommentit

vastaus

Moduulin tuominen ei tuhlaa mitään ; moduuli on aina täysin tuotu (sys.modules -kartoitukseen), joten käytä import sys tai from sys import argv ei tee kertoimia.

Ainoa ero näiden kahden lauseen välillä on se, mikä nimi on sidottu; import sys sitoo nimen sys moduuliin (joten sys -> sys.modules["sys"]), kun taas from sys import argv sitoutuu eri nimi, argv, joka osoittaa suoraan moduulin sisällä olevaan määritteeseen (joten argv -> sys.modules["sys"].argv). Loput e sys -moduuli on edelleen olemassa riippumatta siitä, käytätkö muuta moduulista vai ei.

Näiden kahden lähestymistavan välillä ei myöskään ole eroa. Kyllä, sys.argv on etsittävä kahta asiaa; sen on etsittävä sys maailmanlaajuisesta nimitilastasi (etsi moduulin) ja sitten määritteen argv. Ja kyllä, käyttämällä from sys import argv -ohjelmaa voit ohittaa määritteen haun, koska sinulla on jo suora viittaus määritteeseen. Mutta import -lausekkeen on silti tehtävä tämä työ, se etsii samaa määritettä tuotaessa, ja sinun tarvitsee vain käyttää argv kerran . Jos joudut käyttämään argv tuhansia kertoja silmukassa, se voisi ehkä vaikuttaa, mutta tässä erityisessä tapauksessa se ei todellakaan ole .

Tällöin valinnan tulisi perustua koodaustyyliin .

isossa moduulissa , Käytän varmasti import sys; koodidokumentaatiolla on merkitystä, ja sys.argv -toiminnon käyttäminen jonnekin isossa moduulissa tekee paljon selvemmäksi, mihin tarkoitat kuin vain argv koskaan.

Jos ainoa paikka, jota käytät argv, on "__main__" -lohkossa soittaaksesi main() -funktiota, käytä kaikin keinoin from sys import argv, jos sinusta tuntuu onnellisemmalta:

if __name__ == "__main__": from sys import argv main(argv) 

I ”d käytän silti siellä itse import sys. Kaikki asiat ovat tasa-arvoisia (ja ne ovat täsmälleen suorituskyvyn suhteen ja merkkien lukumäärä, joita käytetään sen kirjoittamiseen) , se on minulle vain helpompaa silmissä.

Jos tuot jotain muuta kokonaan, ehkä suorituskyky tulee esiin. Mutta vain jos käytät tiettyä nimeä moduuli monta kertaa , esimerkiksi kriittisessä silmukassa. Mutta sitten paikallisen nimen luominen (funktion sisällä) on yhä nopeampaa:

 import somemodule def somefunction(): localname = somemodule.somefunctionorother while test: # huge, critical loop foo = localname(bar) 

Kommentit

  • On myös tilanne, jossa sinulla on paketteja, joissa on alipaketteja tai moduuleja, jotka paljastavat yhden näistä alipaketeista / moduuleista ylemmän tason paketissa. Käyttämällä from...import voit tehdä package.attribute eikä package.subpackage_or_module.attribute, mikä voi olla hyödyllistä, jos sinulla on loogisia tai käsitteellisiä ryhmitelmiä paketissa, mutta haluat tehdä asiat hieman mukavammiksi pakettisi käyttäjille. (numpy tekee jotain tällaista, uskon.)
  • Djangossa sinulla on paljon paikkoja, joissa esimerkiksi from django.core.management.base import BaseCommand ovat parempia, ja mikä tahansa muu (etenkin import django) johtaisi lukukoodiin. Joten vaikka pidän tästä vastauksesta, mielestäni on joitain kirjastoja (ja erityisesti joitain kehyksiä), joissa yleissopimuksen on tarkoitus rikkoa paljasta tuontia.Kuten aina, käytä arviointiasi siitä, mikä on parasta tietyssä tilanteessa. Mutta erehdy eksplisiittisen suhteen (toisin sanoen olen samaa mieltä suurimmaksi osaksi).
  • @JAB: voit silti käyttää pakettia import ... as eri nimi: import package.subpackage_or_module as shortname. from parent import sub tekee olennaisesti saman.
  • so wether you use import sys or from sys import argv makes no odds näyttää siltä, ettei IDLE: ssä ole kyse. Pelkkä moduulin tuominen ei tuo sen toimintoja, ja voin kutsua sitä IDLE-kuoressa vain < -moduulilla >. < function > nimi
  • @Suncatcher: lue vastaukseni kokonaan. Lainailmaasi lause puhuu siitä, kuinka paljon tuodaan, ei siitä, mikä nimi on sidottu. Se ’ on katettu muualla vastauksessa.

Vastaa

import module -sivun from module import function sijaan kannattaa käyttää kahta syytä.

Ensimmäinen on nimitila. Funktion tuominen globaaliin nimiavaruuteen vaarantaa nimien törmäykset.

Toinen ei ole merkityksellinen vakiomoduuleille, mutta merkittävä sinulle omistaa moduuleja, etenkin kehityksen aikana. Se on vaihtoehto reload() moduuli. Harkitse tätä:

from module import func ... reload(module) # func still points to the old code 

Toisaalta

import module ... reload(module) # module.func points to the new code 

Mitä tulee nopeuteen .. .

tuomme vain tarvittavan toiminnon koko moduulin tuonnin sijaan (joka sisältää enemmän hyödyttömiä toimintoja, joiden python tuhlaa aikaa niiden tuomiseen)

Onko tuot moduulin vai funktion moduulista, Python jäsentää koko moduulin. Kummassakin tapauksessa moduuli tuodaan. ”Funktion tuominen” ei ole muuta kuin funktion sitominen nimeen. Itse asiassa import module on vähemmän tulkkityötä kuin from module import func.

Kommentit

  • reload () oli sisäänrakennettu Python 2: ssa; näin ei ole enää Python 3: ssa.
  • Luulin, että myös pyöreiden tuontiriippuvuuksien kanssa oli vaikutuksia?

Vastaa

Käytän from import s aina, kun se parantaa luettavuutta. Esimerkiksi, pidän mieluummin (puolipisteillä vain säästetään tilaa tässä):

from collections import defaultdict from foomodule import FooBar, FooBaz from twisted.internet.protocol import Factory defaultdict(); FooBar(); FooBaz(); Factory() 

eikä:

import collections import foomodule import twisted.internet.protocol collections.defaultdict(); foomodule.FooBar(); foomodule.FooBaz() twisted.internet.protocol.Factory() 

Jälkimmäistä on minulle vaikeampaa lukea (ja kirjoittaa), koska se sisältää niin paljon turhaa tietoa. Lisäksi on hyödyllistä tietää etukäteen, mitä moduulin osia käytän.

Pidän parempana tavallisista import s, jos käytän paljon lyhyitä nimiä moduulista:

import sys sys.argv; sys.stderr; sys.exit() 

Tai jos nimi on niin yleinen, että sillä ei ole merkitystä nimiavaruutensa ulkopuolella:

import json json.loads(foo) from json import loads loads(foo) # potentially confusing 

Kommentit

  • Tämä on suosikkivastaukseni. ’ eksplisiittinen on parempi kuin implisiittinen. ’ on joskus ristiriidassa luettavuuden, yksinkertaisuuden ja kuivuuden kanssa. Varsinkin kun käytetään kehystä, kuten Django.

Vastaa

Mielestäni käyttämällä säännöllistä import parantaa luettavuutta. Tarkastellessani Python-koodia haluan nähdä, mistä annettu funktio tai luokka on peräisin siitä, mihin sitä käytetään. Se säästää minua vierittämästä moduulin yläosaan saadakseni nämä tiedot.

Pitkien moduulien nimien osalta käytän vain avainsanaa as ja annan heille lyhyen aliakset:

import collections as col import foomodule as foo import twisted.internet.protocol as twip my_dict = col.defaultdict() foo.FooBar() twip_fac = twip.Factory() 

Poikkeuksena käytän aina merkintää from module import something, kun käsittelen __future__ -moduuli. Et voi tehdä sitä toisella tavalla, kun haluat kaikkien merkkijonojen olevan oletusarvoisesti unicode Python 2: ssa, esim.

from __future__ import unicode_literals from __future__ import print_function 

Kommentit

  • Amen! ” tuonti nimellä ” on voittoyhdistelmä 🙂

Vastaa

Vaikka import sys ja from sys import agrv molemmat tuovat koko sys -moduulin, jälkimmäinen käyttää nimisidontaa, joten vain koodin argv moduuliin pääsee muulle koodille.

Joillekin ihmisille tämä olisi ensisijainen tyyli, koska se tekee vain nimenomaisesti ilmoittamasi toiminnon saataville.

Se kuitenkin aiheuttaa mahdollisia ristiriitoja. Entä jos sinulla olisi toinen moduuli nimeltä argv? Huomaa, että voit myös tuoda nimenomaisesti funktion ja nimetä sen uudelleen nimellä from sys import argv as sys_argv, käytäntö, joka täyttää nimenomaisen tuonnin ja on vähemmän todennäköistä, että hän antaa nimitilaa törmäykset.

Kommentit

  • Joten miten if sys_argv: on parempi kuin if sys.argv:? Tiedän mitä toinen lausunto tarkoittaa, minulla ei ole aavistustakaan mitä ensimmäinen muoto tarkoittaa ilman paluuta omituiseen tuontiin.

vastaus

Esitin äskettäin tämän kysymyksen itselleni. Ajoitin eri menetelmät.

pyytää kirjastoa

def r(): import requests return "hello" timeit r() # output: 1000000 loops, best of 3: 1.55 µs per loop def rg(): from requests import get return "hello" timeit rg() # output: 100000 loops, best of 3: 2.53 µs per loop 

beautifulsoup-kirjasto

def bs(): import bs4 return "hello" timeit bs() # output: 1000000 loops, best of 3: 1.53 µs per loop def be(): from bs4 import BeautifulSoup return "hello" timeit be() # output: 100000 loops, best of 3: 2.59 µs per loop 

json-kirjasto

def js(): import json return "hello" timeit js() # output: 1000000 loops, best of 3: 1.53 µs per loop def jl(): from json import loads return "hello" timeit jl() # output: 100000 loops, best of 3: 2.56 µs per loop 

sys-kirjasto

def s(): import sys return "hello" timeit s() # output: 1000000 loops, best of 3: 1.55 µs per loop def ar(): from sys import argv return "hello" timeit ar() # output: 100000 loops, best of 3: 2.87 µs per loop 

Näyttää siltä minulle, että suorituskyvyssä on pieni ero.

Kommentit

  • Olet lisäämässä attribuuttihaun. Jos haluat verrata import module -palvelua from module import name -palveluun oikein, lisää kyseisen nimen haku hakemistoon import module tapaus. Esimerkiksi. lisää rivi sys.argv ar -testiin jne. Tällöin ero on edelleen, koska tehty työ on hieman eri, koska syntyy erilainen tavukoodi ja suoritetaan erilaisia kooditietä.
  • Huomaa, että käsittelen tätä eroa suoraan vastauksessani; import sys -toiminnon ja sitten sys.argv -tuotteen käyttäminen silmukassa tuhansien aikojen välillä eroaa välillä from sys import argv käyttämällä vain argv. Mutta et ’ t. Asioita varten, joita teet vain kerran moduulin globaalilla tasolla, sinun pitäisi todella optimoida luettavuus, älä mikroskooppisia eroja ajoituksissa.
  • Ahhhh! Ja ajattelin olevani jossakin asiassa! 🙂 Minä vain löysin vastauksesi. Näyttää siltä, että hyppäsin aseen sen päälle. Tuntuu hyvältä nöyryytetyksi.

Vastaa

Julkaistun koodin fragmenttien tarkasteleminen, kokonaisten moduulien tuonti ja div id = ”d4f287ac19”>

on melko vakio, ainakin vakiomoduuleille. Ainoa poikkeus näyttää olevandatetime

from datetime import datetime, timedelta 

joten voit sanoa datetime.now() eikä datetime.datetime.now().

Jos olet huolissasi suorituskyvystä, voit aina sanoa (esimerkiksi)

argv = sys.argv 

ja tee sitten suorituskyvyn kannalta kriittinen koodi, koska moduulin haku on jo tehty. Vaikka tämä toimii toimintojen / menetelmien kanssa, useimmat IDE: t sekoittuvat ja eivät (esimerkiksi) näytä funktion lähdelinkkiä / allekirjoitusta, kun se on määritetty muuttujalle.

Vastaa

Haluan vain lisätä, että jos teet jotain

from math import sin 

(tai mikä tahansa muu sisäänrakennettu kirjasto, kuten sys tai posix), sitten sin sisällytetään moduulin dokumentaatioon (ts. kun teet >>> help(mymodule) tai $ pydoc3 mymodule. Välttääksesi tämän, tuoda käyttämällä:

import math from math import sin as _sin 

PS: sisäänrakennettu kirjasto on C-koodista koottu ja Pythonin mukana oleva kirjasto. argparse, os ja io eivät ole sisäänrakennettuja paketteja

Vastaa

Sähköpostiosoitettasi ei julkaista. Pakolliset kentät on merkitty *