% matplotlib inline
from IPython.display import display
import numpy as np
import matplotlib.pyplot as plt
On considère la superposition de 2 OPPHs de pulsations voisines $\omega_{1}$ et $\omega_{2}$ et de même amplitude $u_{0}$ donnée par: $$u(x,t)=u_{0}\left[\cos(k_{1}x-\omega_{1}t)+\cos(k_{2}x-\omega_{2}t)\right] $$ où $k_{1}$ et $k_{2}$ sont respectivement reliés à $\omega_{1}$ et $\omega_{2}$ par la relation de dispersion du milieu.
Dans le cadre ci-dessous, on définit une fonction def OPPH(x,t,w,k)
qui renvoie la valeur de l'onde $\cos(kx-\omega t)$ ainsi que la fonction def k(w)
qui est la relation de dispersion du milieu considéré.
def OPPH(x,t,w,k):
return np.cos(k*x-w*t)
def k(w):
return w/3
On peut réécrire l'expression précédente sous la forme : $$ u(x,t)=2u_{0}cos\left(\cfrac{k_{1}+k_{2}}{2}x-\cfrac{\omega_{1}+\omega_{2}}{2}t\right)cos\left(\cfrac{k_{1}-k_{2}}{2}x-\cfrac{\omega_{1}-\omega_{2}}{2}t\right) $$ Et en posant : $\delta k=\cfrac{k_{1}-k_{2}}{2}$, $k_{m}=\cfrac{k_{1}+k_{2}}{2}$, $\delta\omega=\cfrac{\omega_{1}-\omega_{2}}{2}$ et $\omega_{m}=\cfrac{\omega_{1}+\omega_{2}}{2}$, on obtient : $$ u(x,t)=2u_{0}\underset{\mathrm{onde\, moyenne}}{\underbrace{cos\left(k_{m}x-\omega_{m}t\right)}}\underset{\mathrm{enveloppe}}{\underbrace{cos\left(\delta kx-\delta\omega t\right)}} $$ La superposition des deux OPPH s'interprète comme le produit de deux ondes:
une onde moyenne correspondant à une OPPH de pulsation $\omega_{m}$ élevée et se déplaçant à la vitesse $v_{\varphi}=\cfrac{\omega_{m}}{k_{m}}$.
une onde enveloppe correspondant à une OPPH de pulsation $\delta\omega$ faible et se déplaçant à la vitesse $v_{g}=\cfrac{\delta\omega}{\delta k}$. On a $T_{m}=\cfrac{2\pi}{\omega_{m}}\ll T_e=\cfrac{2\pi}{\delta\omega}$
Dans le cadre ci-dessous, tracer la fonction u(x,t) de deux manières:
On représentera $u(x,t)$ sur l'intervalle $x\in\left[-4;4\right]$ à l'instant $t=0$ en choisissant $u_0=2$, $\omega_1=80$ et $\omega_2=84$.
x=np.linspace(-4,4,1e3)
w1,w2,t=80,84,0
plt.plot(x,2*(OPPH(x,t,w1,k(w1))+OPPH(x,t,w2,k(w2))),'b-')
wm=(w1+w2)/2
km=(k(w1)+k(w2))/2
we=np.abs(w2-w1)/2
ke=np.abs(k(w2)-k(w1))/2
plt.plot(x,4*(OPPH(x,t,wm,km)*OPPH(x,t,we,ke)),'r-')
[<matplotlib.lines.Line2D at 0xc1ef0b8>]
Commenter l'allure du signal obtenu.
Sur l'écriture de $u(x,t)$ trouvée précédemment, identifier un terme d'enveloppe et un terme de pulsation moyenne.
On note $\Delta T$ la taille du motif, c'est-à-dire la demi-période de l'enveloppe. Que vaut le produit $\Delta T\times \left(\omega_2-\omega_1\right)$?
La période de l'enveloppe est $T_e=\frac{2\pi}{\omega_e}=\frac{4\pi}{\omega_2-\omega_1}$ On obtient alors: $$ \Delta T\times \left(\omega_2-\omega_1\right)=2\pi $$
Les programmes suivants permettent de tracer les spectres et les signaux temporels associés à une superposition de plusieurs OPPHs de pulsations proches et en nombre de plus en plus important.
Vous pouvez tracer une somme d'OPPH de même amplitude, d'amplitude qui varie de façon triangulaire ou normale. Observer comment varie l'étalement temporel des signaux et celui des spectres.
import numpy as np
import matplotlib.pyplot as plt
import time
x = np.linspace(-400,400,5e3)
y=np.zeros(len(x))
def f(x,a,b,c):
return a*np.cos(b*x+c)
def spectr_carree(ax,wmin,wmax,Ntot,N):
""" trace le spectre carree compris entre wmin,wmax et renvoie
le nbre N de raies sur un découpage total de Ntot"""
x=np.array([wmin-(wmax-wmin)/4,wmin,wmin,wmax,wmax,wmax+(wmax-wmin)/4])
y=np.array([0,0,1,1,0,0])
ax.plot(x,y,'g--')
ax.set_ylim(-0.1,1.2)
Tw=np.linspace(wmin,wmax,Ntot)
Tw=np.add(Tw,+(wmax-wmin)/10/Ntot) # décalage pour plot de l'histogramme
n,bins,patches=ax.hist(Tw[(Ntot-N)//2:(Ntot-N)//2+N],bins=Ntot,range=[wmin,wmax+(wmax-wmin)/(Ntot-1)],rwidth=0.5,align='left')
#ax.show()
#print('bins',bins)
#print('Tw',Tw)
return n,bins,x,y
def spectr_tri(ax,wmin,wmax,Ntot,N):
""" trace le spectre triangulaire compris entre wmin,wmax et renvoie
le nbre N de raies sur un découpage total de Ntot"""
x=np.array([wmin-(wmax-wmin)/4,wmin,(wmin+wmax)/2,wmax,wmax+(wmax-wmin)/4])
y=np.array([0,0,1,0,0])
ax.plot(x,y,'g--')
ax.set_ylim(-0.1,1.2)
Tw=np.linspace(wmin,wmax,Ntot)
Ta=np.zeros(len(Tw))
for i in range(len(Tw)):
if Tw[i]<=(wmin+wmax)/2 and i>=(Ntot-N)//2:
Ta[i]=2/(wmax-wmin)*(Tw[i]-wmin)
elif Tw[i]>(wmin+wmax)/2 and i<(Ntot-N)//2+N:
Ta[i]=2/(wmax-wmin)*(wmax-Tw[i])
Tw=np.add(Tw,+(wmax-wmin)/10/Ntot)# décalage pour plot de l'histogramme
n,bins,patches=ax.hist(Tw,bins=Ntot,range=[wmin,wmax+(wmax-wmin)/(Ntot-1)],weights=Ta,rwidth=0.5,align='left')
#ax.show()
#print('bins',bins)
#print('Tw',Tw)
return n,bins,x,y
def normal(w,w0,dw):
return np.exp(-((w-w0)/dw)**2/2)
def spectr_gauss(ax,wmin,wmax,Ntot,N):
x=np.linspace(wmin-(wmax-wmin)/4,wmax+(wmax-wmin)/4,500)
y=normal(x,(wmin+wmax)/2,(wmax-wmin)/5)
ax.plot(x,y,'g--')
ax.set_ylim(-0.1,1.2)
Tw=np.linspace(wmin,wmax,Ntot)
Ta=np.zeros(len(Tw))
for i in range(len(Tw)):
if i>=(Ntot-N)//2 and i<(Ntot-N)//2+N:
Ta[i]=normal(Tw[i],(wmin+wmax)/2,(wmax-wmin)/5)
Tw=np.add(Tw,+(wmax-wmin)/10/Ntot)# décalage pour plot de l'histogramme
n,bins,patches=ax.hist(Tw,bins=Ntot,range=[wmin,wmax+(wmax-wmin)/(Ntot-1)],weights=Ta,rwidth=0.5,align='left')
#ax.show()
#print('bins',bins)
#print('Tw',Tw)
return n,bins,x,y
def plot_temps(ax,tmax,TT):
#plt.clf()
t=np.linspace(-tmax,tmax,5000)
y=np.array([0]*len(t))
for i in range(len(TT[0])):
y=np.add(y,f(t,TT[0][i],TT[1][i],0))
ax.plot(t,y)
#plt.show()
return t,y
#phase=[random() for i in range(-10,10)]
#for i in range(-10,10):
# plt.clf()
# y=np.add(y,f(x,1,(50+i)/50,phase[i]))
# plt.plot(x,y)
# plt.show()
#spectr_carree(8,12,25,5)
#set figure
fig=plt.figure(num=0,figsize=(14,4))
ax1=plt.subplot2grid((1,3), (0,0))
ax2=plt.subplot2grid((1,3), (0,1), colspan=2)
ax1.set_ylim(-0.1,1.2)
for i in [1,3,5,11,15]:
fig.get_axes()[0].cla()
fig.get_axes()[1].cla()
TT= spectr_carree(ax1,8,12,15,i)
plot_temps(ax2,20,TT)
plt.tight_layout()
display(fig)
#plt.waitforbuttonpress(timeout=1)
#set figure
fig=plt.figure(num=0,figsize=(14,4))
ax1=plt.subplot2grid((1,3), (0,0))
ax2=plt.subplot2grid((1,3), (0,1), colspan=2)
ax1.set_ylim(-0.1,1.2)
for i in [1,3,5,11,15]:
fig.get_axes()[0].cla()
fig.get_axes()[1].cla()
TT= spectr_tri(ax1,8,12,15,i)
plot_temps(ax2,20,TT)
plt.tight_layout()
display(fig)
#plt.waitforbuttonpress(timeout=1)
#set figure
fig=plt.figure(num=0,figsize=(14,4))
ax1=plt.subplot2grid((1,3), (0,0))
ax2=plt.subplot2grid((1,3), (0,1), colspan=2)
ax1.set_ylim(-0.1,1.2)
for i in [1,3,5,11,15]:
fig.get_axes()[0].cla()
fig.get_axes()[1].cla()
TT= spectr_gauss(ax1,8,12,15,i)
plot_temps(ax2,20,TT)
plt.tight_layout()
display(fig)
#plt.waitforbuttonpress(timeout=1)
On voit que plus le nombre d'OPPHs est important, plus l'onde devient localisée et ressemble à un "paquet d'onde".
On peut également remarquer que plus l'écart $\Delta\omega$ entre les pulsations extrêmes du signal est important, plus l'extension temporelle $\Delta t$ du signal est faible.
class PDF(object):
def __init__(self, pdf, size=(200,200)):
self.pdf = pdf
self.size = size
def _repr_html_(self):
return '<iframe src={0} width={1[0]} height={1[1]}></iframe>'.format(self.pdf, self.size)
def _repr_latex_(self):
return r'\includegraphics[width=1.0\textwidth]{{{0}}}'.format(self.pdf)
PDF('5_Paquet_ondes.pdf',size=(1024,500))