Numpy / scipy: creating one series converges to another after a while

I have a series of rows in the pandas data frame representing the speeds observed annually.

For the experiment, I want some of these series to converge to one of the coefficients of another series for the last year observed.

For example, let's say that I have this data, and I decided that column a is a significant goal for column b for the asymptotic approach, for example, a ten-year period with small, even dimensional, increments (or decrease; this is really important.

I could, of course, do this in a loop, but I was wondering if there is a more general numpy or scipy vector way to make one series another asymptotically off the shelf.

 rate ab year 2006 0.393620 0.260998 2007 0.408620 0.260527 2008 0.396732 0.257396 2009 0.418029 0.249123 2010 0.414246 0.253526 2011 0.415873 0.256586 2012 0.414616 0.253865 2013 0.408332 0.257504 2014 0.401821 0.259208 
+5
source share
2 answers

Generally speaking, you would apply an “attenuation function” over a certain range.

For example, consider the following figure:

enter image description here

Here we have two original datasets. We subtract two, multiply the difference by the attenuation function shown in the third row, and then add the result back to the first curve. This will lead to the appearance of a new series, which is the source data to the left of the gray area, a mixture of two inside the gray area and data from another curve to the right of the gray area.

As an example:

 import numpy as np import matplotlib.pyplot as plt # Generate some interesting random data np.random.seed(1) series1 = np.random.normal(0, 1, 1000).cumsum() + 20 series2 = np.random.normal(0, 1, 1000).cumsum() # Our x-coordinates index = np.arange(series1.size) # Boundaries of the gray "easing region" i0, i1 = 300, 700 # In this case, I've chosen a sinusoidal easing function... x = np.pi * (index - i0) / (i1 - i0) easing = 0.5 * np.cos(x) + 0.5 # To the left of the gray region, easing should be 1 (all series2) easing[index < i0] = 1 # To the right, it should be 0 (all series1) easing[index >= i1] = 0 # Now let calculate the new series that will slowly approach the first # We'll operate on the difference and then add series1 back in diff = series2 - series1 series3 = easing * diff + series1 

Also, if you're curious about the plot above, here's how it is generated:

 fig, axes = plt.subplots(nrows=4, sharex=True) axes[0].plot(series1, color='lightblue', lw=2) axes[0].plot(series2, color='salmon', lw=1.5) axes[0].set(ylabel='Original Series') axes[1].plot(diff, color='gray') axes[1].set(ylabel='Difference') axes[2].plot(easing, color='black', lw=2) axes[2].margins(y=0.1) axes[2].set(ylabel='Easing') axes[3].plot(series1, color='lightblue', lw=2) axes[3].plot(series3, color='salmon', ls='--', lw=2, dashes=(12,20)) axes[3].set(ylabel='Modified Series') for ax in axes: ax.locator_params(axis='y', nbins=4) for ax in axes[-2:]: ax.axvspan(i0, i1, color='0.8', alpha=0.5) plt.show() 
+5
source

Ok, so this is just the procedure described in comment in code form, assuming a and b are your two numpy arrays:

 b += (a[-1]-b[-1])/len(b)*numpy.arange(1,len(b)+1) 

(a[-1]-b[-1])/len(b) is one “piece”, and another one is added to each “iteration” (year) by multiplying by the numpy.arange() array. I tried several plots, and it doesn’t look very good unless you pick it up, but that’s what you asked for.

An example of how it looks

+2
source

Source: https://habr.com/ru/post/1237600/


All Articles