{ "cells": [ { "cell_type": "code", "execution_count": null, "metadata": { "autoscroll": "json-false", "ein.tags": [ "worksheet-0" ], "slideshow": { "slide_type": "-" } }, "outputs": [], "source": [ "%pylab inline" ] }, { "cell_type": "markdown", "metadata": { "ein.tags": [ "worksheet-0" ], "slideshow": { "slide_type": "-" } }, "source": [ "# ``TfData`` objects\n", "\n", "A ``TfData`` is a ``MaskedArray`` dedicated to handle Time-Frequency representations obtained from a real signal. As such, it has two attributes ``tf_params`` and ``signal_params``, giving respectively the parameters of the STFT used to obtain the representation, and the parameters of the real signali, as well as dedicated methods to facilitate the manipulation of time-frequency data." ] }, { "cell_type": "code", "execution_count": null, "metadata": { "autoscroll": "json-false", "collapsed": true, "ein.tags": [ "worksheet-0" ], "slideshow": { "slide_type": "-" } }, "outputs": [], "source": [ "from pyteuf import TfData, Stft\n", "import numpy as np\n", "import matplotlib.pyplot as plt\n", "import matplotlib\n", "matplotlib.rcParams['figure.figsize'] = (14, 4)\n", "\n", "# Data parameters\n", "tf_params = {'hop': 32, 'n_bins': 128, 'win_len': 64, 'win_name': 'hanning'}\n", "signal_params = {'len':1024, 'fs':44100}" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "## Example of TF representation of a complex signal, with binary masking" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "As for ``MaskedArray``, ``TfData`` can be initialized from a 2D complex nd-array with or without mask. Parameters ``stft_params`` and ``signal_params`` are explicitly given if available. For a complex signal, coefficients for both negative and positive frequencies are handled and displayed" ] }, { "cell_type": "code", "execution_count": null, "metadata": {}, "outputs": [], "source": [ "# Data ans mask for a complex signal (no symetry in TF)\n", "tf_shape_complex = (tf_params['n_bins'], signal_params['len'] // tf_params['hop'])\n", "mask_complex = np.zeros(tf_shape_complex)\n", "mask_complex[int(0.2*tf_shape_complex[0]):int(0.6*tf_shape_complex[0]), \n", " int(0.25*tf_shape_complex[1]):int(0.7*tf_shape_complex[1])] = True\n", "data_complex = np.random.randn(*tf_shape_complex) + 1j * np.random.randn(*tf_shape_complex)\n", "\n", "# TF data\n", "X = TfData(data=data_complex, mask=mask_complex, tf_params=tf_params, signal_params=signal_params)\n", "\n", "plt.subplot(121)\n", "X.plot_spectrogram()\n", "plt.subplot(122)\n", "X.plot_mask()\n", "print(X)" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "## Example of TF representation of a real signal, with binary masking" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "For a real signal, only the non-negative frequencies area is handled due to Hermitian symetry." ] }, { "cell_type": "code", "execution_count": null, "metadata": {}, "outputs": [], "source": [ "# Data and mask for a real signal (Hermitian symetry in TF)\n", "tf_shape_real = (tf_params['n_bins'] // 2 + 1, signal_params['len'] // tf_params['hop'])\n", "mask_real = np.zeros(tf_shape_real)\n", "mask_real[int(0.2*tf_shape_real[0]):int(0.6*tf_shape_real[0]), \n", " int(0.25*tf_shape_real[1]):int(0.7*tf_shape_real[1])] = True\n", "data_real = np.random.randn(*tf_shape_real) + 1j * np.random.randn(*tf_shape_real)\n", "\n", "# TF data\n", "X = TfData(data=data_real, mask=mask_real, tf_params=tf_params, signal_params=signal_params)\n", "\n", "plt.subplot(121)\n", "X.plot_spectrogram()\n", "plt.subplot(122)\n", "X.plot_mask()\n", "print(X)" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "## Example of TF representation with complex masking" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "With complex masking, two masks are handled: a mask for amplitudes and a mask for phases." ] }, { "cell_type": "code", "execution_count": null, "metadata": {}, "outputs": [], "source": [ "# Data and mask for a real signal (Hermitian symetry in TF)\n", "tf_shape_real = (tf_params['n_bins'] // 2 + 1, signal_params['len'] // tf_params['hop'])\n", "mask_mag = np.zeros(tf_shape_real)\n", "mask_mag[int(0.2*tf_shape_real[0]):int(0.6*tf_shape_real[0]), \n", " int(0.25*tf_shape_real[1]):int(0.7*tf_shape_real[1])] = True\n", "mask_phi = np.zeros(tf_shape_real)\n", "mask_phi[int(0.5*tf_shape_real[0]):int(0.65*tf_shape_real[0]), \n", " int(0.65*tf_shape_real[1]):int(0.75*tf_shape_real[1])] = True\n", "data_real = np.random.randn(*tf_shape_real) + 1j * np.random.randn(*tf_shape_real)\n", "\n", "# TF data\n", "X = TfData(data=data_real,\n", " mask_magnitude=mask_mag, mask_phase=mask_phi,\n", " tf_params=tf_params, signal_params=signal_params)\n", "print(X)" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "One may select one of the masks or a combination of them for display." ] }, { "cell_type": "code", "execution_count": null, "metadata": {}, "outputs": [], "source": [ "for mask_type in ['any', 'all', 'magnitude', 'phase', 'magnitude only', 'phase only']:\n", " plt.figure()\n", " plt.subplot(121)\n", " X.plot_spectrogram(mask_type=mask_type)\n", " plt.title('mask type: {}'.format(mask_type))\n", " plt.subplot(122)\n", " X.plot_mask(mask_type=mask_type)\n", " plt.title('mask type: {}'.format(mask_type))\n" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "Selecting a mask type can also be used to extract the related mask:" ] }, { "cell_type": "code", "execution_count": null, "metadata": {}, "outputs": [], "source": [ "for mask_type in ['any', 'all', 'magnitude', 'phase', 'magnitude only', 'phase only']:\n", " mask = X.get_unknown_mask(mask_type)\n", " print('Ratio of \"{}\" unknown coefficients: {:.1%}'.format(mask_type, np.mean(mask)))\n", " mask = X.get_known_mask(mask_type)\n", " print('Ratio of \"{}\" known coefficients: {:.1%}'.format(mask_type, np.mean(mask)))" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "Other useful properties:" ] }, { "cell_type": "code", "execution_count": null, "metadata": {}, "outputs": [], "source": [ "print('Number of frequencies: {}'.format(X.n_frequencies))\n", "print('Number of frames: {}'.format(X.n_frames))\n", "print('Start time of frames: {}'.format(X.start_times))\n", "print('Center time of frames: {}'.format(X.mid_times))\n", "print('End time of frames: {}'.format(X.end_times))" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "Current operations between two ``TfData`` objects are not recommended since resulting operations on masks are not designed adequately:" ] }, { "cell_type": "code", "execution_count": null, "metadata": { "ein.tags": [ "worksheet-0" ], "slideshow": { "slide_type": "-" } }, "outputs": [], "source": [ "mask1 = np.zeros(tf_shape_real)\n", "mask1[int(0.2*tf_shape_real[0]):int(0.6*tf_shape_real[0]), \n", " int(0.25*tf_shape_real[1]):int(0.7*tf_shape_real[1])] = True\n", "mask2 = np.zeros(tf_shape_real)\n", "mask2[int(0.5*tf_shape_real[0]):int(0.65*tf_shape_real[0]), \n", " int(0.65*tf_shape_real[1]):int(0.75*tf_shape_real[1])] = True\n", "data_real = np.random.randn(*tf_shape_real) + 1j * np.random.randn(*tf_shape_real)\n", "\n", "# TF data\n", "X1 = TfData(data=np.random.randn(*tf_shape_real) + 1j * np.random.randn(*tf_shape_real),\n", " mask=mask1, tf_params=tf_params, signal_params=signal_params)\n", "X2 = TfData(data=np.random.randn(*tf_shape_real) + 1j * np.random.randn(*tf_shape_real),\n", " mask=mask2, tf_params=tf_params, signal_params=signal_params)\n", "\n", "plt.figure()\n", "plt.subplot(121)\n", "X1.plot_spectrogram()\n", "plt.subplot(122)\n", "X2.plot_spectrogram()\n", "\n", "plt.figure()\n", "X3 = X1 + X2\n", "X4 = X1 - X2\n", "plt.subplot(121)\n", "X3.plot_spectrogram()\n", "plt.subplot(122)\n", "X4.plot_spectrogram()\n", "\n", "plt.figure()\n", "X3 = X1 * X2\n", "X4 = X1 / X2\n", "plt.subplot(121)\n", "X3.plot_spectrogram()\n", "plt.subplot(122)\n", "X4.plot_spectrogram()\n", "pass" ] }, { "cell_type": "code", "execution_count": null, "metadata": { "collapsed": true }, "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.6.2" }, "name": "data_structures.ipynb" }, "nbformat": 4, "nbformat_minor": 1 }