2016-09-02 13 views
0

Я просто сражаюсь с модуляцией волны синуса. У меня есть частота (из посыльных данных - меняется во времени), и теперь мне нужно построить синусовую волну с соответствующей частотой.получил частоту, нужен график синусовой волны в питоне

real data and sinus

Синяя линия просто точки на графике реальных данных и зеленый, что я сделал до сих пор, но это не corespond с реальными данными на всех.

Код для построения греховных волн является дном:

def plotmodulsin(): 
    n = 530 
    f1, f2 = 16, 50 # frequency 

    t = linspace(6.94,8.2,530) 
    dt = t[1] - t[0] # needed for integration 
    print t[1] 
    print t[0] 
    f_inst = logspace(log10(f1), log10(f2), n) 
    phi = 2 * pi * cumsum(f_inst) * dt # integrate to get phase 
    pylab.plot(t, 5*sin(phi)) 

Amplitude вектор:

[2,64, -2,64, 6,14, -6,14, 9,56, -9,56, 12,57, -12,57, 15,55, -15,55, 18,04, -18,04, 21,17, -21,17, 23,34, -23,34, 25,86, -25,86, 28,03, -28,03, 30,49, -30,49, 33,28, -33,28, 35,36, -35,36, 36,47, -36,47, 38,86, -38,86, 41,49, -41,49, 42,91, -42,91, 44,41, -44,41, 45,98, -45,98, 47,63, -47,63, 47,63, -47,63, 51,23, -51,23, 51,23, -51,23, 53,18, -53,18, 55,24, -55,24, 55,24, -55,24, 55,24, -55,24, 57,43, -57,43, 57,43, -57 , 43,75, 59,75, -59,75, 59,75, -59,75, 59,75, -59,75, 59,75, -59,75, 62,22, -62.22, 59.75, -59.75, 62.22, -62.22, 62.22, -62.22, 59.75, -59.75, 62.22, -62.22, 62.22, -62.22, 62.22, -62.22, 59.75, -59.75, 62.22, -62.22, 59.75, -59,75, 62,22, -62,22, 59,75, -59,75, 59,75]

Время вектор для реальных данных:

[6,954, 6,985, 7,016, 7,041, 7,066, 7,088, 7,11, 7,13, 7.149, 7.167, 7.186, 7.202, 7.219, 7.235, 7.251, 7.266, 7.282, 7.296, 7.311, 7.325, 7.339, 7.352, 7.366, 7.379, 7.392, 7.404, 7.417, 7.43, 7.442, 7.454, 7.466, 7.478, 7.49, 7,501, 7,513, 7,524, 7,536, 7,547, 7,558, 7.569, 7.58, 7.591, 7.602, 7.613, 7.624, 7.634, 7.645, 7.655, 7.666, 7.676, 7.686, 7.697, 7.707, 7.717, 7.728, 7.738, 7.748, 7.758, 7.768, 7.778, 7.788, 7.798, 7.808, 7.818, 7.828, 7.838, 7.848, 7.858, 7.868, 7.877, 7.887, 7.897, 7.907, 7.917, 7.927, 7.937, 7.946, 7.956, 7.966, 7.976, 7.986, 7.996, 8.006, 8.016, 8.026, 8.035, 8.045, 8.055, 8.065, 8,075, 8,084, 8,094, 8,104, 8,114, 8,124, 8,134, 8,144, 8,154, 8,164, 8,174, 8,184, 8,194, 8,20]

Поэтому мне нужно генерировать синус с постоянной амплитудой и следующей частотой:

[10,5, 16,03, 20,0, 22,94, 25,51, 27,47, 29,76, 31,25, 32,89, 34,25, 35,71, 37,31, 38,46, 39,06, 40,32, 41,67, 42,37, 4 3,1, 43,86, 44,64, 44,64, 46,3, 46,3, 47,17, 48,08, 48,08, 48,08, 49,02, 49,02, 50,0, 50,0, 50,0, 50,0]

+0

Вы построить синус с постоянной амплитудой (5). Таким образом, вы не можете ожидать, что он будет соответствовать вашим данным, имеющим амплитуду, которая, кажется, более или менее линейно возрастает, пока не достигнет 60. Но без формы ваших данных и любой информации о том, что она представляет, нельзя реально решить, как правильно ваши данные. Самое лучшее, что можно сделать, это заговорить что-то, что качественно выглядит похоже ... – jotasi

+0

Теперь мне нужно сопоставить данные с их частотой. Амплитуду можно сделать в следующем шаге. Вот почему я умножился с постоянным числом. –

+0

Я добавил свои векторы, если кто-то может с этим справиться? –

ответ

0

Вы можете попытаться соответствовать вам работать с чем-то или синус- на самом деле косинус-подобный, путем извлечения оценок частоты и амплитуды из ваших данных. Если я правильно понял вас, ваши данные будут максимальными и минимальными, и вы хотите иметь тригонометрическую функцию, которая напоминает это. Если ваши данные сохраняются в двух массивах time и value, оценки амплитуды просто задаются np.abs(value). Частоты задаются как обратные в два раза разность во времени между максимумом и минимумом. freq = 0.5/(time[1:]-time[:-1]) дает вам частотные оценки для средних точек каждого временного интервала. Соответствующие времена приводятся, таким образом, как freqTimes = (time[1:]+time[:-1])/2..

Чтобы получить более плавную кривую, вы можете теперь интерполировать эти значения амплитуды и частоты, чтобы получить оценки для значений между ними. Очень простой способ сделать это - использовать np.interp, который будет выполнять простую линейную интерполяцию. Вам нужно будет указать, в какие моменты времени интерполировать. Мы построим массив для этого, а затем интерполировать по:

n = 10000 
timesToInterpolate = np.linspace(time[0], time[-1], n, endpoint=True) 
freqInterpolated = np.interp(timesToInterpolate, freqTimes, freq) 
amplInterpolated = np.interp(timesToInterpolate, time, np.abs(value)) 

Теперь вы можете сделать интеграцию, что вы уже в вашем примере, выполнив:

phi = (2*np.pi*np.cumsum(freqInterpolated) 
     *(timesToInterpolate[1]-timesToInterpolate[0])) 

И теперь вы можете построить. Таким образом, положить все это вместе дает:

import numpy as np 
import matplotlib.pyplot as plt 

time = np.array([6.954, 6.985, 7.016, 7.041, 7.066, 7.088, 7.11, 7.13]) #... 
value = np.array([2.64, -2.64, 6.14, -6.14, 9.56, -9.56, 12.57, -12.57]) #... 

freq = 0.5/(time[1:]-time[:-1]) 
freqTimes = (time[1:]+time[:-1])/2. 

n = 10000 
timesToInterpolate = np.linspace(time[0], time[-1], n, endpoint=True) 
freqInterpolated = np.interp(timesToInterpolate, freqTimes, freq) 
amplInterpolated = np.interp(timesToInterpolate, time, np.abs(value)) 

phi = (2*np.pi*np.cumsum(freqInterpolated) 
     *(timesToInterpolate[1]-timesToInterpolate[0])) 

plt.plot(time, value) 
plt.plot(timesToInterpolate, amplInterpolated*np.cos(phi)) #or np.sin(phi+np.pi/2) 
plt.show() 

Результат выглядит следующим образом (если включить полные массивы):

enter image description here

+0

ничего себе ... спасибо ... это замечательно: D –