Skip to content
GitLab
Menu
Projects
Groups
Snippets
Help
Help
Support
Community forum
Keyboard shortcuts
?
Submit feedback
Sign in
Toggle navigation
Menu
Open sidebar
IENT
GDET3-Demos
Commits
e1f827da
Commit
e1f827da
authored
Nov 28, 2019
by
Christian Rohlfing
Browse files
Merge branch 'development-lab' of git.rwth-aachen.de:IENT/gdet3-demos into development-lab
parents
23285a50
40ea7565
Changes
2
Hide whitespace changes
Inline
Side-by-side
GDET3 Diskrete Faltung GUI.ipynb
0 → 100644
View file @
e1f827da
{
"cells": [
{
"cell_type": "code",
"execution_count": null,
"metadata": {
"jupyter": {
"source_hidden": true
}
},
"outputs": [],
"source": [
"# Copyright 2019 Institut für Nachrichtentechnik, RWTH Aachen University\n",
"%matplotlib widget\n",
"\n",
"import ipywidgets as widgets\n",
"from ipywidgets import interact, interactive, fixed, Layout, HBox, VBox\n",
"from IPython.display import clear_output, display, HTML\n",
"\n",
"from scipy import signal # convolution\n",
"\n",
"from ient_nb.ient_plots import *\n",
"from ient_nb.ient_signals import *"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"# Demonstrator Diskrete Faltung"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"Im Folgenden wird die Faltung\n",
"$g(n)=s(n)\\ast h(n)$\n",
"betrachtet. <br>\n",
"$s(n)$ und $h(n)$ können gewählt werden als:\n",
"* $\\delta(n)$\n",
"* $\\epsilon(n)$\n",
"* $\\epsilon(n)\\cdot\\mathrm{b}^{n}$\n",
"* $rect(n) = \\epsilon(n+M)-\\epsilon(n-M-1)$"
]
},
{
"cell_type": "code",
"execution_count": null,
"metadata": {
"jupyter": {
"source_hidden": true
}
},
"outputs": [],
"source": [
"n = np.linspace(-10, 10, 21)\n",
"m = np.linspace(-40, 40, 81) # m Achse\n",
"s_type = h_type = ''; s_n0 = h_n0 = 0\n",
"M = 1\n",
"b = .5\n",
"\n",
"n0 = -2\n",
"\n",
"def convolution(s, h):\n",
" # Convolve s and h numerically\n",
" return signal.convolve(s(m), h(m), mode='same')\n",
"\n",
"signal_types = {'Dirac-Impuls' : lambda n: np.where(n==0, 1, 0),\n",
" 'Sprungfunktion' : unitstep,\n",
" 'Exponentialimpuls' : lambda n: unitstep(n)*b**n,\n",
" 'Rechteck' : lambda n: unitstep(n+M) - unitstep(n-M-1)\n",
" }\n",
"\n",
"def _update_b(_b):\n",
" global b\n",
" b = _b\n",
" update_signals(s_type, s_n0, h_type, h_n0)\n",
"\n",
"def _update_M(_M):\n",
" global M\n",
" M = _M\n",
" update_signals(s_type, s_n0, h_type, h_n0)\n",
"\n",
"# widgets for setting parameters b and M\n",
"w_b = interactive(_update_b, _b=widgets.FloatSlider(min=.1, max=1, value=.5, step=.1, description=r'$b$', style=ient_wdgtl_style))\n",
"w_M = interactive(_update_M, _M=widgets.FloatSlider(min=0, max=5, value=1, step=1, description=r'$M$', style=ient_wdgtl_style))\n",
"box = HBox([])\n",
"\n",
"fig0, axs0 = plt.subplots(1, 2, figsize=(8,2)); container_s = container_h = None\n",
"@widgets.interact(_s_type=widgets.Dropdown(options=list(signal_types.keys()), description=r'Wähle $s(n)$:'),\n",
" _s_n0=widgets.FloatSlider(min=-5, max=5, value=0, step=1, description=r'Verschiebung $n_0$', style=ient_wdgtl_style), \n",
" _h_type=widgets.Dropdown(options=list(signal_types.keys()), description=r'Wähle $h(n)$:'),\n",
" _h_n0=widgets.FloatSlider(min=-5, max=5, value=0, step=1, description=r'Verschiebung $n_0$', style=ient_wdgtl_style))\n",
"def update_signals(_s_type, _s_n0, _h_type, _h_n0):\n",
" # set global variables\n",
" global s_type, s_n0, h_type, h_n0\n",
" s_type = _s_type; s_n0 = _s_n0; h_type = _h_type; h_n0 = _h_n0\n",
" \n",
" global s, h, gn, container_s, container_h # reused in second interactive plot\n",
" s = lambda m: signal_types[_s_type]((m-_s_n0)); # s(m-n0)\n",
" h = lambda m: signal_types[_h_type]((m-_h_n0)); # h(m-n0)\n",
" gn = convolution(s, h) # numerical convolution\n",
" \n",
" # update second plot if existing\n",
" try:\n",
" global n0\n",
" update_plot(n0)\n",
" except NameError:\n",
" pass\n",
" \n",
" # show widgets according to chosen s and h\n",
" if _s_type == 'Exponentialimpuls' and _h_type == 'Rechteck':\n",
" box.children = [w_b, w_M]\n",
" elif _s_type == 'Rechteck' and _h_type == 'Exponentialimpuls':\n",
" box.children = [w_M, w_b]\n",
" elif _s_type == 'Exponentialimpuls' or _h_type == 'Exponentialimpuls':\n",
" box.children = [w_b]\n",
" elif _s_type == 'Rechteck' or _h_type == 'Rechteck':\n",
" box.children = [w_M]\n",
" else:\n",
" box.children = []\n",
" \n",
" # display s and h plots\n",
" if container_s is None:\n",
" ax = axs0[0]; \n",
" container_s = ient_stem(ax, m, s(m), 'rwth')\n",
" ax.set_xticks(np.arange(-10, 11, step=2))\n",
" ax.set_xlabel(r'$\\rightarrow n$'); ax.set_ylabel(r'$\\uparrow s(n)$')\n",
" ax.set_xlim([-10.9, 10.9]); ax.set_ylim([-1.19, 1.19]); ient_axis(ax); ient_grid(ax);\n",
" \n",
" ax = axs0[1]; \n",
" container_h = ient_stem(ax, m, h(m), 'rwth')\n",
" ax.set_xticks(np.arange(-10, 11, step=2))\n",
" ax.set_xlabel(r'$\\rightarrow n$'); ax.set_ylabel(r'$\\uparrow h(n)$')\n",
" ax.set_xlim(axs0[0].get_xlim()); ax.set_ylim(axs0[0].get_ylim()); ient_axis(ax); ient_grid(ax);\n",
"\n",
" else:\n",
" ient_stem_set_ydata(container_s, s(m))\n",
" ient_stem_set_ydata(container_h, h(m))\n",
" \n",
"\n",
"display(box)"
]
},
{
"cell_type": "code",
"execution_count": null,
"metadata": {
"jupyter": {
"source_hidden": true
}
},
"outputs": [],
"source": [
"fig, axs = plt.subplots(2, 1, figsize=(8,6),) # gridspec_kw = {'width_ratios':[3, 1]}\n",
"global n0\n",
"container_ss = container_hh = container_gg = None\n",
"@widgets.interact(n=widgets.FloatSlider(min=-10, max=10, value=n0, step=1, description='Verschiebung $n$', style=ient_wdgtl_style))\n",
"def update_plot(n):\n",
" global container_ss, container_hh, container_gg\n",
" global n0\n",
" n0 = n\n",
" n_ind = np.where(m>=n); n_ind = n_ind[0][0]; g_plot = gn.copy(); g_plot[n_ind+1:] = 0; # hide g(n') with n'>n\n",
" if container_gg is None:\n",
" ax = axs[1]\n",
" container_gg = ient_stem(ax, m, g_plot)\n",
" \n",
" if container_ss is not None:\n",
" ient_stem_set_ydata(container_ss, s(m))\n",
" ient_stem_set_ydata(container_hh, h(n-m))\n",
" ient_stem_set_ydata(container_gg, g_plot)\n",
" ax = axs[0]\n",
" ax.texts[0].set_x(n); ax.lines[3].set_xdata([n,n]) # update labels\n",
" ax = axs[1]\n",
" ient_update_ylim(ax, gn, 0.19, 20);\n",
" \n",
" else:\n",
" ax = axs[0];\n",
" container_ss = ient_stem(ax, m, s(m), 'grun', label=r'$s(m)$')\n",
" container_ss[0].set_markerfacecolor('none'); \n",
" container_ss[0].set_markersize(8); \n",
" container_ss[0].set_markeredgewidth(2);\n",
" \n",
" container_hh = ient_stem(ax, m, h(n-m), 'rwth', label=r'$h(n-m)$')\n",
" \n",
" ient_annotate_xtick(ax, r'$n$', n, -0.1, 'rwth', 15); # mark n on m axis\n",
" ax.set_xlabel(r'$\\rightarrow m$');\n",
" ax.set_xlim([-10.2,10.2]); ient_update_ylim(ax, np.concatenate((h(m), s(m))), 0.19, 5);\n",
" ax.set_xticks(np.arange(-10, 11, step=2))\n",
" ax.legend(); ient_grid(ax); ient_axis(ax);\n",
" \n",
" ax = axs[1]\n",
" ax.set_xlabel(r'$\\rightarrow n$'); ax.set_ylabel(r'$\\uparrow g(n)=s(n)\\ast h(n)$'); \n",
" ax.set_xlim(axs[0].get_xlim()); ient_update_ylim(ax, gn, 0.19, 20);\n",
" ax.set_xticks(np.arange(-10, 11, step=2))\n",
" ient_grid(ax); ient_axis(ax);"
]
},
{
"cell_type": "code",
"execution_count": null,
"metadata": {},
"outputs": [],
"source": []
}
],
"metadata": {
"kernelspec": {
"display_name": "Python 3",
"language": "python",
"name": "python3"
},
"language_info": {
"codemirror_mode": {
"name": "ipython",
"version": 3
},
"file_extension": ".py",
"mimetype": "text/x-python",
"name": "python",
"nbconvert_exporter": "python",
"pygments_lexer": "ipython3",
"version": "3.7.3"
}
},
"nbformat": 4,
"nbformat_minor": 4
}
%% Cell type:code id: tags:
```
python
# Copyright 2019 Institut für Nachrichtentechnik, RWTH Aachen University
%
matplotlib
widget
import
ipywidgets
as
widgets
from
ipywidgets
import
interact
,
interactive
,
fixed
,
Layout
,
HBox
,
VBox
from
IPython.display
import
clear_output
,
display
,
HTML
from
scipy
import
signal
# convolution
from
ient_nb.ient_plots
import
*
from
ient_nb.ient_signals
import
*
```
%% Cell type:markdown id: tags:
# Demonstrator Diskrete Faltung
%% Cell type:markdown id: tags:
Im Folgenden wird die Faltung
$g(n)=s(n)
\a
st h(n)$
betrachtet.
<br>
$s(n)$ und $h(n)$ können gewählt werden als:
*
$
\d
elta(n)$
*
$
\e
psilon(n)$
*
$
\e
psilon(n)
\c
dot
\m
athrm{b}^{n}$
*
$rect(n) =
\e
psilon(n+M)-
\e
psilon(n-M-1)$
%% Cell type:code id: tags:
```
python
n
=
np
.
linspace
(
-
10
,
10
,
21
)
m
=
np
.
linspace
(
-
40
,
40
,
81
)
# m Achse
s_type
=
h_type
=
''
;
s_n0
=
h_n0
=
0
M
=
1
b
=
.
5
n0
=
-
2
def
convolution
(
s
,
h
):
# Convolve s and h numerically
return
signal
.
convolve
(
s
(
m
),
h
(
m
),
mode
=
'same'
)
signal_types
=
{
'Dirac-Impuls'
:
lambda
n
:
np
.
where
(
n
==
0
,
1
,
0
),
'Sprungfunktion'
:
unitstep
,
'Exponentialimpuls'
:
lambda
n
:
unitstep
(
n
)
*
b
**
n
,
'Rechteck'
:
lambda
n
:
unitstep
(
n
+
M
)
-
unitstep
(
n
-
M
-
1
)
}
def
_update_b
(
_b
):
global
b
b
=
_b
update_signals
(
s_type
,
s_n0
,
h_type
,
h_n0
)
def
_update_M
(
_M
):
global
M
M
=
_M
update_signals
(
s_type
,
s_n0
,
h_type
,
h_n0
)
# widgets for setting parameters b and M
w_b
=
interactive
(
_update_b
,
_b
=
widgets
.
FloatSlider
(
min
=
.
1
,
max
=
1
,
value
=
.
5
,
step
=
.
1
,
description
=
r
'$b$'
,
style
=
ient_wdgtl_style
))
w_M
=
interactive
(
_update_M
,
_M
=
widgets
.
FloatSlider
(
min
=
0
,
max
=
5
,
value
=
1
,
step
=
1
,
description
=
r
'$M$'
,
style
=
ient_wdgtl_style
))
box
=
HBox
([])
fig0
,
axs0
=
plt
.
subplots
(
1
,
2
,
figsize
=
(
8
,
2
));
container_s
=
container_h
=
None
@
widgets
.
interact
(
_s_type
=
widgets
.
Dropdown
(
options
=
list
(
signal_types
.
keys
()),
description
=
r
'Wähle $s(n)$:'
),
_s_n0
=
widgets
.
FloatSlider
(
min
=-
5
,
max
=
5
,
value
=
0
,
step
=
1
,
description
=
r
'Verschiebung $n_0$'
,
style
=
ient_wdgtl_style
),
_h_type
=
widgets
.
Dropdown
(
options
=
list
(
signal_types
.
keys
()),
description
=
r
'Wähle $h(n)$:'
),
_h_n0
=
widgets
.
FloatSlider
(
min
=-
5
,
max
=
5
,
value
=
0
,
step
=
1
,
description
=
r
'Verschiebung $n_0$'
,
style
=
ient_wdgtl_style
))
def
update_signals
(
_s_type
,
_s_n0
,
_h_type
,
_h_n0
):
# set global variables
global
s_type
,
s_n0
,
h_type
,
h_n0
s_type
=
_s_type
;
s_n0
=
_s_n0
;
h_type
=
_h_type
;
h_n0
=
_h_n0
global
s
,
h
,
gn
,
container_s
,
container_h
# reused in second interactive plot
s
=
lambda
m
:
signal_types
[
_s_type
]((
m
-
_s_n0
));
# s(m-n0)
h
=
lambda
m
:
signal_types
[
_h_type
]((
m
-
_h_n0
));
# h(m-n0)
gn
=
convolution
(
s
,
h
)
# numerical convolution
# update second plot if existing
try
:
global
n0
update_plot
(
n0
)
except
NameError
:
pass
# show widgets according to chosen s and h
if
_s_type
==
'Exponentialimpuls'
and
_h_type
==
'Rechteck'
:
box
.
children
=
[
w_b
,
w_M
]
elif
_s_type
==
'Rechteck'
and
_h_type
==
'Exponentialimpuls'
:
box
.
children
=
[
w_M
,
w_b
]
elif
_s_type
==
'Exponentialimpuls'
or
_h_type
==
'Exponentialimpuls'
:
box
.
children
=
[
w_b
]
elif
_s_type
==
'Rechteck'
or
_h_type
==
'Rechteck'
:
box
.
children
=
[
w_M
]
else
:
box
.
children
=
[]
# display s and h plots
if
container_s
is
None
:
ax
=
axs0
[
0
];
container_s
=
ient_stem
(
ax
,
m
,
s
(
m
),
'rwth'
)
ax
.
set_xticks
(
np
.
arange
(
-
10
,
11
,
step
=
2
))
ax
.
set_xlabel
(
r
'$\rightarrow n$'
);
ax
.
set_ylabel
(
r
'$\uparrow s(n)$'
)
ax
.
set_xlim
([
-
10.9
,
10.9
]);
ax
.
set_ylim
([
-
1.19
,
1.19
]);
ient_axis
(
ax
);
ient_grid
(
ax
);
ax
=
axs0
[
1
];
container_h
=
ient_stem
(
ax
,
m
,
h
(
m
),
'rwth'
)
ax
.
set_xticks
(
np
.
arange
(
-
10
,
11
,
step
=
2
))
ax
.
set_xlabel
(
r
'$\rightarrow n$'
);
ax
.
set_ylabel
(
r
'$\uparrow h(n)$'
)
ax
.
set_xlim
(
axs0
[
0
].
get_xlim
());
ax
.
set_ylim
(
axs0
[
0
].
get_ylim
());
ient_axis
(
ax
);
ient_grid
(
ax
);
else
:
ient_stem_set_ydata
(
container_s
,
s
(
m
))
ient_stem_set_ydata
(
container_h
,
h
(
m
))
display
(
box
)
```
%% Cell type:code id: tags:
```
python
fig
,
axs
=
plt
.
subplots
(
2
,
1
,
figsize
=
(
8
,
6
),)
# gridspec_kw = {'width_ratios':[3, 1]}
global
n0
container_ss
=
container_hh
=
container_gg
=
None
@
widgets
.
interact
(
n
=
widgets
.
FloatSlider
(
min
=-
10
,
max
=
10
,
value
=
n0
,
step
=
1
,
description
=
'Verschiebung $n$'
,
style
=
ient_wdgtl_style
))
def
update_plot
(
n
):
global
container_ss
,
container_hh
,
container_gg
global
n0
n0
=
n
n_ind
=
np
.
where
(
m
>=
n
);
n_ind
=
n_ind
[
0
][
0
];
g_plot
=
gn
.
copy
();
g_plot
[
n_ind
+
1
:]
=
0
;
# hide g(n') with n'>n
if
container_gg
is
None
:
ax
=
axs
[
1
]
container_gg
=
ient_stem
(
ax
,
m
,
g_plot
)
if
container_ss
is
not
None
:
ient_stem_set_ydata
(
container_ss
,
s
(
m
))
ient_stem_set_ydata
(
container_hh
,
h
(
n
-
m
))
ient_stem_set_ydata
(
container_gg
,
g_plot
)
ax
=
axs
[
0
]
ax
.
texts
[
0
].
set_x
(
n
);
ax
.
lines
[
3
].
set_xdata
([
n
,
n
])
# update labels
ax
=
axs
[
1
]
ient_update_ylim
(
ax
,
gn
,
0.19
,
20
);
else
:
ax
=
axs
[
0
];
container_ss
=
ient_stem
(
ax
,
m
,
s
(
m
),
'grun'
,
label
=
r
'$s(m)$'
)
container_ss
[
0
].
set_markerfacecolor
(
'none'
);
container_ss
[
0
].
set_markersize
(
8
);
container_ss
[
0
].
set_markeredgewidth
(
2
);
container_hh
=
ient_stem
(
ax
,
m
,
h
(
n
-
m
),
'rwth'
,
label
=
r
'$h(n-m)$'
)
ient_annotate_xtick
(
ax
,
r
'$n$'
,
n
,
-
0.1
,
'rwth'
,
15
);
# mark n on m axis
ax
.
set_xlabel
(
r
'$\rightarrow m$'
);
ax
.
set_xlim
([
-
10.2
,
10.2
]);
ient_update_ylim
(
ax
,
np
.
concatenate
((
h
(
m
),
s
(
m
))),
0.19
,
5
);
ax
.
set_xticks
(
np
.
arange
(
-
10
,
11
,
step
=
2
))
ax
.
legend
();
ient_grid
(
ax
);
ient_axis
(
ax
);
ax
=
axs
[
1
]
ax
.
set_xlabel
(
r
'$\rightarrow n$'
);
ax
.
set_ylabel
(
r
'$\uparrow g(n)=s(n)\ast h(n)$'
);
ax
.
set_xlim
(
axs
[
0
].
get_xlim
());
ient_update_ylim
(
ax
,
gn
,
0.19
,
20
);
ax
.
set_xticks
(
np
.
arange
(
-
10
,
11
,
step
=
2
))
ient_grid
(
ax
);
ient_axis
(
ax
);
```
%% Cell type:code id: tags:
```
python
```
src/laplace/laplace_plot.py
View file @
e1f827da
...
...
@@ -41,6 +41,8 @@ class pzPlot():
H
=
None
Hlog
=
None
P
=
1
# no of poles for butterworth filter
def
__init__
(
self
,
pp
=
np
.
array
([
0
]),
pz
=
np
.
array
([]),
ord_p
=
np
.
array
([
1
]),
ord_z
=
np
.
array
([])):
self
.
H0
=
1
...
...
@@ -135,9 +137,14 @@ class pzPlot():
self
.
w_action_type
=
interactive
(
self
.
update_action
,
action
=
widgets
.
Dropdown
(
options
=
list
(
self
.
action_types
.
keys
()),
value
=
"Hinzufügen"
,
description
=
'Modus'
,
disabled
=
True
))
self
.
w_point_type
=
interactive
(
self
.
update_mode
,
mode
=
widgets
.
Dropdown
(
options
=
list
(
self
.
mode_types
.
keys
()),
value
=
"Polstelle"
,
description
=
'Typ'
,
disabled
=
True
))
self
.
w_amp_type
=
interactive
(
self
.
update_amp
,
H0
=
widgets
.
IntSlider
(
min
=
1
,
max
=
10
,
step
=
1
,
value
=
1
),
description
=
"H0"
)
self
.
w_no_of_poles
=
interactive
(
self
.
update_no_of_poles
,
P
=
widgets
.
IntSlider
(
min
=
1
,
max
=
7
,
step
=
1
,
value
=
1
),
description
=
"P"
)
self
.
VBox_AMP
=
VBox
([
self
.
w_filter_type
,
self
.
w_amp_type
])
# vertical box for displaying H0
self
.
VBox_Butter
=
VBox
([
self
.
w_filter_type
,
self
.
w_no_of_poles
])
# vertical box for displaying no. of poles (only for butterworth)
self
.
VBox_mode_type
=
VBox
([
self
.
w_action_type
,
self
.
w_point_type
])
# vertical box action type and point type
self
.
w_hbox
=
HBox
([
self
.
VBox_AMP
,
self
.
VBox_mode_type
])
self
.
w_hbox
=
HBox
([
VBox
([
self
.
w_filter_type
,
self
.
w_amp_type
]),
VBox
([
self
.
w_action_type
,
self
.
w_point_type
])])
display
(
self
.
w_hbox
)
def
find_closest_point
(
self
,
p
,
mode
=
'n'
):
...
...
@@ -307,6 +314,11 @@ class pzPlot():
self
.
update_plot
()
def
update_no_of_poles
(
self
,
P
):
self
.
P
=
P
if
self
.
w_filter_type
.
kwargs
[
'filtr'
]
==
'Butterworth'
:
# skip execution on startup
self
.
update_filter
(
'Butterworth'
)
def
update_filter
(
self
,
filtr
):
self
.
filter
=
self
.
filter_types
[
filtr
]
...
...
@@ -314,17 +326,23 @@ class pzPlot():
ord_poles_butr
=
np
.
array
([])
# calculate butterworth poles and orders
if
filtr
==
'Butterworth'
:
# TODO - Filtergrad und -grenzfrequenz anpassen
filtergrad
=
2
filtergrenzfrequenz
=
1
# TODO - self.H0 je nach Filtergrad und -grenzfrequenz ändern
if
filtr
==
'Butterworth'
:
# show slider for no of poles (filtergrad)
self
.
w_hbox
.
children
=
[
self
.
VBox_Butter
,
self
.
VBox_mode_type
]
filtergrad
=
self
.
P
filtergrenzfrequenz
=
1
# omega_g = 1
tmp
=
(
np
.
linspace
(
0
,
filtergrad
-
1
,
num
=
filtergrad
)
+
0.5
)
/
filtergrad
*
np
.
pi
+
np
.
pi
/
2
tmp
=
tmp
[
np
.
where
(
tmp
<=
np
.
pi
)[
0
]]
poles_butr
=
np
.
array
(
filtergrenzfrequenz
*
np
.
exp
(
1j
*
tmp
))
ord_poles_butr
=
np
.
array
(
np
.
ones
(
poles_butr
.
shape
),
dtype
=
int
)
else
:
# show slider for H0
self
.
w_hbox
.
children
=
[
self
.
VBox_AMP
,
self
.
VBox_mode_type
]
# clear plot
def
clear_all_points
():
tmp
=
list
(
self
.
pp
)
+
list
(
self
.
pz
)
...
...
Write
Preview
Supports
Markdown
0%
Try again
or
attach a new file
.
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment