Mathématiques avec Python et Ruby/Fonctions en Ruby
En Ruby, une fonction s'appelle une méthode, mais du point de vue mathématique, ce n'est guère qu'une question de vocabulaire.
Exemple
modifierSujet Bac STG CGRH Métropole-Réunion Septembre 2007
modifierpour
Et plus bas, dans le même exercice,
pour x appartenant à [5 ; 40].
Définition des méthodes
modifierDonc pour Ruby, C et f seront des méthodes, dont l'antécédent s'appellera x et dont l'image sera envoyée par return:
def C(x)
return x**2+50*x+100.0
end
def f(x)
return C(x)/x
end
Bien entendu, on pouvait aussi définir f directement par
def f(x)
return x+50+100.0/x
end
Tableau de valeurs
modifierSuite de l'énoncé du Bac STG 2007
modifierPar la suite, on demande de reproduire et compléter le tableau suivant, arrondi au centième d'euro:
x | 5 | 10 | 20 | 30 | 40 |
f(x) |
Tableau de valeurs
modifierCertes, avec une boucle, on peut calculer plein de valeurs de f(x) différentes:
for x in 5..40 do
puts("l'image de #{x} par f est #{f(x)}")
end
mais on a trop de valeurs de x pour remplir le tableau. Une meilleure variante sera donc
for x in [5,10,20,30,40] do
puts("l'image de #{x} par f est #{f(x)}")
end
qui est déjà bien plus léger à exploiter.
Plus typiquement Ruby:
[5,10,20,30,40].collect {|x| puts(f(x))}
Image d'un ensemble par une fonction
modifierPour que la fonction f ne s'applique plus seulement à un réel, mais à tous les nombres du tableau, on utilise map (une méthode de l'objet tableau):
[5,10,20,30,40].map { |x| puts(f(x)) }
Cette notion d'image d'un ensemble par une fonction est à la base de pratiquement toute la géométrie: Alors que la symétrie centrale est définie comme une transformation qui associe un point à un point, on l'applique très vite à des ensembles de points comme dans l'expression la symétrique d'une droite par rapport à un point.
Arrondis
modifierEnfin, pour avoir les arrondis au centime près:
[5,10,20,30,40].collect {|x| puts(f(x).round(2))}
qui remplit le tableau presque immédiatement.
Représentation graphique
modifierRuby n'étant pas très doué (pour le moment) en dessin, on va utiliser ses talents littéraires pour fabriquer un fichier au format svg. Ce fichier sera fabriqué comme une chaîne de caractères, et inscrit dans un fichier nommé FonctionRuby01.svg posté ci-dessous. Le fichier sera créé en mode écriture (w) avec
figure=File.open("FonctionRuby01.svg","w")
Création de la figure
modifierOn commence par écrire dans le fichier (qui, on l'a vu ci-dessus, s'appelle figure), ce qu'il faut pour dire que c'est un fichier svg (l'entête):
figure.puts('<?xml version="1.0" encoding="utf-8"?>')
figure.puts('<!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 1.1//EN"')
figure.puts('"http://www.w3.org/Graphics/SVG/1.1/DTD/svg11.dtd">')
figure.puts('<svg xmlns="http://www.w3.org/2000/svg" width="640" height="480">')
Le fichier fera donc 640 pixels de large et 480 pixels de haut.
Axes
modifierLes axes et leurs graduations seront des traits, créés par des boucles puisque le travail des graduations est répétitif et que les boucles sont faites pour tout ce qui est répétitif.
Des abscisses
modifierL'axe des abscisses et ses graduations sera bleu:
figure.puts('<line x1="20.0" y1="460.0" x2="540.0" y2="460.0" style="stroke:rgb(0,0,64);stroke-width:1"/>')
((0..500).select {|x| x%100==0}).collect { |x| figure.print('<text x="'+(x+20).to_s+'" y="475.0" style="font-size:16;fill:rgb(0,0,64);font-weight:normal">'+(x/10).to_s+'</text>\n'+'<line x1="'+(x+20).to_s+'" y1="455" x2="'+(x+20).to_s+'" y2="465" style="stroke:rgb(0,0,64);stroke-width:1"/>\n')}
((0..500).select {|x| x%50==0}).collect { |x| figure.print('<line x1="'+(x+20).to_s+'" y1="456" x2="'+(x+20).to_s+'" y2="464" style="stroke:rgb(0,0,64);stroke-width:1"/>\n')}
((0..500).select {|x| x%10==0}).collect { |x| figure.print('<line x1="'+(x+20).to_s+'" y1="458" x2="'+(x+20).to_s+'" y2="462" style="stroke:rgb(0,0,64);stroke-width:1"/>\n')}
Des ordonnées
modifierL'axe des ordonnées est en vert:
figure.puts('<line x1="20.0" y1="460.0" x2="20.0" y2="40.0" style="stroke:rgb(0,40,0);stroke-width:1"/>')
((0..400).select {|y| y%40==0}).collect { |y| figure.print('<text x="0" y="'+(460-y).to_s+'" style="font-size:16;fill:rgb(0,40,0);font-weight:normal">'+(y/4).to_s+'</text>\n'+'<line x1="15" y1="'+(460-y).to_s+'" x2="25" y2="'+(460-y).to_s+'" style="stroke:rgb(0,40,0);stroke-width:1"/>\n')}
((0..400).select {|y| y%20==0}).collect { |y| figure.print('<line x1="16" y1="'+(460-y).to_s+'" x2="24" y2="'+(460-y).to_s+'" style="stroke:rgb(0,40,0);stroke-width:1"/>\n')}
((0..400).select {|y| y%4==0}).collect { |y| figure.print('<line x1="18" y1="'+(460-y).to_s+'" x2="22" y2="'+(460-y).to_s+'" style="stroke:rgb(0,40,0);stroke-width:1"/>\n')}
Courbe
modifierOn va représenter graphiquement la fonction en rouge, sous forme d'un polygone à 350 côtés:
(50..400).collect {|x| figure.print('<line x1="'+(19+x).to_s+'" y1="'+(460-4*f((x-1).to_f/10)).to_s+'" x2="'+(20+x).to_s+'" y2="'+(460-4*f(x.to_f/10)).to_s+'" style="stroke:rgb(120,0,0);stroke-width:1"/>\n')}
Résultat
modifierPour que la figure soit reconnue, il reste encore à fermer la balise svg, ouvert au tout début de la figure, puis à fermer le fichier pour que Ruby le libère:
figure.puts('</svg>')
figure.close
L'exécution du script ci-dessus produit le fichier suivant:
Certes, le fichier Ruby a l'air encore plus compliqué que le fichier svg mais il est possible de créer des méthodes axes et trait pour en simplifier la lecture.