Kirjautuminen

Haku

Tehtävät

Keskustelu: Ohjelmointikysymykset: Python ja sisäkkäiset moduulit

Cartter [04.01.2013 17:15:22]

#

A/
  __init__.py
  A.py
A/B/
    __init.py
    B.py
A/B/C/
      __init__.py
      C.py

Minkälaiset importit mun tarvitsee kirjoittaa yllä oleviin moduuleihin, kun haluan käyttää B.py-moduulia C.py moduulissa?

The Alchemist [04.01.2013 20:43:55]

#

Hakemistorakenteesi lienee väärin. Hakemistoihin laitetaan __init__.py-filu silloin, kun haluat käyttää hakemistoa pakettina. Tällöin et todennäköisesti aio lisätä pakettiin sen itsensä nimistä skriptitiedostoa vaan hakemiston nimen ilmaisemaan ryhmään kuuluvia moduuleita.

Nykyisellään importtisi olisivat tällaisia:

*** B.py
import C.C
# tai
from C import C

Olisi siis järkevämpää joko laittaa kaikki kolme skriptiä samaan hakemistoon tai sitten jakaa A.py, B.py ja C.py uusiksi skripteiksi.

Cartter [04.01.2013 23:05:57]

#

Eka esimerkki oli ehkä huono. Seuraavassa kuvaavampi esimerkki. Kyse on siis sisäkkäisistä moduuleista kuten otsikkoon on korjattu :)

Ajoneuvo/Ajoneuvo.py <-- Abstrakti Ajoneuvo-luokka
Ajoneuvo/Auto/Auto.py <-- Abstrakti Auto-luokka, perii abstraktin Ajoneuvo-luokan
Ajoneuvo/Auto/Farmari/Farmari.py <-- Abstrakti Farmari-luokka, perii abstraktin Auto-luokan
Ajoneuvo/Auto/Farmari/FarmariXXX.py <-- Konkreettinen FarmariXXX-luokka, perii abstraktin Farmari-luokan

1. Onko tarkoitus laittaa __init__.py-tiedosto jokaiseen Ajoneuvo-kansion alikansioon(Auto, Laiva, Lentokone, ...), jotta ne voidaan ylipäätään importata?
2. Kuinka kirjoitan FarmariXXX-luokan importin


EDIT. Nonni... pidin Eclipse+PyDev-projektin juurikansiota tavallisena kansiona omassa projektissa :D Ongelma hoidettu!

Metabolix [04.01.2013 23:54:38]

#

Kuten Pythonin moduuliohjeessa varsin selvästi kerrotaan, voit viitata paketin ylempiin moduuleihin pisteiden avulla. Yksi piste tarkoittaa nykyistä tasoa, kaksi pistettä ylempää, kolme pistettä sitä ylempää.

# Ajoneuvo/Auto/Farmari/FarmariXXX.py
from . import Farmari
class FarmariXXX(Farmari.Farmari):
	# ...
# Ajoneuvo/Auto/Farmari/Farmari.py
from .. import Auto
# Tai: from ..Auto import Auto
class Farmari(Auto.Auto):
	# ...

Kuten huomaat, tässä päädyttiin kuitenkin hassuun tilanteeseen, jossa esimerkiksi Auto-luokka kuuluu Auto-moduuliin ja koodiin pitää kirjoittaa Auto.Auto (tai import-riviin from Auto import Auto). Juuri tätä The Alchemist yritti äsken jo selittää. Jokin muu rakenne voisi siis olla järkevä.

The Alchemist [05.01.2013 15:57:09]

#

Cartter kirjoitti:

1. Onko tarkoitus laittaa __init__.py-tiedosto jokaiseen Ajoneuvo-kansion alikansioon(Auto, Laiva, Lentokone, ...), jotta ne voidaan ylipäätään importata?

Jos haluat ryhmitellä koodiasi paketteihin niin joudut tekemään näin. Mutta mikäli tarkoituksesi on vain vähentää yhdessä hakemistossa olevien tiedostojen määrää, niin voit lisätä alihakemistot polkuun, jolloin voit importata niistä moduuleita kuin ne sijaitsisivat kaikki samassa hakemistossa.

import sys

sys.path.append('sub_folder_1')
sys.path.append('sub_folder_1/sub')

# lataa sub_folder_1/foo.py
import foo

# lataa sub_folder_2/sub/bar.py
import bar

Vastaus

Aihe on jo aika vanha, joten et voi enää vastata siihen.

Tietoa sivustosta