resultat :
- chaque professeur est 8 ou 9 fois sélectionné comme surveillant ou remplacant (donc assez equilibre)
- chaque professeur est 6 à 8 fois sélectionné comme surveillant
- chaque professeur est 0 à 3 fois sélectionné comme remplaçant
Sub BSALV_aleatoire()
Dim iC, Plann, iProf, iSalle, iPériodes, c0, c, c2
iSalle = 24 'nombre de salles
iPériodes = 10 'nombre de périodes d'examen, par exemple 5 jours * 2 examen/jour
T = Timer 'demarre le chronomètre
Application.ScreenUpdating = False
Set dict = CreateObject("scripting.dictionary")
Randomize
ReDim Plann(1 To iSalle, 1 To iPériodes * 3) 'array du planning
Set c = Sheets("liste des profs").ListObjects("TBProfs").DataBodyRange 'les données des professeurs
iC = c.Columns.Count 'nombre de colonnes
a = c.Resize(, iC + 4).Value 'ajouter 4 colonnes comme brouillon
iProf = UBound(a) 'nombre de professeurs
For i = 1 To UBound(a)
For J = 1 To 3: a(i, iC + J) = 0: Next 'les 3 premières colonnes de brouillon = 0
a(i, iC + 4) = Rnd '4ièem colonne de brouillon = aleatoire 0-1
Next
Set c0 = Sheets("result").Range("AA1") 'partie dans cette feuille qui sert à sorter
c0.Resize(1000, 20).ClearContents
Set c = c0.Resize(UBound(a), UBound(a, 2))
For ipick = 1 To iPériodes 'boucle les périodes d'examen
Randomize
c.Value = a 'l'array a vers plage de brouillon
With c.Parent.Sort 'sortkey = nombre de fois selectionné (A) + nombre de fois surveillant (A) + nombre de fois remplacant (D) + aleatoire (A)
.SortFields.Clear
.SortFields.Add2 Key:=c.Columns(iC + 1), SortOn:=xlSortOnValues, Order:=xlAscending, DataOption:=xlSortNormal
.SortFields.Add2 Key:=c.Columns(iC + 2), SortOn:=xlSortOnValues, Order:=xlAscending, DataOption:=xlSortNormal
.SortFields.Add2 Key:=c.Columns(iC + 3), SortOn:=xlSortOnValues, Order:=xlDescending, DataOption:=xlSortNormal
.SortFields.Add2 Key:=c.Columns(iC + 4), SortOn:=xlSortOnValues, Order:=xlAscending, DataOption:=xlSortNormal
.SetRange c
.Header = xlNo
.MatchCase = False
.Orientation = xlTopToBottom
.SortMethod = xlPinYin
.Apply
End With
Set c2 = c.Offset(2 * iSalle) 'les 2*iSalle sont les surveillant, le rest maintenant, donc à partir du 2*isalle+1 ième professeur
With c2.Parent.Sort 'sortkey = nombre de fois selectionné (A) + nombre de fois remplacant (A) + aleatoire (A)
.SortFields.Clear
.SortFields.Add2 Key:=c2.Columns(iC + 1), SortOn:=xlSortOnValues, Order:=xlAscending, DataOption:=xlSortNormal
.SortFields.Add2 Key:=c2.Columns(iC + 3), SortOn:=xlSortOnValues, Order:=xlAscending, DataOption:=xlSortNormal
.SortFields.Add2 Key:=c2.Columns(iC + 4), SortOn:=xlSortOnValues, Order:=xlAscending, DataOption:=xlSortNormal
.SetRange c2
.Header = xlNo
.MatchCase = False
.Orientation = xlTopToBottom
.SortMethod = xlPinYin
.Apply
End With
arr = c.Value 'read to array
For i = 1 To Application.Min(WorksheetFunction.Ceiling_Math(2.5 * iSalle, 1), iProf) 'nombre de personnes à assigner pour un examen
ptr = arr(i, 1) 'pointer vers l'array a
prof = arr(i, 2) 'nom du professeur
Select Case i
Case 1 To iSalle: dict.Add dict.Count, Array(ipick, i, "Surv.1", prof, 1): Plann(i, (ipick - 1) * 3 + 1) = prof: a(ptr, iC + 2) = a(ptr, iC + 2) + 1 'surveillant 1
Case iSalle + 1 To iSalle * 2: dict.Add dict.Count, Array(ipick, i - 24, "Surv.2", prof, 1): Plann(i - 24, (ipick - 1) * 3 + 2) = prof: a(ptr, iC + 2) = a(ptr, iC + 2) + 1 'surveuillance2
Case Is > iSalle * 2: dict.Add dict.Count, Array(ipick, (i - 50) * 2 + 1, "Rempl.", prof, 0): Plann((i - 49) * 2 + 1, (ipick - 1) * 3 + 3) = prof: a(ptr, iC + 3) = a(ptr, iC + 3) + 1 'remplacant
End Select
a(ptr, iC + 1) = a(ptr, iC + 1) + 1
a(ptr, iC + 4) = Rnd
Next
Next
arr = Application.Index(dict.items, 0, 0)
With Sheets("result").Range("A1").ListObject
If .ListRows.Count Then .DataBodyRange.Delete
If dict.Count Then
.ListRows.Add.Range.Range("A1").Resize(UBound(arr), UBound(arr, 2)).Value = arr
End If
End With
With Sheets("répartition").Range("B4")
.Resize(100, 100).ClearContents
.Resize(UBound(Plann), UBound(Plann, 2)).Value = Plann
End With
ThisWorkbook.RefreshAll
MsgBox Timer - T
End Sub