Téléchargé 9 fois
Vote des utilisateurs
1
0
Détails
Licence : Non renseignée
Mise en ligne le 1er avril 2021
Plate-formes :
Linux, Mac, Windows
Langue : Français
Référencé dans
Navigation
Simulateur de relativité restreinte
Simulateur de relativité restreinte
Ce script permet de visualiser l'exemple ultra classique illustrant les distorsions du temps et de l'espace en relativité restreinte :
Le wagon en déplacement par rapport à un quai.
Il suffit de lancer ce script et de jouer avec les flèches droite et gauche.
Le second lien de téléchargement semble fonctionner... (à la différence du premier)
Le wagon en déplacement par rapport à un quai.
Il suffit de lancer ce script et de jouer avec les flèches droite et gauche.
Le second lien de téléchargement semble fonctionner... (à la différence du premier)
Salut,
Le téléchargement ne se fait pas. Page blanche après click sur le bouton.
Le téléchargement ne se fait pas. Page blanche après click sur le bouton.
voici le script ici, à copier/coller
Si quelqu'un sait comment rendre le script téléchargeable depuis la page d'origine...
Hadrien
Code : | Sélectionner tout |
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190 191 192 193 194 195 196 197 198 199 200 201 202 203 204 205 206 207 208 209 210 | # encoding:utf8 ''' Simulateur de relativité restreinte ================================================== Ce script permet de visualiser l'exemple ultra classique illustrant les distorsions du temps et de l'espace en relativité restreinte : Le wagon en déplacement par rapport à un quai. Il suffit de lancer ce script et de jouer avec les flèches droite et gauche. On peut voir, sous le wagon, des horloge qui donnent l'heure "locale" à différentes positions. Quelques explications à peu près scientifiques : On commence par définir le référentiel ("immobile") de l’observateur : le quai. Ensuite, dans le le référentiel du wagon qui se déplace à une vitesse V par rapport au quai, on a un point p qui se déplace à la vitesse v, et est à la position x0 quand t = 0. On a donc : position de p dans le référentiel du wagon = x = x0 + vt A un instant T sur le quai, on veut connaître X, la position de p vu depuis le quai. On utilise la transformation de Lorentz t = γ( T - βX/c ) x = γ( X - βcT ) en remplaçant x par x0 + vt : x0 + vt = γ( X - βcT ) On connaît x0, v et T, et on veut X et t. x0 + vγ( T - βX/c ) = γ( X - βcT ) x0 + vγT - vγβX/c = γX - γβcT γX + vγβX/c = x0 + γβcT + vγT X( γ + vβγ/c ) = x0 + γβcT + vγT X = ( x0 + γβcT + vγT ) / ( vβγ/c + γ ) X = ( x0/γ + βcT + vT ) / ( vβ/c + 1 ) X = ( x0/γ + T( v + βc )) / ( vβ/c + 1 ) <-- voici X t = γ( T - βX/c ) <-- et t Dans les formules qui précèdent et le code qui suit, les capitales désignent les coordonnées dans le référentiel du quai, et les minuscules, celles du référentiel en mouvement (le wagon). Les variables "q" désignent des "quasi-quadri-vecteurs", c'est-à-dire, dans ce contexte, une paire (z,t) où z donne les coordonnées spatiales 2D sous forme d'un nombre complexe, et t le temps. Par ailleurs, les variables "c", "b", et "g" contiennent respectivement la vitesses de la lumière dans les unités de mesures choisies, β = le rapport v/c, et γ = le facteur de Lorentz. Hadrien Flammang - nov 2015 ''' def lorentz ( x0,y0,vx,vy,T,c,b,g ): ''' Variante de la transformation de Lorentz qui calcule X,Y,t en fonction de x0,y0,vx,vy,T ''' X = ( x0/g + T*( vx + b*c )) / ( vx*b/c + 1 ) t = g*( T - b*X/c ) Y = y0 + vy*t return X,Y,t #------------------------------------------------------------------- #-- quelques outils génériques ------------------------------------- iterable = lambda obj : hasattr( obj,'__iter__') flatize = lambda obj : sum( map( flatize,obj ),[] ) if iterable( obj ) else [obj] invcomplex = lambda z : complex( z.imag,z.real ) def to_complex ( *z ) : try : return complex( *z ) except : pass try : return complex( *z[0] ) except : return 0 #------------------------------------------------------------------- #-- Les classes des différents objets en mouvement (dans un repère qui sera donné) nope,box,dot,clock,text = range( 5 ) class Object: def __init__(self,type=nope,**param): self.type = type self.pos = to_complex( param.get('pos',0 )) self.size = to_complex( param.get('size',0 )) self.speed = to_complex( param.get('speed',0 )) self.clock = param.get('clock',False ) self.text = param.get('text',None ) self.start = param.get('start',0 ) self.color = param.get('color',0 ) def draw (self,t,trans,drawer): # trans = fonction de transformation : ( x,v,T )-> (X,t) avec x,v,X complexes if self.type == nope : return q0 = trans( self.pos,self.speed,t ) q1 = trans( self.pos+self.size,self.speed,t ) if self.type == box : drawer.box ( q0,q1,self.color ) elif self.type == dot : drawer.dot ( q0,self.color ) elif self.type == text : drawer.text ( q0,self.text,self.color ) elif self.type == clock : drawer.clock( q0,self.color ) if self.clock : drawer.clock( (q0[0]+1j,q0[1]),self.color ) def Nop ( **param ) : return Object() # objet invisible et qui ne fait rien... def Box ( **param ) : return Object( box ,**param ) # rectangle (pour symboliser un wagon) def Dot ( **param ) : return Object( dot ,**param ) # point (pour symboliser un projectile ou un photon) def Text ( **param ) : return Object( text ,**param ) # explication bienvenue qui accompagne un objet def Clock ( **param ) : return Object( clock,**param ) # horloge qui donne le temps propre dans un repère #------------------------------------------------------------------- #-- repère défini par une position et une vitesse ------------------ class Frame: def __init__( self,position,speed,c=1 ): speed = to_complex( speed ) self.onx = speed.imag == 0 self.V = speed self.O = to_complex( position ) self.v = speed.real or speed.imag self.c = c self.b = self.v/c self.g = (1-self.b**2)**-0.5 assert speed.real == 0 or speed.imag == 0 # la vitesse d'un repère ne peut être que horizontale ou verticale def __call__ (self,x0,v,T): # fonction de transformation (ici : celle de Lorentz) O,V,b,c,g = self.O,self.V,self.b,self.c,self.g (x0x,x0y),(vx,vy) = (x0.real,x0.imag),(v.real,v.imag) x0,y0,v,vy = (x0x,x0y,vx,vy) if self.onx else (x0y,x0x,vy,vx) X,Y,t = lorentz( x0,y0,vx,vy,T,self.c,self.b,self.g ) Z = complex( X,Y ) if self.onx else complex( Y,X ) return self.O+Z,t #------------------------------------------------------------------- #-- classe d'affichage des objets ---------------------------------- class Drawer : def __init__(self,canvas,origin=0,scale=1): # canvas doit se comporter comme un Tkinter.canvas self.colors = ('#000','#00b','#080','#c00') self.canvas = canvas self.origin = to_complex(origin) self.scale = to_complex(scale) self.font = ('Arial narrow',int(scale*0.8)) def _int (self,*qpoints ): qpoints = ( q[0]*self.scale+self.origin for q in qpoints ) qpoints = flatize( (q.real,q.imag) for q in qpoints ) return map( int,qpoints ) def box (self,q0,q1,color ): v = self._int( q0,q1 ) self.canvas.create_rectangle( *v,width=2,outline=self.colors[color] ) def dot (self,q,color ): r,(x,y) = 2,self._int( q ) self.canvas.create_oval( x-r,y-r,x+r,y+r,outline=self.colors[color],fill=self.colors[color] ) def text (self,q,txt,color ): if not txt : return (x,y) = self._int( q ) self.canvas.create_text( x,y,text=txt,font=self.font,fill=self.colors[color] ) def clock (self,q,color ): t,(x,y) = q[1],self._int( q ) self.canvas.create_text( x,y,text='%.1f'%t,font=self.font,fill=self.colors[color] ) #------------------------------------------------------------------- def relativity ( size,origin,scale,dT,*frames ): def draw ( step = 0 ): root.T += dT*step can.delete('all') can.create_text( size[0]/2,size[1]-10,text='FLÈCHES du temps , ECHAP pour quitter' ) for frame in frames : for obj in frame[1:]: obj.draw( root.T,frame[0],drawer ) import Tkinter root = Tkinter.Tk() root.T = 0 root.geometry('+20+20') root.bind('<Left>' ,lambda e : draw(-1)) root.bind('<Right>' ,lambda e : draw(+1)) root.bind('<space>' ,lambda e : draw(+5)) root.bind('<Escape>',lambda e : root.quit()) can = Tkinter.Canvas( root,width = size[0],height = size[1] ) can.pack() drawer = Drawer( can,origin,scale ) draw() root.mainloop() #------------------------------------------------------------------- #--- démo avec unité de temps = seconde # unité de longueur = seconde-lumière (~300000km) => c = 1 def build_wagon ( pos,speed,nbclock,color,text,vertical_photon=False ): ''' Construit un repère contenant un wagon long de 20sl + 2 photons qui partent de son centre. ''' wsize = 20 frame = Frame( pos*1j,speed,1 ) wagon = Box( pos=-wsize/2+1j,size=wsize+4j,color=color ) spot1 = Dot( pos=3j,speed= 1,clock=True,color=color ) spot2 = Dot( pos=3j,speed=-1,clock=True,color=color ) spotV = (Dot if vertical_photon else Nop)( pos=3j,speed=1j,clock=True,color=color ) name = Text( pos=2j,text=text,color=color ) clocks = tuple(Clock( pos=i+6j,color=color ) for i in xrange( -wsize/2,wsize/2+1,wsize/(nbclock-1))) return (frame,wagon,spot1,spot2,spotV,name)+clocks def demo1 ( scale = 10 ): deck = build_wagon( 0,0 ,3,0,'wagon sur le quai' )+(Box( pos=-100,size=200+8j ),) wagon1 = build_wagon( 9,0.1,5,1,'wagon 10%' ) wagon2 = build_wagon( 16,0.8,5,2,'wagon 80%' ) wagon3 = build_wagon( 23,0.9,5,3,'wagon 90%' ) relativity( (scale*80,scale*35),(scale*20,0),scale,0.1,deck,wagon1,wagon2,wagon3 ) demo1( 20 ) |
Hadrien
Sinon, le deuxième lien de téléchargement semble fonctionner...
Bonjour,
J'ai une erreur à l'exécution
NameError: name 'xrange' is not defined
cordialement
J'ai une erreur à l'exécution
NameError: name 'xrange' is not defined
cordialement
Salut,
Et si tu gommes le 'x' ?
Et si tu gommes le 'x' ?
Pardon !
J'aurais dû préciser : ce script est écrit en python 2.7, et je ne l'ai pas testé sur d'autres versions.
J'aurais dû préciser : ce script est écrit en python 2.7, et je ne l'ai pas testé sur d'autres versions.
Ce code devrait marcher mais je ne sais pas s'il préserve le but premier
Code : | Sélectionner tout |
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190 191 192 193 194 195 196 197 198 199 200 201 202 203 204 205 206 207 208 209 | from tkinter import * # encoding:utf8 ''' Simulateur de relativité restreinte ================================================== Ce script permet de visualiser l'exemple ultra classique illustrant les distorsions du temps et de l'espace en relativité restreinte : Le wagon en déplacement par rapport à un quai. Il suffit de lancer ce script et de jouer avec les flèches droite et gauche. On peut voir, sous le wagon, des horloge qui donnent l'heure "locale" à différentes positions. Quelques explications à peu près scientifiques : On commence par définir le référentiel ("immobile") de l’observateur : le quai. Ensuite, dans le le référentiel du wagon qui se déplace à une vitesse V par rapport au quai, on a un point p qui se déplace à la vitesse v, et est à la position x0 quand t = 0. On a donc : position de p dans le référentiel du wagon = x = x0 + vt A un instant T sur le quai, on veut connaître X, la position de p vu depuis le quai. On utilise la transformation de Lorentz t = γ( T - βX/c ) x = γ( X - βcT ) en remplaçant x par x0 + vt : x0 + vt = γ( X - βcT ) On connaît x0, v et T, et on veut X et t. x0 + vγ( T - βX/c ) = γ( X - βcT ) x0 + vγT - vγβX/c = γX - γβcT γX + vγβX/c = x0 + γβcT + vγT X( γ + vβγ/c ) = x0 + γβcT + vγT X = ( x0 + γβcT + vγT ) / ( vβγ/c + γ ) X = ( x0/γ + βcT + vT ) / ( vβ/c + 1 ) X = ( x0/γ + T( v + βc )) / ( vβ/c + 1 ) <-- voici X t = γ( T - βX/c ) <-- et t Dans les formules qui précèdent et le code qui suit, les capitales désignent les coordonnées dans le référentiel du quai, et les minuscules, celles du référentiel en mouvement (le wagon). Les variables "q" désignent des "quasi-quadri-vecteurs", c'est-à-dire, dans ce contexte, une paire (z,t) où z donne les coordonnées spatiales 2D sous forme d'un nombre complexe, et t le temps. Par ailleurs, les variables "c", "b", et "g" contiennent respectivement la vitesses de la lumière dans les unités de mesures choisies, β = le rapport v/c, et γ = le facteur de Lorentz. Hadrien Flammang - nov 2015 ''' def lorentz ( x0,y0,vx,vy,T,c,b,g ): ''' Variante de la transformation de Lorentz qui calcule X,Y,t en fonction de x0,y0,vx,vy,T ''' X = ( x0/g + T*( vx + b*c )) / ( vx*b/c + 1 ) t = g*( T - b*X/c ) Y = y0 + vy*t return X,Y,t #------------------------------------------------------------------- #-- quelques outils génériques ------------------------------------- iterable = lambda obj : hasattr( obj,'__iter__') flatize = lambda obj : sum( map( flatize,obj ),[] ) if iterable( obj ) else [obj] invcomplex = lambda z : complex( z.imag,z.real ) def to_complex ( *z ) : try : return complex( *z ) except : pass try : return complex( *z[0] ) except : return 0 #------------------------------------------------------------------- #-- Les classes des différents objets en mouvement (dans un repère qui sera donné) nope,box,dot,clock,text = range( 5 ) class Object: def __init__(self,type=nope,**param): self.type = type self.pos = to_complex( param.get('pos',0 )) self.size = to_complex( param.get('size',0 )) self.speed = to_complex( param.get('speed',0 )) self.clock = param.get('clock',False ) self.text = param.get('text',None ) self.start = param.get('start',0 ) self.color = param.get('color',0 ) def draw (self,t,trans,drawer): # trans = fonction de transformation : ( x,v,T )-> (X,t) avec x,v,X complexes if self.type == nope : return q0 = trans( self.pos,self.speed,t ) q1 = trans( self.pos+self.size,self.speed,t ) if self.type == box : drawer.box ( q0,q1,self.color ) elif self.type == dot : drawer.dot ( q0,self.color ) elif self.type == text : drawer.text ( q0,self.text,self.color ) elif self.type == clock : drawer.clock( q0,self.color ) if self.clock : drawer.clock( (q0[0]+1j,q0[1]),self.color ) def Nop ( **param ) : return Object() # objet invisible et qui ne fait rien... def Box ( **param ) : return Object( box ,**param ) # rectangle (pour symboliser un wagon) def Dot ( **param ) : return Object( dot ,**param ) # point (pour symboliser un projectile ou un photon) def Text ( **param ) : return Object( text ,**param ) # explication bienvenue qui accompagne un objet def Clock ( **param ) : return Object( clock,**param ) # horloge qui donne le temps propre dans un repère #------------------------------------------------------------------- #-- repère défini par une position et une vitesse ------------------ class Frame: def __init__( self,position,speed,c=1 ): speed = to_complex( speed ) self.onx = speed.imag == 0 self.V = speed self.O = to_complex( position ) self.v = speed.real or speed.imag self.c = c self.b = self.v/c self.g = (1-self.b**2)**-0.5 assert speed.real == 0 or speed.imag == 0 # la vitesse d'un repère ne peut être que horizontale ou verticale def __call__ (self,x0,v,T): # fonction de transformation (ici : celle de Lorentz) O,V,b,c,g = self.O,self.V,self.b,self.c,self.g (x0x,x0y),(vx,vy) = (x0.real,x0.imag),(v.real,v.imag) x0,y0,v,vy = (x0x,x0y,vx,vy) if self.onx else (x0y,x0x,vy,vx) X,Y,t = lorentz( x0,y0,vx,vy,T,self.c,self.b,self.g ) Z = complex( X,Y ) if self.onx else complex( Y,X ) return self.O+Z,t #------------------------------------------------------------------- #-- classe d'affichage des objets ---------------------------------- class Drawer : def __init__(self,canvas,origin=0,scale=1): # canvas doit se comporter comme un Tkinter.canvas self.colors = ('#000','#00b','#080','#c00') self.canvas = canvas self.origin = to_complex(origin) self.scale = to_complex(scale) self.font = ('Arial narrow',int(scale*0.8)) def _int (self,*qpoints ): qpoints = ( q[0]*self.scale+self.origin for q in qpoints ) qpoints = flatize( (q.real,q.imag) for q in qpoints ) return map( int,qpoints ) def box (self,q0,q1,color ): v = self._int( q0,q1 ) self.canvas.create_rectangle( *v,width=2,outline=self.colors[color] ) def dot (self,q,color ): r,(x,y) = 2,self._int( q ) self.canvas.create_oval( x-r,y-r,x+r,y+r,outline=self.colors[color],fill=self.colors[color] ) def text (self,q,txt,color ): if not txt : return (x,y) = self._int( q ) self.canvas.create_text( x,y,text=txt,font=self.font,fill=self.colors[color] ) def clock (self,q,color ): t,(x,y) = q[1],self._int( q ) self.canvas.create_text( x,y,text='%.1f'%t,font=self.font,fill=self.colors[color] ) #------------------------------------------------------------------- def relativity ( size,origin,scale,dT,*frames ): def draw ( step = 0 ): root.T += dT*step can.delete('all') can.create_text( size[0]/2,size[1]-10,text='FLÈCHES du temps , ECHAP pour quitter' ) for frame in frames : for obj in frame[1:]: obj.draw( root.T,frame[0],drawer ) root = Tk() root.T = 0 root.geometry('+20+20') root.bind('<Left>' ,lambda e : draw(-1)) root.bind('<Right>' ,lambda e : draw(+1)) root.bind('<space>' ,lambda e : draw(+5)) root.bind('<Escape>',lambda e : root.quit()) can = Canvas( root,width = size[0],height = size[1] ) can.pack() drawer = Drawer( can,origin,scale ) draw() root.mainloop() #------------------------------------------------------------------- #--- démo avec unité de temps = seconde # unité de longueur = seconde-lumière (~300000km) => c = 1 def build_wagon ( pos,speed,nbclock,color,text,vertical_photon=False ): ''' Construit un repère contenant un wagon long de 20sl + 2 photons qui partent de son centre. ''' wsize = 20 frame = Frame( pos*1j,speed,1 ) wagon = Box( pos=-wsize/2+1j,size=wsize+4j,color=color ) spot1 = Dot( pos=3j,speed= 1,clock=True,color=color ) spot2 = Dot( pos=3j,speed=-1,clock=True,color=color ) spotV = (Dot if vertical_photon else Nop)( pos=3j,speed=1j,clock=True,color=color ) name = Text( pos=2j,text=text,color=color ) clocks = tuple(Clock( pos=i+6j,color=color ) for i in range( int(-wsize/2),int(wsize/2+1),int(wsize/(nbclock-1)))) return (frame,wagon,spot1,spot2,spotV,name)+clocks def demo1 ( scale = 10 ): deck = build_wagon( 0,0 ,3,0,'wagon sur le quai' )+(Box( pos=-100,size=200+8j ),) wagon1 = build_wagon( 9,0.1,5,1,'wagon 10%' ) wagon2 = build_wagon( 16,0.8,5,2,'wagon 80%' ) wagon3 = build_wagon( 23,0.9,5,3,'wagon 90%' ) relativity( (scale*80,scale*35),(scale*20,0),scale,0.1,deck,wagon1,wagon2,wagon3 ) demo1( 20 ) |
Merci :-)
Developpez.com décline toute responsabilité quant à l'utilisation des différents éléments téléchargés.