Skip to content
Snippets Groups Projects
Commit 0e656988 authored by Christof Kaufmann's avatar Christof Kaufmann
Browse files

Notebooks from applied-cs/data-science@13f72230

parent db0b9b67
Branches
No related tags found
No related merge requests found
Showing
with 1716 additions and 0 deletions
%% Cell type:markdown id: tags:
# Code zu Folien
Dieses Skript bzw. Jupyter-Notebook enthält den Code, der auch auf den Folien "Python Grundlagen" enthalten ist. Zum Vorbereiten, Mitmachen oder Nacharbeiten.
%% Cell type:code id: tags:
```
a = 10 # Datentypen werden implizit bestimmt
print(type(a)) # type() gibt den Typ aus
A = 20 / 2 # Groß- / Kleinschreibung wird unterschieden
print(type(A))
print(a ** 2, 7 // 2) # ∗∗ ist der Potenzoperator, // steht für floor Division
```
%% Cell type:code id: tags:
```
print(A == 10) # Vergleichsoperatoren: <, <=, >, >=, ==, !=
print(A == 10 and a == 10) # Verknüpfungsoperatoren: not, and, or
print((A == 10) + 1) # implizite Konvertierung: False → 0, True → 1
print(isinstance(A, (int, float))) # ist A vom Typ int oder float? wichtig um Überladung nachbilden zu können
```
%% Cell type:code id: tags:
```
a = 'Hello'
b = "world"
print(a, b) # print gibt mehrere Argumente mit Leerzeichen getrennt aus
c = """Hello,
you are my "world"!"""
print(c)
c = 'Hello,\nyou are my "world"!'
print(c)
```
%% Cell type:code id: tags:
```
a = 'Hello,' + ' world' # Leerzeichen zwischen Komma und world im String
print(a)
print(a + str(123))
print(len('vier'))
print(a.replace('ello', 'i'))
print(a.lower())
print(a.endswith('.png'))
```
%% Cell type:code id: tags:
```
b = 'Beispiel'
print(b[7], b[2], b[6], b[3])
f = 'logo.pdf'
print(f[-3] + f[-2] + f[-1])
# f[0] = 'L' # TypeError
```
%% Cell type:code id: tags:
```
f = 'logo.pdf'
print(f[0:4])
print(f[:-4], f[-3:])
print(f[0:6:2])
print(f[::2])
```
%% Cell type:code id: tags:
```
path = '../images/logo.pdf'
file_pos = path.rfind('/') + 1
print(file_pos)
dir = path[:file_pos]
file = path[file_pos:]
print('dir:', dir, ' file:', file)
```
%% Cell type:code id: tags:
```
print(8 + 4)
print(8, 4)
print(8); print(4)
print(8, 4, 2, sep=' > ', end=' (richtige Aussage)\n\n')
```
%% Cell type:code id: tags:
```
print('Hi {}!'.format(5)) # formatierte(r) String / Ausgabe
print('{0} {1} {0}!'.format('First', 'Things')) # {n} referenziert Parameter n
print('named: {test}!'.format(test=42)) # {varname} definiert Namen
print('significant digits: {:.2}'.format(20/3)) # {...:.2} 2 signifikante Stellen
print('Fill: {:04}'.format(3)) # {...:0s} reserviert s Zeichen und füllt mit 0
print('Fixed point: {:.2f}'.format(3)) # {...:f} gibt Zahl als fixed point aus
```
%% Cell type:code id: tags:
```
print(f'Explicit: {3:.2f}') # f'\{var:...\}' ersetzt '{:...}'.format(var)
print('old style: %d %.2f' % (2, 3)) # formatierte(r) String / Ausgabe
print('bad style: %d %d' % (2.3, 3.8)) # Typspezifizierer könnten falsch sein! ⚡
ip = '127.0.0.1'
port = 8888
# port = '8888' # ergibt Fehler beim alten Formatierungsstil.
server = ip + ':%d' % port # Wurde port vielleicht als String gegeben? ⚡
print(server)
server = f'{ip}:{port}' # Besser! Funktioniert mit strings und ints 👍
print(server)
```
%% Cell type:code id: tags:
```
if A > 10:
print('too big')
elif A > 5: # es kann mehrere elif-Zweige geben
print('correct')
else:
print('too small')
print()
if 's' in 'Hellas':
print('It is')
```
%% Cell type:code id: tags:
```
for c in 'bla':
print('Buchstabe:', c)
print()
for i in range(3):
print('It:', i)
print()
for i, c in enumerate('bla'):
print('It:', i, 'Buchstabe:', c)
print()
for c, s in zip('ABC', 'abc'):
print(c + s)
```
%% Cell type:code id: tags:
```
for c in 'AKIS':
if c == 'I':
break
print(c)
print()
for c in 'AKIS':
if c == 'I':
continue
print(c)
print()
while True:
prompt = input('> ')
if prompt == 'exit':
break
print(prompt)
```
%% Cell type:code id: tags:
```
def greet(name):
print('Hello', name)
greet('and goodbye!') # Ausgabe: Hello and goodbye!
def greet(name='my sunshine!'):
print('Hello', name)
greet() # Ausgabe: Hello my sunshine!
greet('you') # Ausgabe: Hello you
```
%% Cell type:code id: tags:
```
def f(x, y):
return x**2 - y**2
print(f(1, 2))
print(f(y=2, x=1)) # Reihenfolge ist egal
def f(x=0, y=0):
return x**2 - y**2
print(f(y=2)) # x=0, y=2
```
%% Cell type:code id: tags:
```
import math
def pq_formel(p, q):
x1 = -p / 2 + math.sqrt(p**2 / 4 - q)
x2 = -p / 2 - math.sqrt(p**2 / 4 - q)
return x1, x2
lsg1, lsg2 = pq_formel(2, 0) # Ausgabe:
print('Lösungen:') # Lösungen:
print('x1 =', lsg1) # x1 = 0.0
print('x2 =', lsg2) # x2 = -2.0
```
%% Cell type:code id: tags:
```
liste = [1, 'text', 1/3] # Listenelemente können verschiede Typen haben
liste[0] = 2 # Listen sind veränderbar
liste.append(42) # Listen sind erweiterbar
print(liste)
liste = ['tag', 'monat', 'jahr']
print(liste.index('monat')) # Stelle bzw. Index des Elements 'monat'
liste = [1, 2, 3] * 2 # Ergibt: liste = [1, 2, 3, 1, 2, 3]
print(liste)
```
%% Cell type:code id: tags:
```
t = (3, 'text') # Tupel-Elemente können auch verschiedene Typen haben
print(t[1]) # Lesen geht
# t[1] = 5 # Schreiben nicht (TypeError)
print((3, 4) + (6, 8)) # Ergibt: (3, 4, 6, 8)
c, d = 5, 7 # c ist 5 und d ist 7 (``unpacking''), 5, 7 ist hier ein Tupel
print(c, d)
```
%% Cell type:code id: tags:
```
s = {11, 7, 3, 13, 2, 6} # #*set* wird definiert mit #*\{...\}*
print(s)
print(s & set(range(4,10))) # Schnittmenge
print(s | set(range(4,10))) # Vereinigungsmenge
print(s - set(range(4,10))) # Differenzmenge
print(s ^ set(range(4,10))) # sym. Differenzmenge (XOR)
```
%% Cell type:code id: tags:
```
tele = {'alice': 213, 'bob': 558} # Dictionary: Zuordnung von Keys zu Values
print(tele['bob'])
tele['charlie'] = 666 # Einträge können hinzugefügt oder verändert werden
print(tele)
d = {42: [1, 2, 3], 2.4: 31, 'valid': True}
print(d) # Reihenfolge bleibt erhalten
```
%% Cell type:code id: tags:
```
for name in tele.keys():
print(name)
print()
for nummer in tele.values():
print(nummer)
print()
for name, nummer in tele.items():
print(name, ': ', nummer, sep='')
print()
```
%% Cell type:code id: tags:
```
squares = [i ** 2 for i in range(-4, 5)]
print(squares)
squares = []
for i in range(-4, 5):
squares.append(i ** 2)
print(squares)
squares = [i ** 2 for i in range(-4, 5) if i % 2 == 0]
print(squares)
squares = []
for i in range(-4, 5):
if i % 2 == 0:
squares.append(i ** 2)
print(squares)
unique_squares = {i ** 2 for i in range(-4, 5) if i % 2 == 0}
print(unique_squares)
```
%% Cell type:code id: tags:
```
print({word: len(word) for word in ('hey', 'world')})
names = ['Alice', 'Bob', 'Charlie', 'David']
numbers = [333, 558, 666, 696]
tele = {name: no for name, no in zip(names, numbers)}
print(tele)
backward_search = {no: name for name, no in tele.items()}
print(backward_search[666])
```
# %% [markdown]
# # Code zu Folien
#
# Dieses Skript bzw. Jupyter-Notebook enthält den Code, der auch auf den Folien "Python Grundlagen" enthalten ist. Zum Vorbereiten, Mitmachen oder Nacharbeiten.
# %% Variablen
a = 10 # Datentypen werden implizit bestimmt
print(type(a)) # type() gibt den Typ aus
A = 20 / 2 # Groß- / Kleinschreibung wird unterschieden
print(type(A))
print(a ** 2, 7 // 2) # ∗∗ ist der Potenzoperator, // steht für floor Division
# %% Boolesche Operationen
print(A == 10) # Vergleichsoperatoren: <, <=, >, >=, ==, !=
print(A == 10 and a == 10) # Verknüpfungsoperatoren: not, and, or
print((A == 10) + 1) # implizite Konvertierung: False → 0, True → 1
print(isinstance(A, (int, float))) # ist A vom Typ int oder float? wichtig um Überladung nachbilden zu können
# %% Strings erstellen
a = 'Hello'
b = "world"
print(a, b) # print gibt mehrere Argumente mit Leerzeichen getrennt aus
c = """Hello,
you are my "world"!"""
print(c)
c = 'Hello,\nyou are my "world"!'
print(c)
# %% Stringkonkatenation und Methoden
a = 'Hello,' + ' world' # Leerzeichen zwischen Komma und world im String
print(a)
print(a + str(123))
print(len('vier'))
print(a.replace('ello', 'i'))
print(a.lower())
print(a.endswith('.png'))
# %% Indizierung von Strings
b = 'Beispiel'
print(b[7], b[2], b[6], b[3])
f = 'logo.pdf'
print(f[-3] + f[-2] + f[-1])
# f[0] = 'L' # TypeError
# %% Slicing von Strings
f = 'logo.pdf'
print(f[0:4])
print(f[:-4], f[-3:])
print(f[0:6:2])
print(f[::2])
# %% Beispiel für Slicing
path = '../images/logo.pdf'
file_pos = path.rfind('/') + 1
print(file_pos)
dir = path[:file_pos]
file = path[file_pos:]
print('dir:', dir, ' file:', file)
# %% Ausgabe mit der print-Funktion
print(8 + 4)
print(8, 4)
print(8); print(4)
print(8, 4, 2, sep=' > ', end=' (richtige Aussage)\n\n')
# %% Formatierung
print('Hi {}!'.format(5)) # formatierte(r) String / Ausgabe
print('{0} {1} {0}!'.format('First', 'Things')) # {n} referenziert Parameter n
print('named: {test}!'.format(test=42)) # {varname} definiert Namen
print('significant digits: {:.2}'.format(20/3)) # {...:.2} 2 signifikante Stellen
print('Fill: {:04}'.format(3)) # {...:0s} reserviert s Zeichen und füllt mit 0
print('Fixed point: {:.2f}'.format(3)) # {...:f} gibt Zahl als fixed point aus
# %% f-Strings und alter Formatierungsstil
print(f'Explicit: {3:.2f}') # f'\{var:...\}' ersetzt '{:...}'.format(var)
print('old style: %d %.2f' % (2, 3)) # formatierte(r) String / Ausgabe
print('bad style: %d %d' % (2.3, 3.8)) # Typspezifizierer könnten falsch sein! ⚡
ip = '127.0.0.1'
port = 8888
# port = '8888' # ergibt Fehler beim alten Formatierungsstil.
server = ip + ':%d' % port # Wurde port vielleicht als String gegeben? ⚡
print(server)
server = f'{ip}:{port}' # Besser! Funktioniert mit strings und ints 👍
print(server)
# %% Verzweigung
if A > 10:
print('too big')
elif A > 5: # es kann mehrere elif-Zweige geben
print('correct')
else:
print('too small')
print()
if 's' in 'Hellas':
print('It is')
# %% for-Schleifen
for c in 'bla':
print('Buchstabe:', c)
print()
for i in range(3):
print('It:', i)
print()
for i, c in enumerate('bla'):
print('It:', i, 'Buchstabe:', c)
print()
for c, s in zip('ABC', 'abc'):
print(c + s)
# %% break und continue und while-Schleifen
for c in 'AKIS':
if c == 'I':
break
print(c)
print()
for c in 'AKIS':
if c == 'I':
continue
print(c)
print()
while True:
prompt = input('> ')
if prompt == 'exit':
break
print(prompt)
# %% Funktionen definieren und aufrufen
def greet(name):
print('Hello', name)
greet('and goodbye!') # Ausgabe: Hello and goodbye!
def greet(name='my sunshine!'):
print('Hello', name)
greet() # Ausgabe: Hello my sunshine!
greet('you') # Ausgabe: Hello you
# %% Rückgabewerte und benannte Argumente
def f(x, y):
return x**2 - y**2
print(f(1, 2))
print(f(y=2, x=1)) # Reihenfolge ist egal
def f(x=0, y=0):
return x**2 - y**2
print(f(y=2)) # x=0, y=2
# %% Mehrere Rückgabewerte
import math
def pq_formel(p, q):
x1 = -p / 2 + math.sqrt(p**2 / 4 - q)
x2 = -p / 2 - math.sqrt(p**2 / 4 - q)
return x1, x2
lsg1, lsg2 = pq_formel(2, 0) # Ausgabe:
print('Lösungen:') # Lösungen:
print('x1 =', lsg1) # x1 = 0.0
print('x2 =', lsg2) # x2 = -2.0
# %% Listen
liste = [1, 'text', 1/3] # Listenelemente können verschiede Typen haben
liste[0] = 2 # Listen sind veränderbar
liste.append(42) # Listen sind erweiterbar
print(liste)
liste = ['tag', 'monat', 'jahr']
print(liste.index('monat')) # Stelle bzw. Index des Elements 'monat'
liste = [1, 2, 3] * 2 # Ergibt: liste = [1, 2, 3, 1, 2, 3]
print(liste)
# %% Tupel
t = (3, 'text') # Tupel-Elemente können auch verschiedene Typen haben
print(t[1]) # Lesen geht
# t[1] = 5 # Schreiben nicht (TypeError)
print((3, 4) + (6, 8)) # Ergibt: (3, 4, 6, 8)
c, d = 5, 7 # c ist 5 und d ist 7 (``unpacking''), 5, 7 ist hier ein Tupel
print(c, d)
# %% Mengen
s = {11, 7, 3, 13, 2, 6} # #*set* wird definiert mit #*\{...\}*
print(s)
print(s & set(range(4,10))) # Schnittmenge
print(s | set(range(4,10))) # Vereinigungsmenge
print(s - set(range(4,10))) # Differenzmenge
print(s ^ set(range(4,10))) # sym. Differenzmenge (XOR)
# %% Dictionaries
tele = {'alice': 213, 'bob': 558} # Dictionary: Zuordnung von Keys zu Values
print(tele['bob'])
tele['charlie'] = 666 # Einträge können hinzugefügt oder verändert werden
print(tele)
d = {42: [1, 2, 3], 2.4: 31, 'valid': True}
print(d) # Reihenfolge bleibt erhalten
# %% Schleifen über Dictionaries
for name in tele.keys():
print(name)
print()
for nummer in tele.values():
print(nummer)
print()
for name, nummer in tele.items():
print(name, ': ', nummer, sep='')
print()
# %% List und Set Comprehension
squares = [i ** 2 for i in range(-4, 5)]
print(squares)
squares = []
for i in range(-4, 5):
squares.append(i ** 2)
print(squares)
squares = [i ** 2 for i in range(-4, 5) if i % 2 == 0]
print(squares)
squares = []
for i in range(-4, 5):
if i % 2 == 0:
squares.append(i ** 2)
print(squares)
unique_squares = {i ** 2 for i in range(-4, 5) if i % 2 == 0}
print(unique_squares)
# %% Dictionary Comprehension
print({word: len(word) for word in ('hey', 'world')})
names = ['Alice', 'Bob', 'Charlie', 'David']
numbers = [333, 558, 666, 696]
tele = {name: no for name, no in zip(names, numbers)}
print(tele)
backward_search = {no: name for name, no in tele.items()}
print(backward_search[666])
x1,x2,x3,y
25,1,20,0
5,16,2,1
13,21,13,1
17,9,11,0
21,17,13,1
\ No newline at end of file
%% Cell type:markdown id: tags:
# Code zu Folien
Dieses Skript bzw. Jupyter-Notebook enthält den Code, der auch auf den Folien "Python Vertiefung" enthalten ist. Zum Vorbereiten, Mitmachen oder Nacharbeiten.
%% Cell type:code id: tags:
```
a = [1, 3, 5]
b = a # b ist eine weitere Referenz
print(a, b)
b[1] = 10 # ändere Objekt, das b referenziert
print(a, b)
```
%% Cell type:code id: tags:
```
a = [1, 3, 5]
b = a # b ist eine weitere Referenz
c = [1, 3, 5] # zweites Objekt
print(a == b, a is b) # a und b sind dasselbe Objekt
print(a == c, a is c) # a und c sind gleich, aber verschiedene Objekte
```
%% Cell type:code id: tags:
```
a = [1, [3], 5] # Objekt in Objekt
b = a.copy() # b ist eine flache Kopie
print(a, b)
b[0] = 2 # ändere Objekt auf das b referenziert
b[1].append(4) # ändere Objekt auf das das Objekt referenziert auf das b referenziert
print(a, b)
```
%% Cell type:code id: tags:
```
t = (1, 2, 3)
a, b, c = t # auf der linken Seite darf ein Tupel oder eine Liste von Variablen stehen
def fun(x, y, z):
print(x, y, z)
t = (1, 2, 3) # Reihenfolge wird beibehalten
fun(*t) # ergibt: 1 2 3
d = {'z':1, 'y':2, 'x':3} # Reihenfolge ist hier unwichtig, aber Namen müssen übereinstimmen
fun(**d) # ergibt: 3 2 1
```
%% Cell type:code id: tags:
```
def fun(*args):
print(len(args), 'Argumente:', args)
fun(1, 2, 3) # ergibt: 3 Argumente: (1, 2, 3)
fun('hello', 'python') # ergibt: 2 Argumente: ('hello', 'python')
def fun(**kwargs):
print(len(kwargs), 'Argumente:', kwargs)
fun(y=1, x=2, z=3) # ergibt: 3 Argumente: {'y': 1, 'x': 2, 'z': 3}
def fun(*args, **kwargs):
print('args:', args, 'kwargs:', kwargs)
fun(1, 2, x=3, y=4) # ergibt args: (1, 2) kwargs: {'x': 3, 'y': 4}
```
%% Cell type:code id: tags:
```
def f(a, b):
return a(b)
f(print, 'test') # normale print-Funktion übergeben
def arg_fun(s):
return s * 2
print(f(arg_fun, 'test'))
arg_fun = lambda s: s * 2 # analog zu def arg_fun(s): return s * 2
print(f(arg_fun, 'test'))
print(f(lambda s: s * 2, 'test')) # analog zu def arg_fun(s): return s * 2
```
%% Cell type:code id: tags:
```
def multiplier(a):
def multiply(b):
return a * b
return multiply
five_times = multiplier(5)
ten_times = multiplier(10)
print(five_times(6))
print(ten_times(1))
```
%% Cell type:code id: tags:
```
def make_stars(fun):
def wrapped_in_stars():
print('*' * 30)
fun() # call original function
print('*' * 30)
return wrapped_in_stars
@make_stars
def hello_stars():
print('Hello, stars! :-)')
# starred = make_stars(hello_stars)
# starred()
# hello_stars = make_stars(hello_stars)
hello_stars()
```
%% Cell type:code id: tags:
```
import numpy # numpy steht über numpy zur Verfügung
print(numpy.pi)
import numpy as np # numpy steht über np zur Verfügung (üblich)
print(np.pi)
from numpy import pi # nur numpy.pi steht über pi zur Verfügung
print(pi)
```
%% Cell type:code id: tags:
```
# check current working directory – must be in the same directory as mymodule.py
import os
assert 'mymodule.py' in os.listdir(), f'mymodule.py is not in the current working directory of the python interpreter. You are here: {os.getcwd()}'
# try code from slide
import mymodule # gibt nur beim ersten Import etwas aus
mymodule.say_hello('you')
print(mymodule.__file__)
help(mymodule) # Hilfe anzeigen
```
%% Cell type:code id: tags:
```
# gibt nur beim ersten Import etwas aus
import mypackage
from mypackage.mymod import say_hello
mypackage.say_hello('you')
say_hello('you')
# hier muss das Modul "more" explizit importiert werden, da die Init-Datei leer ist
import mypackage.subpackage.more
mypackage.subpackage.more.say_bye()
```
%% Cell type:code id: tags:
```
f = open('data.csv')
header = f.readline()
print(header)
# for line in f.readlines(): # iteriert über alle Zeilen
for line in f: # oder kürzer: for line in f: iteriert auch über alle Zeilen
print(line.strip()) # strip entfernt \n um Leerzeilen zu vermeiden
f.close()
```
%% Cell type:code id: tags:
```
f = open('test.md', mode='w')
f.write('# Schreibtest\n\n')
print('Kleiner Test', file=f)
f.writelines(['\n', '- bli\n', '- bla\n'])
f.write('\n'.join(['', '- blupp', '- blupp\n']))
f.close()
# Ausgabe der Datei
f = open('test.md')
print(f.read())
f.close()
```
%% Cell type:code id: tags:
```
f = open('data.csv')
print(f.closed)
f.close()
print(f.closed)
with open('data.csv') as f:
# innerhalb dieses Blocks ist die Datei offen
header = f.readline()
print(f.closed) # ergibt: False
# außerhalb des Blocks ist die Datei geschlossen
print(f.closed) # ergibt: True
print(header)
```
%% Cell type:code id: tags:
```
p = 'summe.ipynb' # relativer Pfad zu einer Datei
dirname, filename = os.path.split(p) # splitte Pfad in Verzeichnis und Datei
base, ext = os.path.splitext(filename) # splitte Datei in Basis und Erweiterung
print(dirname, filename, base, ext, sep=', ')
absdir = os.path.abspath(dirname) # wandle dirname zu absoluten Pfad um
absfile = os.path.join(absdir, base + '.py') # fügt mit Pfadtrenner zusammen
print(absfile)
```
%% Cell type:code id: tags:
```
import pathlib
p = pathlib.Path('summe.ipynb') # relativer Pfad zu einer Datei
abs_p = p.absolute() # wandle p zu absoluten Pfad um (hier: irrelevant)
abs_py = abs_p.with_suffix('.py') # Dateinamenserweiterung tauschen
print(abs_py)
framework_dir = abs_p.parent.parent # gehe zweimal "hoch"
print(framework_dir) # (ginge auch relativ: PosixPath('..'))
prod_ex = framework_dir / 'funktionen' / 'prod.py' # füge mit Pfadtrenner an
print(prod_ex)
file_content = prod_ex.read_text() # Datei einlesen
prod_ex.with_name('prod_copy.py').write_text(file_content) # Datei schreiben
```
%% Cell type:code id: tags:
```
from glob import glob
files = glob('~/data-science-notebooks/*grundlagen/*-sol.ipynb')
print(files)
files = glob('~/data-science-notebooks/**/[g-h]*-sol.ipynb', recursive=True)
print(files)
paths = pathlib.Path('..').glob('**/[a-g]*.ipynb')
print(list(paths))
```
%% Cell type:code id: tags:
```
def nthroot(x: float, n: float = 2) -> float:
"""nth root of a number
Parameters
----------
x : float or int
Number to take the root from.
n : float or int, optional
Root parameter (the default is 2).
Returns
-------
float
The nth root.
"""
return x ** (1/n)
help(nthroot)
print(nthroot(3, 3))
print(nthroot('asd', 3)) # um hier den Fehler sehen zu können, sollte mypy als Paket und VS Code Erweiterung installiert sein
```
%% Cell type:code id: tags:
```
from pathlib import Path
def tabs_to_spaces(filename):
if '*' in filename:
raise InvalidFileName(f'Filenames with * are not allowed: {filename}') # message if not caught
# raise ValueError(f'Filenames with * are not allowed: {filename}') # message if not caught
p = Path(filename)
file_contents = p.read_text().replace('\t', ' ')
p.write_text(file_contents)
class InvalidFileName(Exception):
pass
filenames = ['data.csv', 'does-not-exist', '*.csv']
for filename in filenames:
try:
tabs_to_spaces(filename)
except FileNotFoundError as e:
print(f'File {filename} not found, so also not converted to spaces.')
# except ValueError as e:
except InvalidFileName as e:
print(f'Use proper filenames, not glob syntax. Resolve {filename} before using glob.glob.')
except PermissionError as e: # e enthält die Fehlernachricht als str(e)
print(e, 'Could not convert to spaces.', sep='. ')
```
%% Cell type:code id: tags:
```
def fun():
with open('does-not-exist') as f:
f.read()
fun() # FileNotFoundError
```
%% Cell type:code id: tags:
```
class MyComplex:
def __init__(self, re=0, im=0): # Konstruktor mit zwei "echten" Argumenten
self.re = re
self.im = im
def conjugate(self): # Methode ohne "echte" Argumente
return MyComplex(self.re, -self.im)
def __repr__(self): # wird über repr(z) (und ggf. über str(z)) aufgerufen
return f'MyComplex({self.re}, {self.im})'
def __str__(self): # wird über str(z) aufgerufen
return f'({self.re}{self.im:+}j)'
z1 = MyComplex(3, 4)
z2 = z1.conjugate()
print(f'z1: ({z1.re}, {z1.im})')
print(f'z2: ({z2.re}, {z2.im})')
print(repr(z1))
print(z1) # ruft intern str(z) auf, das als Fallback repr(z) aufrufen würde
```
%% Cell type:code id: tags:
```
class A:
def __bar(self):
print('...not really private...')
a = A()
# a.__bar() # So geht es zwar nicht...
a._A__bar() # aber so
class B:
def _foo(self):
print('foo!')
b = B()
b._foo()
```
%% Cell type:code id: tags:
```
class MyPositiveNumber:
def __init__(self, r=0):
self.r = r
num = MyPositiveNumber(3)
num.r = -8 # schreiben
print(num.r) # lesen, ergibt -8
class MyPositiveNumber:
def __init__(self, r=0):
self.r = r # benutzt schon setter unten
@property # getter
def r(self):
return self._r
@r.setter # setter
def r(self, val):
self._r = val if val > 0 else 0
num = MyPositiveNumber(3)
num.r = -8 # ruft setter auf
print(num.r) # ruft getter auf, ergibt: 0
```
%% Cell type:code id: tags:
```
class MyPositiveComplex(MyPositiveNumber): # erbt von MyPositiveNumber
def __init__(self, r=0, i=0):
super().__init__(r) # rufe Konstruktor von MyPositiveNumber auf
self.i = i # benutzt schon setter unten
@property # getter
def i(self):
return self._i
@i.setter # setter
def i(self, val):
self._i = val if val > 0 else 0
c = MyPositiveComplex(-8, 1)
c.i = -5 # ruft setter auf
print(f'{c.r} + {c.i}j') # ruft getter auf, ergibt: 0 + 0j
```
%% Cell type:code id: tags:
```
class Text:
def __init__(self, text):
self.text = text
@classmethod
def from_file(cls, path):
with open(path) as f:
return cls(f.read())
class GradedText(Text):
def __init__(self, text, grade=None):
super().__init__(text)
self.grade = grade
file = 'data.csv'
t = Text.from_file(file)
print(t.text)
print(type(t))
gt = GradedText.from_file(file)
print(gt.text, gt.grade)
print(type(gt))
```
# %% [markdown]
# # Code zu Folien
#
# Dieses Skript bzw. Jupyter-Notebook enthält den Code, der auch auf den Folien "Python Vertiefung" enthalten ist. Zum Vorbereiten, Mitmachen oder Nacharbeiten.
# %% Referenzen
a = [1, 3, 5]
b = a # b ist eine weitere Referenz
print(a, b)
b[1] = 10 # ändere Objekt, das b referenziert
print(a, b)
# %% Gleichheit und Identität
a = [1, 3, 5]
b = a # b ist eine weitere Referenz
c = [1, 3, 5] # zweites Objekt
print(a == b, a is b) # a und b sind dasselbe Objekt
print(a == c, a is c) # a und c sind gleich, aber verschiedene Objekte
# %% Flache Kopie
a = [1, [3], 5] # Objekt in Objekt
b = a.copy() # b ist eine flache Kopie
print(a, b)
b[0] = 2 # ändere Objekt auf das b referenziert
b[1].append(4) # ändere Objekt auf das das Objekt referenziert auf das b referenziert
print(a, b)
# %% Übergabe an Funktionsargumente
t = (1, 2, 3)
a, b, c = t # auf der linken Seite darf ein Tupel oder eine Liste von Variablen stehen
def fun(x, y, z):
print(x, y, z)
t = (1, 2, 3) # Reihenfolge wird beibehalten
fun(*t) # ergibt: 1 2 3
d = {'z':1, 'y':2, 'x':3} # Reihenfolge ist hier unwichtig, aber Namen müssen übereinstimmen
fun(**d) # ergibt: 3 2 1
# %% Beliebige Anzahl Argumente
def fun(*args):
print(len(args), 'Argumente:', args)
fun(1, 2, 3) # ergibt: 3 Argumente: (1, 2, 3)
fun('hello', 'python') # ergibt: 2 Argumente: ('hello', 'python')
def fun(**kwargs):
print(len(kwargs), 'Argumente:', kwargs)
fun(y=1, x=2, z=3) # ergibt: 3 Argumente: {'y': 1, 'x': 2, 'z': 3}
def fun(*args, **kwargs):
print('args:', args, 'kwargs:', kwargs)
fun(1, 2, x=3, y=4) # ergibt args: (1, 2) kwargs: {'x': 3, 'y': 4}
# %% Funktionen als Objekte
def f(a, b):
return a(b)
f(print, 'test') # normale print-Funktion übergeben
def arg_fun(s):
return s * 2
print(f(arg_fun, 'test'))
arg_fun = lambda s: s * 2 # analog zu def arg_fun(s): return s * 2
print(f(arg_fun, 'test'))
print(f(lambda s: s * 2, 'test')) # analog zu def arg_fun(s): return s * 2
# %% Funktionen als Rückgabewerte / Closure
def multiplier(a):
def multiply(b):
return a * b
return multiply
five_times = multiplier(5)
ten_times = multiplier(10)
print(five_times(6))
print(ten_times(1))
# %% Decorators
def make_stars(fun):
def wrapped_in_stars():
print('*' * 30)
fun() # call original function
print('*' * 30)
return wrapped_in_stars
@make_stars
def hello_stars():
print('Hello, stars! :-)')
# starred = make_stars(hello_stars)
# starred()
# hello_stars = make_stars(hello_stars)
hello_stars()
# %% Module importieren
import numpy # numpy steht über numpy zur Verfügung
print(numpy.pi)
import numpy as np # numpy steht über np zur Verfügung (üblich)
print(np.pi)
from numpy import pi # nur numpy.pi steht über pi zur Verfügung
print(pi)
# %% Eigene Module
# check current working directory – must be in the same directory as mymodule.py
import os
assert 'mymodule.py' in os.listdir(), f'mymodule.py is not in the current working directory of the python interpreter. You are here: {os.getcwd()}'
# try code from slide
import mymodule # gibt nur beim ersten Import etwas aus
mymodule.say_hello('you')
print(mymodule.__file__)
help(mymodule) # Hilfe anzeigen
# %% Eigene Pakete
# gibt nur beim ersten Import etwas aus
import mypackage
from mypackage.mymod import say_hello
mypackage.say_hello('you')
say_hello('you')
# hier muss das Modul "more" explizit importiert werden, da die Init-Datei leer ist
import mypackage.subpackage.more
mypackage.subpackage.more.say_bye()
# %% Dateien lesen
f = open('data.csv')
header = f.readline()
print(header)
# for line in f.readlines(): # iteriert über alle Zeilen
for line in f: # oder kürzer: for line in f: iteriert auch über alle Zeilen
print(line.strip()) # strip entfernt \n um Leerzeilen zu vermeiden
f.close()
# %% Dateien schreiben
f = open('test.md', mode='w')
f.write('# Schreibtest\n\n')
print('Kleiner Test', file=f)
f.writelines(['\n', '- bli\n', '- bla\n'])
f.write('\n'.join(['', '- blupp', '- blupp\n']))
f.close()
# Ausgabe der Datei
f = open('test.md')
print(f.read())
f.close()
# %% Dateien öffnen und schließen mit Kontext-Manager
f = open('data.csv')
print(f.closed)
f.close()
print(f.closed)
with open('data.csv') as f:
# innerhalb dieses Blocks ist die Datei offen
header = f.readline()
print(f.closed) # ergibt: False
# außerhalb des Blocks ist die Datei geschlossen
print(f.closed) # ergibt: True
print(header)
# %% Pfade als Objekt: String
p = 'summe.ipynb' # relativer Pfad zu einer Datei
dirname, filename = os.path.split(p) # splitte Pfad in Verzeichnis und Datei
base, ext = os.path.splitext(filename) # splitte Datei in Basis und Erweiterung
print(dirname, filename, base, ext, sep=', ')
absdir = os.path.abspath(dirname) # wandle dirname zu absoluten Pfad um
absfile = os.path.join(absdir, base + '.py') # fügt mit Pfadtrenner zusammen
print(absfile)
# %% Pfade als Objekt: pathlib
import pathlib
p = pathlib.Path('summe.ipynb') # relativer Pfad zu einer Datei
abs_p = p.absolute() # wandle p zu absoluten Pfad um (hier: irrelevant)
abs_py = abs_p.with_suffix('.py') # Dateinamenserweiterung tauschen
print(abs_py)
framework_dir = abs_p.parent.parent # gehe zweimal "hoch"
print(framework_dir) # (ginge auch relativ: PosixPath('..'))
prod_ex = framework_dir / 'funktionen' / 'prod.py' # füge mit Pfadtrenner an
print(prod_ex)
file_content = prod_ex.read_text() # Datei einlesen
prod_ex.with_name('prod_copy.py').write_text(file_content) # Datei schreiben
# %% Dateinamen finden mittels glob-Syntax
from glob import glob
files = glob('~/data-science-notebooks/*grundlagen/*-sol.ipynb')
print(files)
files = glob('~/data-science-notebooks/**/[g-h]*-sol.ipynb', recursive=True)
print(files)
paths = pathlib.Path('..').glob('**/[a-g]*.ipynb')
print(list(paths))
# %% Docstrings und Type Hinting
def nthroot(x: float, n: float = 2) -> float:
"""nth root of a number
Parameters
----------
x : float or int
Number to take the root from.
n : float or int, optional
Root parameter (the default is 2).
Returns
-------
float
The nth root.
"""
return x ** (1/n)
help(nthroot)
print(nthroot(3, 3))
print(nthroot('asd', 3)) # um hier den Fehler sehen zu können, sollte mypy als Paket und VS Code Erweiterung installiert sein
# %% Fehler werfen und behandeln
from pathlib import Path
def tabs_to_spaces(filename):
if '*' in filename:
raise InvalidFileName(f'Filenames with * are not allowed: {filename}') # message if not caught
# raise ValueError(f'Filenames with * are not allowed: {filename}') # message if not caught
p = Path(filename)
file_contents = p.read_text().replace('\t', ' ')
p.write_text(file_contents)
class InvalidFileName(Exception):
pass
filenames = ['data.csv', 'does-not-exist', '*.csv']
for filename in filenames:
try:
tabs_to_spaces(filename)
except FileNotFoundError as e:
print(f'File {filename} not found, so also not converted to spaces.')
# except ValueError as e:
except InvalidFileName as e:
print(f'Use proper filenames, not glob syntax. Resolve {filename} before using glob.glob.')
except PermissionError as e: # e enthält die Fehlernachricht als str(e)
print(e, 'Could not convert to spaces.', sep='. ')
# %% Traceback
def fun():
with open('does-not-exist') as f:
f.read()
fun() # FileNotFoundError
# %% MyComplex
class MyComplex:
def __init__(self, re=0, im=0): # Konstruktor mit zwei "echten" Argumenten
self.re = re
self.im = im
def conjugate(self): # Methode ohne "echte" Argumente
return MyComplex(self.re, -self.im)
def __repr__(self): # wird über repr(z) (und ggf. über str(z)) aufgerufen
return f'MyComplex({self.re}, {self.im})'
def __str__(self): # wird über str(z) aufgerufen
return f'({self.re}{self.im:+}j)'
z1 = MyComplex(3, 4)
z2 = z1.conjugate()
print(f'z1: ({z1.re}, {z1.im})')
print(f'z2: ({z2.re}, {z2.im})')
print(repr(z1))
print(z1) # ruft intern str(z) auf, das als Fallback repr(z) aufrufen würde
# %% Kapselung
class A:
def __bar(self):
print('...not really private...')
a = A()
# a.__bar() # So geht es zwar nicht...
a._A__bar() # aber so
class B:
def _foo(self):
print('foo!')
b = B()
b._foo()
# %% Getter und Setter mit Decorator property
class MyPositiveNumber:
def __init__(self, r=0):
self.r = r
num = MyPositiveNumber(3)
num.r = -8 # schreiben
print(num.r) # lesen, ergibt -8
class MyPositiveNumber:
def __init__(self, r=0):
self.r = r # benutzt schon setter unten
@property # getter
def r(self):
return self._r
@r.setter # setter
def r(self, val):
self._r = val if val > 0 else 0
num = MyPositiveNumber(3)
num.r = -8 # ruft setter auf
print(num.r) # ruft getter auf, ergibt: 0
# %% Vererbung
class MyPositiveComplex(MyPositiveNumber): # erbt von MyPositiveNumber
def __init__(self, r=0, i=0):
super().__init__(r) # rufe Konstruktor von MyPositiveNumber auf
self.i = i # benutzt schon setter unten
@property # getter
def i(self):
return self._i
@i.setter # setter
def i(self, val):
self._i = val if val > 0 else 0
c = MyPositiveComplex(-8, 1)
c.i = -5 # ruft setter auf
print(f'{c.r} + {c.i}j') # ruft getter auf, ergibt: 0 + 0j
# %% Alternativer Konstruktor mit Klassenmethode
class Text:
def __init__(self, text):
self.text = text
@classmethod
def from_file(cls, path):
with open(path) as f:
return cls(f.read())
class GradedText(Text):
def __init__(self, text, grade=None):
super().__init__(text)
self.grade = grade
file = 'data.csv'
t = Text.from_file(file)
print(t.text)
print(type(t))
gt = GradedText.from_file(file)
print(gt.text, gt.grade)
print(type(gt))
'''This is my example module'''
__version__ = '1.3.4'
print('Hello Module')
def say_hello(name):
print('Hello', name)
\ No newline at end of file
from mypackage.mymod import say_hello
print('Hello Module')
def say_hello(name):
print('Hello', name)
\ No newline at end of file
def say_bye():
print('bye')
"Month","Accidental deaths in USA: monthly, 1973 ? 1978"
"1973-01",9007
"1973-02",8106
"1973-03",8928
"1973-04",9137
"1973-05",10017
"1973-06",10826
"1973-07",11317
"1973-08",10744
"1973-09",9713
"1973-10",9938
"1973-11",9161
"1973-12",8927
"1974-01",7750
"1974-02",6981
"1974-03",8038
"1974-04",8422
"1974-05",8714
"1974-06",9512
"1974-07",10120
"1974-08",9823
"1974-09",8743
"1974-10",9129
"1974-11",8710
"1974-12",8680
"1975-01",8162
"1975-02",7306
"1975-03",8124
"1975-04",7870
"1975-05",9387
"1975-06",9556
"1975-07",10093
"1975-08",9620
"1975-09",8285
"1975-10",8433
"1975-11",8160
"1975-12",8034
"1976-01",7717
"1976-02",7461
"1976-03",7776
"1976-04",7925
"1976-05",8634
"1976-06",8945
"1976-07",10078
"1976-08",9179
"1976-09",8037
"1976-10",8488
"1976-11",7874
"1976-12",8647
"1977-01",7792
"1977-02",6957
"1977-03",7726
"1977-04",8106
"1977-05",8890
"1977-06",9299
"1977-07",10625
"1977-08",9302
"1977-09",8314
"1977-10",8850
"1977-11",8265
"1977-12",8796
"1978-01",7836
"1978-02",6892
"1978-03",7791
"1978-04",8129
"1978-05",9115
"1978-06",9434
"1978-07",10484
"1978-08",9827
"1978-09",9110
"1978-10",9070
"1978-11",8633
"1978-12",9240
\ No newline at end of file
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Please register or to comment