VISUAL BASIC & EXCEL
TP 2
Étude d'une fonction
Comme vous l'avez sans doute remarqué, les couleurs utilisées dans ColorIndex sont des nombres entiers compris entre 0 et 53. Voici le tableau des 15 premières couleurs (sur PC):
Code |
0 |
1 |
2 |
3 |
4 |
5 |
6 |
7 |
Couleur |
Sans |
Blanc |
Noir |
Rouge |
Vert |
Bleu |
Jaune |
Magenta |
Code |
8 |
9 |
10 |
11 |
12 |
13 |
14 |
15 |
Couleur |
Cyan |
Brun |
Vert foncé |
Bleu foncé |
Kaki |
Violet |
Bleu-vert |
Gris |
1.1. Découpage de l'année en 4 trimestres
Seules quelques procédures sont modifiées :
Sub AfficherTitre() For trimestre = 1 To 4 'le calendrier sera imprimé sur 4 pages Cells(1, 9 * trimestre - 8) = "Année " & Année Range(Cells(1, 9 * trimestre - 8), Cells(1, 9 * trimestre)).Select With Selection .HorizontalAlignment = xlHAlignCenterAcrossSelection .VerticalAlignment = xlVAlignCenter .Font.Name = Arial .Font.Size = 20 .Font.Bold = True .BorderAround Weight:=xlThick .Interior.ColorIndex = 4 End With Next trimestre End SubLes largeurs des colonnes peuvent être augmentées car on a plus de place. Il faut donc modifier la procédure RéglerLesLargeursDesColonnes :Sub RéglerLargeurDesColonnes() 'chaque mois occupera 3 colonnes de largeurs 10, 2 et 15 For c = 1 To 12 Columns(3 * c - 2).ColumnWidth = 10 Columns(3 * c - 1).ColumnWidth = 2 Columns(3 * c).ColumnWidth = 15 Next c End SubDe même, la procédure qui affiche les noms des jours peut être modifiée ainsi :
Sub AfficherJours() 'affichage des jours : jours en toutes lettres + rang du jour For m = 1 To 12 For j = 1 To 31 ch = Format(j & "/" & m & "/" & Année, "dddd") If IsDate(j & "/" & m & "/" & Année) Then Cells(2 + j, 3 * m - 2) = ch Cells(2 + j, 3 * m - 1) = j If (Cells(2 + j, 3 * m - 2) = "samedi") _ (voir remarque ci-dessous) Or (Cells(2 + j, 3 * m - 2) = "dimanche") Then Range(Cells(2 + j, 3 * m - 2), Cells(2 + j, 3 * m)).Select Selection.Interior.ColorIndex = 3 End If End If Next j Range(Cells(3, 3 * m - 2), Cells(33, 3 * m)).BorderAround Weight:=xlThick Next m End SubUne particularité dans le texte ci-dessus , concernant les 2 lignes :
If (Cells(2 + j, 3 * m - 2) = "samedi") _ Or (Cells(2 + j, 3 * m - 2) = "dimanche") ThenLa première des 2 lignes se termine par un tiret de soulignement précédé d'un espace. Ces 2 caractères indiquent que l'instruction se poursuit à la ligne suivante. Ceci permet d'avoir une mise en page plus agréable.
Voici le résultat obtenu :
1.2. Calendrier sur une page.
Il s'agit cette fois, de faire tenir le calendrier sur une seule page. La disposition retenue est le mode portrait avec les 2 semestres l'un au-dessus de l'autre. Plusieurs procédures sont modifiées. On trouvera ci-dessous le détail de ces modifications :
'Macro Calendrier sur 1 page 'Réalisée par P. Rabiller le 9/02/2000 Dim Année 'Déclaration d'une variable "Année" utilisable dans tout le programme Sub Calendrier() 'programme principal SaisirAnnée RéglerLargeurDesColonnes AfficherTitre AfficherNomsMois AfficherJours End Sub Sub SaisirAnnée() 'demande à l'utilisateur de taper une année Année = InputBox("Tapez l'année :", "Calendrier") End Sub Sub RéglerLargeurDesColonnes() 'disposition des 2 semestres superposés en mode portrait Range(Cells(1, 1), Cells(65, 18)).Select Selection.Clear For c = 1 To 6 Columns(3 * c - 2).ColumnWidth = 2 Columns(3 * c - 1).ColumnWidth = 2 Columns(3 * c).ColumnWidth = 10 Next c End Sub Sub AfficherTitre() Cells(1, 1) = "Année " & Année Range(Cells(1, 1), Cells(1, 18)).Select With Selection .HorizontalAlignment = xlHAlignCenterAcrossSelection .VerticalAlignment = xlVAlignCenter .Font.Name = Arial .Font.Size = 20 .Font.Bold = True .BorderAround Weight:=xlThick .Interior.ColorIndex = 4 End With End Sub Sub AfficherNomsMois() 'affichage des noms des 12 mois For m = 1 To 12 ch = Format("1/" & m, "dd mmmm") If m < 7 Then Cells(2, 3 * m - 2) = Mid(ch, 4, 10) Range(Cells(2, 3 * m - 2), Cells(2, 3 * m)).Select Else Cells(34, 3 * (m - 6) - 2) = Mid(ch, 4, 10) Range(Cells(34, 3 * (m - 6) - 2), Cells(34, 3 * (m - 6))).Select End If With Selection .HorizontalAlignment = xlHAlignCenterAcrossSelection .VerticalAlignment = xlVAlignCenter .Font.Name = Arial .Font.Size = 14 .Font.Bold = True .BorderAround Weight:=xlThick .Interior.ColorIndex = 15 End With Next m End Sub Sub AfficherJours() 'affichage des jours : 1ère lettre + rang du jour For m = 1 To 12 For j = 1 To 31 ch = Format(j & "/" & m & "/" & Année, "dddd") If IsDate(j & "/" & m & "/" & Année) Then If m < 7 Then Cells(2 + j, 3 * m - 2) = Mid(ch, 1, 1) Cells(2 + j, 3 * m - 1) = j If (Cells(2 + j, 3 * m - 2) = "s") Or (Cells(2 + j, 3 * m - 2) = "d") Then Range(Cells(2 + j, 3 * m - 2), Cells(2 + j, 3 * m)).Select Selection.Interior.ColorIndex = 3 End If Else Cells(34 + j, 3 * (m - 6) - 2) = Mid(ch, 1, 1) Cells(34 + j, 3 * (m - 6) - 1) = j If (Cells(34 + j, 3 * (m - 6) - 2) = "s") _ Or (Cells(34 + j, 3 * (m - 6) - 2) = "d") Then Range(Cells(34 + j, 3 * (m - 6) - 2), _ Cells(34 + j, 3 * (m - 6))).Select Selection.Interior.ColorIndex = 3 End If End If End If Next j If m < 7 Then Range(Cells(2, 3 * m - 2), Cells(33, 3 * m)).BorderAround Weight:=xlThick Else Range(Cells(34, 3 * (m - 6) - 2), Cells(65, 3 * (m - 6))). _ BorderAround Weight:=xlThick End If Next m Range(Cells(3, 1), Cells(33, 18)).Select Selection.VerticalAlignment = xlCenter Selection.RowHeight = 12 Range(Cells(35, 1), Cells(65, 18)).Select Selection.VerticalAlignment = xlCenter Selection.RowHeight = 12 Rows(2).RowHeight = 19 Rows(34).RowHeight = 19 End Sub1.3. Un seul mois choisi par l'utilisateur
'Calendrier avec un seul mois choisi par l'utilisateur 'réalisé par P. Rabiller le 7/02/2001 Dim Année, Mois Sub CalendrierUnMois() Range(Cells(1, 1), Cells(31, 3)).Clear SaisirAnneeEtMois RéglerTailleDesCellules AfficherJours AfficherTitre End Sub Sub SaisirAnneeEtMois() Année = InputBox("Taper l'année : ", "Calendrier") Mois = InputBox("Taper le mois (en chiffres) :", "Calendrier") End Sub Sub RéglerTailleDesCellules() Columns(1).ColumnWidth = 20 Columns(2).ColumnWidth = 5 Columns(3).ColumnWidth = 40 Range(Cells(1, 1), Cells(31, 2)).Select With Selection .VerticalAlignment = xlCenter .Font.Name = "Times new Roman" .Font.Size = 14 End With For k = 1 To 31 Rows(k).RowHeight = 20 Next Cells(1, 1).Select End Sub Sub AfficherJours() For j = 1 To 31 ch = Format(j & "/" & Mois & "/" & Année, "dddd") If IsDate(j & "/" & Mois & "/" & Année) Then Cells(j, 1) = ch Cells(j, 2) = j Range(Cells(j, 1), Cells(j, 3)).BorderAround Weight:=xlThin Range(Cells(j, 1), Cells(j, 3)).Borders(xlInsideVertical).Weight = xlThin End If Next j End Sub Sub AfficherTitre() ch = Format(1 & "/" & Mois & "/" & Année, "mmmm yyyy") With ActiveSheet.PageSetup .CenterHeader = ch .CenterHorizontally = True .CenterVertically = True .Orientation = xlPortrait End With End Sub
2. Étude des valeurs d'une fonction
2.1. Table des valeurs sans programmation
Considérons la fonction f définie sur R par .
On veut obtenir une table de valeurs de f(x) lorsque x décrit un intervalle donné.
Commencer par remplir les premières cellules de la feuille de calcul comme indiqué ci-contre :Définir un nom, en utilisant la commande Insertion / Nom / Définir pour les cellules B1, B2 et B3 . (on les nommera respectivement Xmin, Xmax et Pas)
Dans la cellule A8, taper la formule : =Xmin
Dans la cellule B8, taper la formule : =Si(A8<>"";A8/(A8^2+1);"") (chacun aura compris la formule)
Il s'agit maintenant de construire la table des valeurs de f(x) losrque x décrit l'intervalle [Xmin, Xmax] .
On peut commencer par recopier vers le bas la formule B8 jusqu'à la la cellule B100 (on prévoit large).
Connaissant le pas et les valeurs extrêmes de l'intervalle, on peut calculer la valeur suivante de x en tapant, dans la cellule A9 la formule : =Si(et(A8<>"";A8+Pas<=Xmax);A8+Pas;"")
Ou bien la formule : =Si(Ligne()-8<=(Xmax-Xmin)/Pas;A8+Pas;"")
Il suffit alors de recopier vers le bas la formule A9 jusqu'à la ligne A100.
Normalement, tout fonctionne correctement : si on change l'une des valeurs Xmin, Xmax ou Pas, toute la feuille est recalculée.Cependant, l'inconvénient principal, c'est que, si on veut modifier la fonction, il est nécessaire de changer la formule de la cellule B8 et de la recopier vers le bas jusqu'à la ligne 100... Ce qu'il faudrait, c'est avoir une formule dans la cellule B9 du genre : = f(A8) . Voici comment procéder :
2.2. Table des valeurs avec programmation
Afficher l'éditeur de code de visual basic et taper les lignes suivantes :
'Table de valeurs d'une fonction 'réalisée le 11/02/2002 par P. Rabiller Function f(x) f = x / (x * x + 1) End Function Sub calculs() XMin = Cells(1, 2) XMax = Cells(2, 2) pas = Cells(3, 2) i = 8 x = XMin Do While x <= XMax Cells(i, 1) = x Cells(i, 2) = f(x) x = x + pas i = i + 1 Loop End SubRevenir ensuite à la feuille de calcul et lancer l'exécution de la macro Calculs.
On peut modifier les données introduites par l'utilisateur dans les cellules B1, B2 et B3 pour obtenir une table différente. Inconvénient : les calculs précédents ne sont pas effacés et si la nouvelle table comporte moins de valeurs, les données précédentes restent à l'affichage. De plus, on peut remarquer que les valeurs affichées sont mal formatées. Il serait intéressant que l'utilisateur puisse préciser le nombre de décimales.2.3. Effacer les données précédentes et afficher dans un format défini par l'utilisateur
Modifier la feuille de calcul en ajoutant une ligne pour saisir le nombre de décimales :
Modifier la procédure Calculs de la façon suivante (la partie modifiée est en caractères italiques) :
Sub calculs() XMin = Cells(1, 2) XMax = Cells(2, 2) pas = Cells(3, 2) NbDécimales = Cells(4, 2) Range(Cells(8, 1), Cells(100, 2)).Select Selection.Clear ch = "0." For i = 1 To NbDécimales ch = ch & "0" 'si NbDécimales=3, alors la chaîne de format sera ch="0.000" Next i Range(Cells(8, 2), Cells(100, 2)).NumberFormat = ch 'mise en place du format i = 8 x = XMin Do While x <= XMax Cells(i, 1) = x Cells(i, 2) = f(x) x = x + pas i = i + 1 Loop End Sub2.4. Ajouter un bouton pour lancer l'exécution de la procédureChoisir dans la barre des boutons, le bouton "Bouton" : .
Si ce bouton n'apparaît pas dans votre barre des boutons, effectuer la commande Affichage/Barre d'outils... et choisir la barre d'outils Formulaire :
Placer le bouton en faisant glisser la souris dans la feuille de calcul :
Dès qu'on lâche le bouton de la souris, on obtient une fenêtre permettant d'affecter à notre bouton une macro (procédure) de notre choix. Nous lui affectons la procédure Calculs :
Nous pouvons modifier le nom du bouton. Pour cela :
Désormais un simple clic sur ce bouton suffit à lancer la procédure Calculs.
3. Exercices
3.1. Cas d'une fonction non définie sur tout l'intervalle [Xmin, Xmax]
Essayer de refaire les calculs avec la fonction f définie par : . La fonction racine carrée s'obtient avec le mot Sqr.
Que se passe-t-il si les valeurs de Xmin et de Xmax débordent de l'intervalle [-1, 1] ?
Comment faut-il modifier l'écriture de la fonction pour que les valeurs négatives de 1-x² ne provoquent pas d'erreur à l'exécution ?3.2. Cas d'une fonction définie par morceaux
Modifier l'écriture du programme pour permettre l'étude de la fonction f définie par :
si x £-1 : ,
si x > -1 et x £2 :
si x ³3 :3.3. Calcul de la dérivée
Ajouer une colonne permettant d'obtenir, parallèlement à la table des valeurs de , une table des valeurs de . Plusieurs solutions sont possibles, mais toutes utilisent une approximation pour calculer le nombre dérivé en un point x : »
3.4. Calcul de l'intégraleAjouter une cellule qui reçoit une valeur approchée de l'intégrale sur l'intervalle [Xmin, Xmax] (calculée par la méthode des rectangles par exemple). On pourra utiliser la cellule B5 pour recevoir le résultat.
L'intégrale sera calculée à l'aide d'une fonction, tout comme la fonction f et sa dérivée.3.5. Représentation graphique d'une fonction
Prenons l'exemple de la fonction définie par sur l'intervalle [-4 ; 4]
Pour obtenir directement la courbe représentative de cette fonction :
On obtient alors ceci :
L'inconvénient de ce procédé est que, si on change les bornes Xmin et Xmax ou le pas, le graphique ne couvre pas forcément la totalité de la plage. En effet, la plage sélectionnée correspondant au graphique est toujours la même. Par contre, si on modifie la fonction, le graphique est modifié en conséquence.
Il existe la possibilité d'enregistrer une séquence de commandes sous la forme d'une procédure puis de la modifier pour l'adapter à nos besoins. Une solution sera proposée la prochaine fois....