Pourquoi ai-je des problèmes de l'affectation d'une Gamme à une gamme de Variantes
Je vais avoir quelques problèmes avec certains TRÈS simples lignes de code. Laissez-moi en détail les faits et voir si quelqu'un d'autre peut reproduire ce comportement. Si quelqu'un peut répliquer j'aimerais obtenir une explication de pourquoi cela se produit.
Donc permet moi de commencer avec un très simple ligne de code QUI FONCTIONNE:
Dim arr() As Variant
arr = Range("A1:A10")
ce n'est comme prévu, arr
est attribué les Valeurs de A1:A10
maintenant, pourquoi ne pas en faire la ligne suivante de code de travail?
Dim arr() As Variant
arr = WorkSheets("Sheet1").Range("A1:A10")
J'obtiens une Erreur d'Exécution '13' incompatibilité de Type, même si la même gamme a été attribué à la matrice, juste sans la Feuille de calcul de la valeur.
Mais
Dim arr As Variant
arr = Worksheets("Sheet1").Range("A1:A10")
Et
Dim arr() As Variant
arr = Application.Transpose(Application.Transpose(Worksheets("Sheet1").Range("A1:A10")))
FONCTIONNE
Maintenant, avant de vous répondre s'il vous plaît laissez-moi vous donner quelques faits.
Dim arr() As Variant
arr = Worksheets(1).Range("A1:A10")
Ne Fonctionne Pas
et à l'aide de Sheets
en place de Worksheets
également se donnent tous la même erreur.
J'ai fait sûr que c'est la même feuille que l'actif référencé feuille en utilisant Range("A1:A10").Worksheet.Name
Suivant le code de travail et en effet, dit Sheet1
dans la sortie.
Pas d'autres classeurs sont ouverts donc il ne peut pas être référence à un autre classeur.
Maintenant le dernier bout de code ne fait qu'ajouter à ma confusion, car il fonctionne tout à fait!
Dim arr() As Variant
Dim SampleRange As Range
Set SampleRange = Worksheets("Sheet1").Range("A1:A10")
arr = SampleRange
Donc, en utilisant la MÊME GAMME définie de la même façon sur la même feuille fonctionne maintenant quand je l'affecter à une Variable de Portée. et de l'utiliser! Et comme prévu, cela fonctionne à la fois avec le WorkSheets
et Sheets
fonction indépendamment de la définition de la feuille (je peux utiliser l'index ou le Nom de la feuille de calcul et tous les beaux travaux)
Si ça aide quelqu'un, je suis en train de tester cela avec Excel 2007 sur un ordinateur Windows XP. Je n'ai pas encore testé sur toutes les autres machines, mais j'ai l'intention de tester sur 2003 et 2010 sur Windows 7 et Windows 8, n'ont tout simplement pas eu la chance encore.
Mise à JOUR: Pas sûr à 100% si c'est le même problème qu'avec le tableau, mais à partir d'une faible profondeur de vue, il semble être:
Range("B1:B3") = Range("A1:A3")
Le code ci-dessus ne fonctionnera pas, même si A1:A3 est peuplée, les dates, les valeurs numériques, les chaînes, la formule de quoi que ce soit, il va écrire les blancs en B1:B3
Mais
Range("B1:B3").Value = Range("A1:A3").Value
Et
Range("B1") = Range("A1")
ne travail!
Aussi de travail est:
Range("B1:B3") = Application.Transpose(Application.Transpose(Range("A1:A3")))
arr = Worksheets(1).Range("A1:A10").Value
œuvres- Ce n'est pas pour moi, je n'ai également tester avec
Value2
, rien ne fonctionne tout a été testé, juste oublié que j'ai testé, j'obtiens toujours la même erreur. Incompatibilité de Type, de l'OS et des versino d'excel que vous utilisez? - Excel 2003 / Excel 2013, win 8.1.
- Je pense que cela a quelque chose à voir avec le comportement par défaut de la référence à
Range
. SouventRange(X)
peut être utilisé pour se référer au contenu de la gammeX
. Si nous l'instancier, comme l'ensemble des biens d'une Feuille de calcul, je pense que nous nous y référons codé en dur "de la Gamme-ness" de celui-ci. Cependant, cela n'explique pas pourquoi il à une variable, il contourne. Heureusement, quelqu'un peut venir l'expliquer.Value
elle n'en résout, pour moi, de toute façon, si. Win7, XL2010. - C'est intéressant, quand vous simplement utilisé
arr = Worksheets(1).Range("A1:A10")
fait-il? comme leValue
propriété est généralement la propriété par défaut utilisé dans VBA lorsqu'une propriété n'est pas spécifiée? Et même si ce n'pourquoi la variable prendre une autre propriété, alors la matrice? - Et juste pour être clair... j'ai l'expérience de l'original de votre les problèmes de la même SAUF que quand j'ai ajouter
.Value
à la fin. Si je le fais, pas d'erreurs dans l'un des tests ci-dessus. - Je n'ai aucune idée de pourquoi la seconde méthode ne fonctionne pas lorsque le premier ne. Ce n'est généralement pas comment vous pouvez affecter une plage directement à un tableau cependant: généralement vous déclarer
arr
commeVariant
, et non pas comme un tableau de variants, qui est ce que vous avez ici. En utilisant juste une simple Variante, vous ne verrez pas ce problème. L'ajout de.Value
à la fin de votre deuxième méthode résout également le problème, ce doit être quelque chose lié à compter sur la propriété par défaut étant différente entre les deux approches. arr = Worksheets(1).Range("A1:A10")
ne fonctionne pas.arr = ActiveSheet.Range("A1:A10")
ne fonctionne pas ainsi. Mais `arr = ActiveSheet.Range("A1:A10").Valeur " fonctionne sans aucun problème..je suis confus, parce que.Value
doit être la propriété par défaut deRange
objet- changer
Dim arr() As Variant
àDim arr As Variant
résout le problème pour moi etarr = Worksheets(1).Range("A1:A10")
fonctionne très bien! - J'ai assigné le de NOMBREUX de NOMBREUX tableaux dans le passé, tout simplement jamais remarqué ce bug que j'ai généralement toujours Dim et Affecter toutes mes variables au début de tout le code, juste pour la facilité de mise à jour dans le futur, mais juste quelque chose que je jouais avec et remarqué, je pense que j'ai d'abord appris à dim les tableaux d'un an ou deux il ya, basé sur un article de la Puce Pearson. Je vais essayer et le lien de l'article si je peux le retrouver si.
- est correcte. Retrait
()
, en laissantDim arr As Variant
va corriger le problème sur leWorksheets...
partie. Maintenant, comment faire pour comprendre tout cela. 😀 - Ouais gradation dans la manière fixe aussi pour moi, pour l'enregistrement de l'article, je parlais de l'été Ici
- Une AUTRE CHOSE ÉTRANGE:
Dim arr() As Variant: arr = Sheet1.Range("A1:A10")
bien travailler. Notez que j'ai utiliséarr()
avec des crochets - Peut-être quelque chose de complètement indépendants, mais lors de l'utilisation de vous code EXACT il a bien fonctionné, mais lors de l'utilisation d'une feuille avec un nom différent, dans mon testin j'ai utilisé de l'Échantillon (première renommé de la feuille, puis a couru votre code et changé seulement la feuille Sheet1 à l'Échantillon, et j'ai obtenu une erreur de compilation.
- Je vois que la page: je suppose que je n'ai jamais utilisé cette notation, mais vous avez raison, c'est comment Puce est-il...
- à cette image. Votre fiche a deux noms: pour VBA variable et le nom de l'onglet (entre parenthèses). I. e. si vos feuilles a nom "VBE_intro" (comme sur la photo), vous devez utiliser
Sheet1.Range("a1")
dans le code VBA. Est-il vrai pour vous? Je veux dire que vous devez utiliserSheeti
correspondant au nom de "l'Échantillon" entre parenthèses pour l'utiliser comme variable VBA - Probablement lié à la liaison de la Feuille de calcul de référence comme la liaison tardive (
Dim arr() As Variant: Dim sheet As Worksheet: Set sheet = Worksheets("Sheet1"): arr = sheet.Range("A1:A10")
) fonctionne très bien. En utilisant VarPtr de lire l'adresse de retour deRange("A1:A10")
(et liaison tardive), ils retournent les références de l'objet alors queWorksheets("Sheet1").Range("A1:A10")
retourne un objet à l'intérieur d'une variante (décalage de 1==9), qui est probablement la prévention de la Plage->Variante() de conversion. - Travaillant à l'extérieur de ce que vous avez dit, je pense que c'est parce que
Range
n'est pas un membre de laWorksheets
classe, mais au lieu de laWorksheet
classe, afin d'obtenir leRange
variable à partir de feuilles de travail de la classe, excel a déjà pour convertir les paramètres Saisis dans leWorksheets
classe de convertir cet objet dans leWorksheet
objet qu'il a besoin pour obtenir leRange
membre de cet objet. Mais je ne comprends pas, c'est que Si j'utilise leVarType
ouTypeName
fonction à la fois des représentations qu'ils reviennent tous de la mêmeRange
type, donc avec ce que vous dites, il semble - que les deux méthodes retournent
Range
les variables de type, où un autre renvoie laValue
bien tandis que l'autre n'a pas, le même raisonnement explique pourquoi, lorsque l'indiquer explicitement laValue
Bien travaillé pour à peu près tout le monde. Je suppose que je ne suis pas à un niveau de programmation, alors je peux comprendre le POURQUOI de cela, et c'est exactement pourquoi j'ai posé la question. Je suis à la recherche d'un niveau plus profond de connaissances ici. @simoco tag vous également que vous semblait intéressé comme I. - Que tout est Ok, mais je ne comprends pas pourquoi cela fonctionne
Dim arr As Variant: arr = Worksheets("Sheet1").Range("A1:A10")
mais ce doesen"Dim arr() As Variant: arr = Worksheets("Sheet1").Range("A1:A10")
? Note à l'parenthèses aprèsarr()
- Dang Nab-bits, qui contredit tout ce que j'ai Pensée je viens de comprendre. Parce que clairement, c'EST de retourner la Valeur de la propriété de la Gamme de Classe dans les deux situations.
- ok, pourquoi cela ne fonctionne pas
Dim arr() As Variant: arr = Worksheets("Sheet1").Range("A1:A10")
, mais cela fonctionneDim arr() As Variant: arr = Worksheets("Sheet1").Range("A1:A10").Value
(pour moi et pour BK201)? C'est à moi de les confondre, car.Value
est par défaut de la propriété.. - Que je PENSE est expliqué dans mon double commentaire, que, sans indiquer explicitement la vous voulez que le
Value
Propriété de laRange
classe, qu'après qu'excel fait tout le travail de conversionWorksheets("Sheet1")
à laWorksheet
fonction (notez l'absence deS
, parce que, selon la boîte à outils en VBARange
n'EST PAS un membre deWorkSheets
) que vous êtes, puis en demandant pour laRange
Propriété de laWorksheet
classe et c'est EXACTEMENT ce qu'il est de retour, pas une Propriété de laRange
classe, mais laRange
Objet lui-même. Mais alors que les processus de pensée obtient jeté hors - Lorsque vous prenez en compte cela fonctionne
Dim arr As Variant: arr = Worksheets("Sheet1").Range("A1:A10")
- je pense que Tim déjà dit. il y a une différence entre
arr As Variant
etarr() as Variant
.arr As Variant
peut contenir des objets.arr() As Variant
ne peut pas et ne peuvent donc pas être attribuées à des Objets. suivant cette logique, excel ne peut pas assumer la propriété par défautValue
lors de l'attributionarr = Worsheets("Sheet1").Range("A1:A10")
déjà, elle échoue. - C'est 100% faux et est avérée fausse par le fait que
Dim arr() As Variant : arr = Range("A1:A10")
fonctionne sans problèmes,arr() as Variant
EST assigné avec des objets et excel NE supposons la propriété par défautValue
lors de l'attribution... - j'ai posté une réponse pour vous aider à faire voir mon point de vue. désolé, c'est long à monter dans un commentaire, donc je l'ai posté en tant que réponse.
Vous devez vous connecter pour publier un commentaire.
Non, ce n'est pas un bug.
Les experts de poster des réponses précédentes ont déjà très bien expliqué dans les détails. Je vais garder l'explication du faible et, donc, laissez-moi savoir si vous avez encore des questions.
Nous allons comprendre nos objets. J'ai créé ce petit tableau qui montre clairement ce que nous manutention, de sorte qu'il n'y est pas de confusion.
Vous pouvez également ajouter une
Watch
pour voir laType
pour un objet particulier, comme indiqué dans l'image ci-dessous.Quand vous dites
Excel sait que la propriété par défaut est
.Value
. Mais dans d'autres cas, il ne le sait pas, car Excel n'est pas un lecteur d'esprit ou disons assez intelligent pour comprendre que vous souhaitez utiliserWorksheets("Sheet1").Range("A1:A10")
comme unRange
ou unVariant
Une fois que vous spécifiez explicitement votre objet
Range
Excel sait ce que vous voulez. Par exemple cela fonctionne.Range
pour chaque élément..Value
est la propriété par défaut et quand il ne l'est pas 🙂because Excel is not a mind reader or let's say intelligent enough
. c'est le fait le plus important.Permettez-moi de clarifier mon commentaire.
Il ne rentre pas à commenter pour que je poste comme réponse juste au moins de vider mon point de vue.
ça veut dire quoi?
Cela signifie que
arr
peut prendre n'importe quelle forme (par exemple. integer, string, array, object et tous les autresVariable Type
)ça veut dire quoi?
Cela signifie que
arr()
variable de tableau peut stocker différentsData
types.Qui exclut
Objects
ouCollection of Objects
.Maintenant, pourquoi les ouvrages suivants:
Cela fonctionne aussi:
Ci-dessus fonctionne parce que vous n'essayez pas d'attribuer
Collections of Objects
dans un tableau.Au lieu de cela, l'affectation d'une entité spécifique ou de la valeur.
Range
est un objet, mais pas unCollection of Objects
.N ° 1 exemple est direct, sans accès à
Sheets Collection Object
.Le même est vrai avec
N ° 2 puisque vous travaillez avec
Sheet1
qui est unSheet
Objet, mais pasCollection of Sheet Objects
.N ° 3 est auto-explicatif, vous affectez
.Value
à unarr
tableau.N ° 4 fonctionne parce que
rng
est déjà unRange
objet parSet
qui est nouveau n'est pas unCollection of Objects
.Donc:
ne fonctionne pas car Excel va lire ce que d'essayer d'attribuer
Object
deSheets Collection of Objects
et donc erreur se produit.J'espère que cela a un sens un peu.
Range("A1:A3")
etSheets("Sheet1").Range("A1:A3")
sontRange Objects
indépendamment de ce que vous dites, c'est un fait. Vous pouvez taper les jeter dans de nombreuses façons et de toutes les façons vous de tester les deux versions ils seront de retour unRange
type. Et à cause de cela DEUX doit implicitement travail ou à l'échec. Aussi, vous vous êtes trompé en affirmant queSheets("Sheet1")
retourne une Collection d'Objets de la Feuille.Sheets
lui-même EST une collection de feuilles et en passant le paramètre de nom de feuille les Feuilles de Classe renvoie uneSheet
objet n'est pas toute sa collection. Comme Mehow je pense que c'est juste un bug.Je dirais un Tableau de quelque Chose n'est pas la même chose en tant que quelque Chose, puisque ce quelque Chose peut être un Tableau de quelques autres choses. Si vous définissez quelque chose comme un Tableau, ce que vous attribuez à il doit être un Tableau, un Tableau de Nombre, Texte, la Plage, les objets de Graphique, etc.
Quand les choses fonctionnent que nous ne nous attendons pas, je crois qu'il est intégré dans la conversion de type de données qui rend les choses plus faciles pour nous la plupart du temps. Cette conversion peut être un complément d'objet direct, pas les propriétés d'un objet.
Par exemple, les Lignes et les Colonnes sont de type Long, mais vous pouvez jeter le Byte/type Double chez elle:
Cells(1,1.5)
donne la valeur deCells(1,2)
Vous n'avez pas à convertir de 1,5 à Long; Excel-t-il tout en arrière-plan pour vous.
Lorsque vous définissez un tableau de quelque chose et d'attribuer des choses, Excel n'type de correspondance derrière la scène et de définir des valeurs lorsque cela est possible.
Vérifier avec ceux-ci dans la fenêtre exécution:
?typename(Range("A1:A10").Value)
vous donneVariant()
<-- c'est pourquoi il travaille surDim arr() As Variant
sans aucun problème?typename(Range("A1:A10"))
vous donneRange
. Mais si vous l'affectez àarr
oùDim arr() As Variant
, Excel convertit la Plage à un Tableau en utilisant les valeurs de cette Gamme.Toutefois, Excel semble échouer la conversion si elle ne dispose pas d'un accès direct à l'objet, sauf si vous avez créé de mémoire pour elle. Par exemple:
Le code ci-dessus est bien beau, mais il ne peut pas convertir et attribuer
arr = ThisWorkbook.Worksheets("Sheet1").Range("A1:A10")
en une seule fois, sauf si vous jetez un tableau (ThisWorkbook.Worksheets("Sheet1").Range("A1:A10").Value
est de type Variante()).?typename(Worksheets("Sheet1").Range("A1:A10"))
AUSSI vous offre une Portée encore il n' PAS travailler avecDim arr() As Variant
, c'est kidn de gênant combien de personnes peuvent prendre les informations avec pas de véritable preuve de faits, afin de sauvegarder l'état, en plus de dire que c'est ce qu'il est. Ensuite, utilisez une instruction en pensant que c'est un énoncé factuel.