Example #1
0
def LSP(x,
        y,
        dy,
        fVal=[0, 1, 5, 1],
        norm='standard',
        figout=None,
        label=None,
        freq_set=None):
    '''
    周期分析
    https://docs.astropy.org/en/stable/timeseries/lombscargle.html#periodogram-algorithms

    参数:
    x,y,dy: arrays
        时间,星等,误差
    figout: str
        图片保存名称
    fVal: list
        minimum_frequency,maximum_frequency,samples_per_peak(default 5),nterms(default 1)
    
    return:
        frequency, power, residuals, x_range, y_fit, theta
        if nterms=1:
            theta=[off_set,amplitude,phi,best_frequency]
            y=off_set+amplitude*np.sin(2*np.pi*best_frequency*x+phi)
    '''
    import numpy as np
    import matplotlib.pyplot as plt
    from astropy.timeseries import LombScargle

    if not isinstance(x, np.ndarray):
        x = np.array(x)
        y = np.array(y)
        dy = np.array(dy)
    fVal[0] = 10**-5 if fVal[0] == 0 else fVal[0]
    ls = LombScargle(x, y, dy, nterms=fVal[-1], normalization=norm)
    frequency, power = ls.autopower(minimum_frequency=fVal[0],
                                    maximum_frequency=fVal[1],
                                    samples_per_peak=fVal[2])

    fig, ax = plt.subplots(3)
    fig.set_size_inches(20, 27)
    #ax[0].invert_yaxis();ax[2].invert_yaxis();
    ax[0].grid()
    ax[1].grid()
    ax[2].grid()
    ax[0].errorbar(x, y, dy, fmt='bo-', label=label)
    ax[1].set_xlim((frequency[0], frequency[-1]))
    ax[1].plot(frequency, power, 'b-')
    ax11 = ax[1].twiny()
    ax11.set_xlim(ax[1].get_xlim())
    x_side = np.linspace(0.001 + frequency[0], frequency[-1], 10)
    x_side_var = np.round(24 * 60 / x_side, 2)
    plt.xticks(x_side, x_side_var, rotation=0)

    best_frequency = frequency[np.argmax(power)]
    peak_power = power.max()
    ax[1].plot(best_frequency, peak_power, 'ro')
    ax[1].legend([
        'spectrum distribution',
        'peak frequency ' + str(round(best_frequency, 4)) + 'c/d is period ' +
        str(round(24 / best_frequency, 4)) + 'h'
    ],
                 loc='upper right',
                 fontsize=15,
                 frameon=False)
    if fVal[-1] == 1:
        for cutoff in ls.false_alarm_level([0.1, 0.05, 0.01]):
            ax[1].axhline(cutoff, color='black', linestyle='dotted')
    if freq_set != None: best_frequency = freq_set
    phase = (x * best_frequency) % 1
    y_fit = ls.model(x, best_frequency)
    residuals = y - y_fit
    y_fit = y_fit[np.argsort(phase)]
    ax[2].plot(np.sort(phase), y_fit, 'r-', linewidth=5)
    ax[2].errorbar(phase, y, dy, fmt='b.', alpha=1)
    ax[2].legend(
        ['best fitted curve is ' + str(best_frequency), 'folded data'],
        loc='upper right',
        fontsize=15,
        frameon=False)

    x_range = np.linspace(x.min(), x.max(), 100)
    y_fit = ls.model(x_range, best_frequency)
    ax[0].plot(x_range, y_fit, 'r-', label='fitting curve', linewidth=5)
    ax[0].legend(loc='upper right', fontsize=15, frameon=False)

    if figout: plt.savefig(figout, dpi=100)
    plt.show()

    if fVal[-1] == 1:
        print('the false alarm probability for %0.2f (%0.2f min) is %0.2e' %
              (best_frequency, 24 * 60 / best_frequency,
               ls.false_alarm_probability(peak_power, method='davies')))

    theta = ls.model_parameters(best_frequency)
    theta[0] = ls.offset() + theta[0]
    if len(theta) == 3:
        K = (theta[1]**2 + theta[2]**2)**0.5
        phi = np.arcsin(theta[2] / K)
        theta = [theta[0], K, phi, best_frequency]

    return frequency, power, residuals, x_range, y_fit, theta
Example #2
0
import pandas as pd
import numpy as np
import os
import time

# test
x = np.arange(5)
y = np.random.random(5)
ls = LombScargle(x, y)
freq = 2 / 5
p = ls.model_parameters(freq)
mat = ls.design_matrix(freq)
yp = ls.model(x, freq)
power = ls.power(freq, normalization='psd')
offset = ls.offset()

a = np.fft.fft(y)

yp1 = p[0] + p[1] * np.sin(2 * np.pi * freq * x) + p[2] * np.cos(
    2 * np.pi * freq * x) + ls.offset()

mat
np.sin(2 * np.pi * freq * x)
np.cos(2 * np.pi * freq * x)

yp1 = yp * 0
for f in list(x / 5)[1:]:
    f
    yp1 = yp1 + ls.model(x, f)