2012-07-30 11 views
5

Ich habe festgestellt, dass einige SO-Benutzer bei der Verwendung einer Variante von Cells.Count auf ein Problem gestoßen sind. Der VBA-Code löst in einigen Fällen einen Überlauffehler aus.Falscher Wert beim Zählen von Zellen in verschiedenen Excel-Versionen

Zur Bezugnahme siehe Kommentare zu this answer:

ich denke, das wird funktionieren, aber ich erhalte eine „Überlauf“ Fehler und er zeigt mir auf den Code „Wenn Master.Cells.SpecialCells (xlCellTypeVisible) .Count> 0 Then“--- es scheint, wie es nicht ist Filterung für etwas Bestimmtes - user1556069

und this answer:

Ist diese only funktioniert (und Cells.Count hat nicht funktioniert), weil die letzte eine Ganzzahl, 16 Bit, max Wert von 65.536 verwendet und die ganze Tabelle eine Nummer größer zurückgegeben? - fast_code


Ich gehe davon aus, dass irgendwo hinter den Kulissen VBA versucht die Zellenzahl auf einen kleinen Integer (16-Bit) oder Lange Ganzzahl zu zwingen (32-Bit). Die Zellenanzahl eines Excel 2007-Arbeitsblattes würde beide dieser -Datentypen überlaufen. Leider kann ich es jetzt nicht isolieren, weil ich keine Kopie von Excel 2007 handlich habe und nicht wirklich deinen Fehler reproduzieren kann. - mwolfe02

Der Versuch, dies zu verstehen, habe ich versucht, mich zu reproduzieren und bekam einen Überlauf bei dem Versuch, Cells.Count als Integer zuzuweisen. Dies ist sinnvoll, da der Wert für den Datentyp Integer zu groß ist.

Mit dem folgenden Code in Excel 2003 und 2010 wurde mir ein numerisches Ergebnis gegeben, wenn Sie versuchen, als Long oder Variant zuzuweisen.

Option Explicit 

Sub testInteger() 
    Dim i As Integer 
    i = Cells.Count 'Overflow 
    Debug.Print i 'Doesn't get this far... 
End Sub 

Sub testLong() 
    Dim l As Long 
    l = Cells.Count 
    Debug.Print l 'Prints 16777216 in both versions 
End Sub 

Sub testVariant() 
    Dim v As Variant 
    v = Cells.Count 
    Debug.Print v 'Prints 16777216 in both versions 
End Sub 

Wie Sie in meinen Kommentaren sehen kann, ist der Wert Cells.Count16777216 (die für 2003 korrekt ist), aber es ist die gleiche für beide Versionen, und dass Sinn für mich nicht machen. Zu zitieren mwolfe02 aus einem der oben verlinkte Antworten:

Excel 2007 Arbeitsblatt haben 1.048.576 Zeilen und 16.384 Spalten für insgesamt 17179869184 Zellen.

Welche sagt mir der Wert im Jahr 2010 gedruckt sollte mindestens (ich glaube, es sollte wirklich das gleiche sein) 17,179,869,184.

Warum wird diese Zahl nicht korrekt gedruckt/warum wird der Wert von 2003 im Jahr 2010 zurückgegeben?

+2

16777216 ist '0x1000000' und 17179869184 ist' 0x400000000' in hexadezimal nur FYI. – TheZ

+0

Führen Sie Excel 2010 im Kompatibilitätsmodus aus oder schauen Sie sich eine im Format 2003 gespeicherte Datei an? –

+0

@TimWilliams Ich begann mit dem Öffnen einer neuen Excel 2010-Sitzung, die standardmäßig auf Book1 gesetzt wurde, in der ich den obigen Code eingefügt habe. Wie stelle ich fest, ob ich compat bin? Modus? – Gaffi

Antwort

7

Bei der Berechnung solcher großen Zahlen verwenden Sie .Countlarge Eigenschaft.

Zum Beispiel

Sub CellsCount() 
    Dim l As Double 
    l = ActiveSheet.Cells.CountLarge 
    Debug.Print l 
End Sub 

auch nie Cells.Count oder Cells.CountLarge verwenden, ohne das Arbeitsblatt-Objekt angibt. Dies stellt sicher, dass wir im Kompatibilitätsmodus keine falsche Anzahl/Fehler erhalten. Verwenden Sie niemals Rows.Count. Verwenden Sie immer ws.Rows.Count. Dies ist der häufigste Fehler, den Leute machen, wenn sie versuchen, die letzte Zeile in Excel zu finden. Zum Beispiel

Diese

lRow = ws.Range("A" & Rows.Count).End(xlUp).Row 

und

lRow = ws.Range("A" & ws.Rows.Count).End(xlUp).Row 

könnten Sie nicht die gleichen Ergebnisse liefern immer.

Ich würde auch empfehlen weiterlesen von this.

+0

Danke, Sid. Ich schätze deine Einsicht. (Trotzdem, warum musste MSFT sowohl '.Count' * als auch *' .CountLarge' ... haben?) – Gaffi

+2

Es ist wie die Frage, warum MS Excel 2003 und Excel 2007 hat: P. '.CountLarge' wurde mit Excel 2007 eingeführt und war mit früheren Versionen von Excel nicht verfügbar. Die 'Count'-Eigenschaft verwendet den Long-Datentyp, sodass der größte Wert, den es speichern kann, 2.147.483.647 ist. '.CountLarge' verwendet den Double-Datentyp, der bis zu 1.79 + E^308 verarbeiten kann. –

+1

+1: Aus Gründen der Abwärtskompatibilität können Sie eine Überprüfung basierend auf 'val (application.version)> = 12' einbeziehen und Cells.Countlarge wenn true und Cells.Count andernfalls verwenden. Beachten Sie, dass bei Verwendung von doubles zum Speichern von ganzen Zahlen auch ein Limit aufgrund der 15 Stellen der Genauigkeit ~ 2^50 erreicht werden kann, aber dies übersteigt die Gittergröße 2^20 * 2^14 = 2^34. –

Verwandte Themen