web-dev-qa-db-fra.com

Calculer le classeur entier mais pas tous les classeurs ouverts VBA

Existe-t-il un moyen de calculer un classeur entier mais pas tous les classeurs ouverts dans VBA?

Je sais à propos de

worksheet.Calculate

mais il ne fera que 1 feuille. Je connais aussi

Application.CalculateFull

Mais je pense que cela recalcule tous les classeurs ouverts en même temps.

Est-il possible de ne faire qu'un seul classeur?

modifier: Je comprends l'approche:

For Each wks In ActiveWorkbook.Worksheets
    wks.Calculate

mais cela est très dangereux si les feuilles ont des liens entre elles, alors l'ordre de calcul est important. Je sais que je pourrais trouver la séquence exacte et l’appliquer, le problème est que sur de très grands cahiers

7
Steven G

Après quelques recherches et tests, la sélection de toutes les feuilles en premier et le calcul ultérieur fonctionnent:

Application.Calculation = xlManual
ThisWorkbook.Sheets.Select
ActiveSheet.Calculate 

cela calcule toutes les feuilles sélectionnées en même temps en créant le bon ordre de calcul

6
Steven G

Aucune que je sache, Steven.

Vous perdez réellement du temps à faire Application.Worksheets (1) .Calcul

Je lance un test de chronométrage:

3 Les classeurs s'ouvrent dans la même instance d'Excel.

Une avec 8200 fonctions volatiles, 8000 dans une feuille de calcul sur 4 plages non contiguës, 200 dans d'autres feuilles de calcul.

Deux autres classeurs avec un total combiné de 100 fonctions . Résultats:

 Application.Calculate - 4.41 ms
 ThisWorkbook.Worksheets(1).Calculate - 52.05 ms for each worksheet
 ThisWorkbook.Worksheets(1).Range("R1").Calculate (repeated 4 times) - 84.64 ms

C'est contre-intuitif, mais vrai.

Vous perdez également du temps à déclarer Dim wks en tant que feuille de calcul. À moins que vous ne le fassiez pour ... Chacun s'y référant en tant que ThisWorkbook.Worksheets (1) - est plus rapide

Veillez également à faire référence à ActiveWorkbook. Lorsque vous exécutez du code, votre classeur principal peut ne pas être actif. ThisWorkbook (celui avec le code) est plus sûr.

1
antonsachs

ThisWorkbook utilisera uniquement le classeur dans lequel réside le code

For Each wks In ThisWorkbook.Worksheets
    wks.Calculate
Next wks
0
Sean O'Reilly

Il suffit d'utiliser calculer

par exemple: Sub Cal_ ()

Calculer

End Sub

0
Vikas Soni

EDIT: Essayez ceci:

Sub CalcBook() Dim wks As Worksheet Application.Calculation = xlManual For Each wks In ActiveWorkbook.Worksheets wks.Calculate Next Set wks = Nothing End Sub

0
William C.

La réponse de Steven G ne fonctionne pas vraiment, elle a juste l’air de le faire (je ne peux pas répondre à ce message car je n’ai pas plus de 50 représentants, ce qui est agaçant). 

Il calcule toujours les feuilles dans 1 ordre directionnel. J'ai testé cela en créant 5 feuilles et en les faisant toutes + 1 dans une autre cellule, sur chaque feuille dans des directions différentes. Utiliser les feuilles de sélection, puis la méthode de calcul donnera un résultat erroné. 

Comme il faut que les feuilles soient visibles, elow est la fonction que j’ai construite pour remplacer la fonction de calcul utilisant cette méthode. (Nécessite une bibliothèque de référence de dictionnaires). Ne pas utiliser si.

    EXAMPLE, METHOD DOES NOT WORK
Function Calculate_Workbook(Optional Wb As Workbook)

'Application.calculate will calculate all open books, which can be very slow.
'Looping through all sheets in workbook to calculate can be risky due to formula referencing a cell thats not yet calculated, calculation order may be important.
Dim DicShtVisible As New Dictionary
DicShtVisible.CompareMode = TextCompare
Dim Asht As Worksheet, AWkbk As Workbook    'Previously selected books
Dim Sht As Worksheet

Set Asht = ActiveSheet
Set AWkbk = ActiveWorkbook

If Wb Is Nothing Then Set Wb = ThisWorkbook

Wb.Activate
'Unhide all sheets as can't select very hidden stuff
For Each Sht In Wb.Sheets
    DicShtVisible.Add Sht.Name, Sht.Visible
    Sht.Visible = xlSheetVisible
Next Sht

'Select all sheets and calculate the lot
Wb.Sheets.Select
ActiveSheet.Calculate

'Reapply visibility settings
Dim Key As Variant
For Each Key In DicShtVisible.Keys
    Wb.Sheets(Key).Visible = DicShtVisible.Item(Key)
Next Key

'Reset selections
AWkbk.Activate
Asht.Select

End Function

Autant que je sache, il n'y a pas de solution. La seule solution est de connaître l'ordre de calcul de votre classeur et de calculer manuellement les feuilles dans cet ordre, ou d'accepter l'utilisation de Calculer pour calculer tous les classeurs ouverts.

J'aimerais cependant avoir tort. C'est une question tellement ennuyeuse et stupide.

0
Dave Scott