{
 "cells": [
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "This is a notebook to whiten signal genreated from \"h_m16_L0.18_l2m2_r300.dat\"."
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 1,
   "metadata": {},
   "outputs": [],
   "source": [
    "import json\n",
    "import numpy as np\n",
    "import matplotlib.pyplot as plt"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 2,
   "metadata": {},
   "outputs": [],
   "source": [
    "with open('0.json','r') as f1:\n",
    "        waveform = json.load(f1)\n",
    "        \n",
    "        #extract time series at V1,L1,and H1 from waveform file.\n",
    "        data_V1 = waveform['data']['V1']\n",
    "        data_L1 = waveform['data']['L1']\n",
    "        data_H1 = waveform['data']['H1']\n",
    "        times_V1 = waveform['times']['V1']\n",
    "        times_L1 = waveform['times']['L1']\n",
    "        times_H1 = waveform['times']['H1']\n",
    "        epoch = waveform['epoch']\n",
    "\n",
    "        \n",
    "sample_rate = 256\n",
    "dt=1./sample_rate"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 3,
   "metadata": {
    "scrolled": false
   },
   "outputs": [
    {
     "data": {
      "text/plain": [
       "[<matplotlib.lines.Line2D at 0x7f6b3ec92860>]"
      ]
     },
     "execution_count": 3,
     "metadata": {},
     "output_type": "execute_result"
    },
    {
     "data": {
      "image/png": "[encoded data, 14980 characters]\n",
      "text/plain": [
       "<Figure size 432x288 with 1 Axes>"
      ]
     },
     "metadata": {
      "needs_background": "light"
     },
     "output_type": "display_data"
    }
   ],
   "source": [
    "\n",
    "# Plot the waveform of L1.\n",
    "plt.title('Original signal')\n",
    "plt.xlabel('Time (s) since '+str(epoch))\n",
    "plt.ylabel('Strain')\n",
    "plt.plot(times_L1,data_L1)"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 4,
   "metadata": {},
   "outputs": [],
   "source": [
    "\n",
    "# Load ASD file of L1.\n",
    "filename = './bilby_gw_detector_noise_curves_aLIGO_ZERO_DET_high_P_asd.txt'\n",
    "freq = []\n",
    "asd = []\n",
    "with open(filename, 'r') as f1:\n",
    "    while True:\n",
    "        lines = f1.readline() \n",
    "        if not lines:\n",
    "            break\n",
    "            pass\n",
    "        freq_tmp, asd_tmp = [float(i) for i in lines.split()] \n",
    "        freq.append(freq_tmp)  \n",
    "        asd.append(asd_tmp)\n",
    "        pass\n",
    "        \n",
    "    # Transfer data format from list to array.\n",
    "    freq = np.array(freq) \n",
    "    asd = np.array(asd)\n",
    "    pass"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 5,
   "metadata": {},
   "outputs": [],
   "source": [
    "def whiten_signal(signal, asd):\n",
    "    \n",
    "    signal_rfft = np.fft.rfft(signal)\n",
    "\n",
    "    whitened_signal_rfft = signal_rfft / asd\n",
    "    whitened_signal = np.fft.irfft(whitened_signal_rfft, n=Nt)\n",
    "    return whitened_signal"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 6,
   "metadata": {},
   "outputs": [
    {
     "data": {
      "image/png": "[encoded data, 14440 characters]\n",
      "text/plain": [
       "<Figure size 432x288 with 1 Axes>"
      ]
     },
     "metadata": {
      "needs_background": "light"
     },
     "output_type": "display_data"
    }
   ],
   "source": [
    "# Interpolate asd data linearly.\n",
    "\n",
    "\n",
    "Nt = len(data_L1)\n",
    "freq_rfft = np.fft.rfftfreq(Nt, dt)\n",
    "\n",
    "asd_interp = np.interp(freq_rfft, freq, asd)  \n",
    "\n",
    "plt.loglog(freq, asd,'-o',label='L1 ASD')\n",
    "plt.loglog(freq_rfft, asd_interp, 'x',label='Interpolation')\n",
    "\n",
    "plt.grid('on')\n",
    "plt.ylabel('ASD (strain/rtHz)')\n",
    "plt.xlabel('Freq (Hz)')\n",
    "plt.legend(loc='upper center')\n",
    "\n",
    "# The frequency range is set here, which comes from the calculation of the LIGO detection range. \n",
    "# The limit of the seismic isolation systems designed by aLIGO is 10Hz, which is actually not good for low frequency noise below 20Hz.\n",
    "# According to Nyquist–Shannon sampling theorem, for half of the sampling rate(128Hz) and above,the signal is meaningless.\n",
    "f_min = 20.\n",
    "f_max = 128. \n",
    "plt.axis([f_min, f_max, 1e-24, 1e-19])\n",
    "plt.show()\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 7,
   "metadata": {},
   "outputs": [
    {
     "data": {
      "text/plain": [
       "<matplotlib.legend.Legend at 0x7f6b0e741518>"
      ]
     },
     "execution_count": 7,
     "metadata": {},
     "output_type": "execute_result"
    },
    {
     "data": {
      "image/png": "[encoded data, 16580 characters]\n",
      "text/plain": [
       "<Figure size 432x288 with 1 Axes>"
      ]
     },
     "metadata": {
      "needs_background": "light"
     },
     "output_type": "display_data"
    }
   ],
   "source": [
    "# This step is not necessary. Just to show a potential issue: interpolation of ASD has some points out of the curve in left side,\n",
    "# I am not sure if this has a big impact on the calculation of the whitening process.\n",
    "\n",
    "plt.loglog(freq, asd,'-o',label='L1 ASD')\n",
    "plt.loglog(freq_rfft, asd_interp, 'x',label='Interpolation')\n",
    "\n",
    "plt.grid('on')\n",
    "plt.ylabel('ASD (strain/rtHz)')\n",
    "plt.xlabel('Freq (Hz)')\n",
    "plt.legend(loc='upper center')\n",
    "\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 8,
   "metadata": {},
   "outputs": [],
   "source": [
    "whitened_signal_L1 = whiten_signal(data_L1,asd_interp)"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 9,
   "metadata": {
    "scrolled": true
   },
   "outputs": [
    {
     "data": {
      "text/plain": [
       "Text(0, 0.5, 'Strain')"
      ]
     },
     "execution_count": 9,
     "metadata": {},
     "output_type": "execute_result"
    },
    {
     "data": {
      "image/png": "[encoded data, 14080 characters]\n",
      "text/plain": [
       "<Figure size 432x288 with 1 Axes>"
      ]
     },
     "metadata": {
      "needs_background": "light"
     },
     "output_type": "display_data"
    }
   ],
   "source": [
    "plt.plot(times_L1,whitened_signal_L1)\n",
    "plt.title('Whitened signal')\n",
    "plt.xlabel('Time (s) since '+str(epoch))\n",
    "plt.ylabel('Strain')"
   ]
  }
 ],
 "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.8"
  }
 },
 "nbformat": 4,
 "nbformat_minor": 2
}
