1
0
forked from tdwojak/Python2017
Python2017/labs04/Klasy.ipynb
2017-12-14 12:28:39 +01:00

20 KiB
Raw Blame History

Wprowadzenie do Pythona: Klasy

Tomasz Dwojak

3 grudnia 2017

Plan na dziś:

  • klasy,
  • wyjątki.

Python jest językiem obiektowym

  • Wszystko jest obiektem: liczby, napisy, None, funkcje, moduły (biblioteki)...
print((2017).imag)
print(' '.join(['Python', 'da', 'się', 'lubić', '!']))
0
Python da się lubić !

Konstrukcja

class NajprostszaKlasa:
    pass

nasza_klasa = NajprostszaKlasa() # Uwaga na nawiasy na końcu!
print(type(nasza_klasa))

nasza_klasa = NajprostszaKlasa # Uwaga na nawiasy na końcu!
print(type(nasza_klasa()))
<type 'instance'>
<type 'instance'>

(Pseudo) Konstruktor

class Punkt:
    def __init__(self, x, y=0):
        self.x = x
        self.y = y
        
# self jak this w C

punkt = Punkt(2)
print(punkt.x)
print(punkt)
2
<__main__.Punkt instance at 0x00000000049B3CC8>
class Figura:
    def __init__(self, vertexes):
        self.vertexes = vertexes
    
    def liczba_wierzcholkow(self):
        return len(self.vertexes)
    
    #metoda - jedynym argumentem jest self
    #funkcja - 
    
    def dodaj_wierzcholek(self, x):
        self.vertexes.append(x)
#dziedziczenie

class Prostokat(Figura):
    def __init__(self, vertexes):
        super().__init__(vertexes)
        #lub self.vertexes = vertexes
    def czy_jestem_kwadratem(self):
        pass
        
class Figura:
    def __init__(self, vertexes):
        self.vertexes = vertexes
    
    def liczba_wierzcholkow(self):
        return len(self.vertexes)
    
    def __len__(self):
        return self.liczba_wierzcholkow()
    
len(Figura([Punkt(2,3), Punkt(3,4), Punkt(0, 0)]))
o = Figura([Punkt(2,3), Punkt(3,4), Punkt(0, 0)])
len(o)
o.__len__()
o.liczba_wierzcholkow()
3

Dobre praktyki: komentarze

class Punkt(object):
    """Klasa reprezentująca punkt w 2D."""
    def __init__(self, x, y):
        """opis argumentów x i y."""
        self.x = x
        self.y = y
help(Punkt)
Help on class Punkt in module __main__:

class Punkt(__builtin__.object)
 |  Klasa reprezentująca punkt w 2D.
 |  
 |  Methods defined here:
 |  
 |  __init__(self, x, y)
 |      opis argumentów x i y.
 |  
 |  ----------------------------------------------------------------------
 |  Data descriptors defined here:
 |  
 |  __dict__
 |      dictionary for instance variables (if defined)
 |  
 |  __weakref__
 |      list of weak references to the object (if defined)

Enkapsulacja: publiczne czy prywatne?

  • Prywatne zaczynają się od dwóch podkreśleń: __, np. def __policz(self)
  • chronione tylko w konwencji, zaczynają się od '_', np. def _parse(self)
  • publiczne jest wszystko co nie zaczyna się od '_'.
class Parser(object):
    def __parse(self): pass
    def _get(self): pass
parser = Parser()
parser._get()
parser.__parse()
---------------------------------------------------------------------------
AttributeError                            Traceback (most recent call last)
<ipython-input-6-80ee186598d3> in <module>()
      4 parser = Parser()
      5 parser._get()
----> 6 parser.__parse()

AttributeError: 'Parser' object has no attribute '__parse'

Iteratory

class Figura:
    def __init__(self, vertexes):
        self.vertexes = vertexes  
        
    def __iter__(self):
        self.index = -1
        return self
    
    def __next__(self):
        self.index += 1
        if self.index == len(self.vertexes):
            raise StopIteration
        return self.vertexes[self.index]
        
for v in Figura([Punkt(2,3), Punkt(3,4), Punkt(0, 0)]):
    print(v)

TypeErrorTraceback (most recent call last)
<ipython-input-42-c424f51c19dc> in <module>()
     13         return self.vertexes[self.index]
     14 
---> 15 for v in Figura([Punkt(2,3), Punkt(3,4), Punkt(0, 0)]):
     16     print(v)

TypeError: instance has no next() method

Atrybuty i metody statyczne

class Klasa:
    atrybut = 0

klasa = Klasa()
#klasa2 = Klasa
#klasa2.atrybut=1
print(id(Klasa))
klasa2 = Klasa()
print(id(klasa2))
klasa2.atrybut=1

print(Klasa.atrybut)  
#atrybut wspólny dla wszystkich instancji
print(klasa.atrybut)

klasa.temp = []
79384200
48959560
0
0
class Klasa:
    def __init__(self):
        self.t = 0
    def metoda():
        # nie będzie działać self.t = 0
        print("Jestem statyczna!")

Klasa.metoda()

TypeErrorTraceback (most recent call last)
<ipython-input-62-63152cc2cac6> in <module>()
      6         print("Jestem statyczna!")
      7 
----> 8 Klasa.metoda()

TypeError: unbound method metoda() must be called with Klasa instance as first argument (got nothing instead)

Wyjątki

with open("nieistniejący_plik.txt") as plik:
    content = plik.read()

IOErrorTraceback (most recent call last)
<ipython-input-1-1bebecf2f5c5> in <module>()
----> 1 with open("nieistniejący_plik.txt") as plik:
      2     content = plik.read()

IOError: [Errno 2] No such file or directory: 'nieistniej\xc4\x85cy_plik.txt'
from pandas.compat import FileNotFoundError

try:
    with open("nieistniejący_plik.txt") as plik:
        content = plik.read()
except FileNotFoundError:
    contenct = ""
try:
    with open("nieistniejący_plik.txt") as plik:
        content = plik.read()
except FileNotFoundError as e:
    print("Warning {}".format(e))
    contenct = ""
Warning [Errno 2] No such file or directory: 'nieistniej\xc4\x85cy_plik.txt'
try:
    with open("nieistniejący_plik.txt") as plik:
        content = plik.read()
except Exception as e:
    print("Warning {}".format(e))
    contenct = ""
Warning [Errno 2] No such file or directory: 'nieistniej\xc4\x85cy_plik.txt'
try:
    with open("nieistniejący_plik.txt") as plik:
        content = plik.read()
except:
    contenct = ""
class Figura:
    def __init__(self, vertexes):
        if len(vertexes) == 0:
            raise Exception("Empty list of vertexes")
        self.vertexes = vertexes
        
figura = Figura([])

ExceptionTraceback (most recent call last)
<ipython-input-19-0884e4d4e2f2> in <module>()
      5         self.vertexes = vertexes
      6 
----> 7 figura = Figura([])

<ipython-input-19-0884e4d4e2f2> in __init__(self, vertexes)
      2     def __init__(self, vertexes):
      3         if len(vertexes) == 0:
----> 4             raise Exception("Empty list of vertexes")
      5         self.vertexes = vertexes
      6 

Exception: Empty list of vertexes
class MyError(Exception):
    def __init__(self, text):
        self.text = text
    def __str__(self):
        return self.text
raise MyError("Coś poszło nie tak!")

MyErrorTraceback (most recent call last)
<ipython-input-34-99f654d8334c> in <module>()
----> 1 raise MyError("Coś poszło nie tak!")

MyError: Coś poszło nie tak!