Este artigo explica com detalhes o uso de variáveis e constantes no VBA.
- Introdução
- Atribuição de Variáveis
- Por Que Usar Variáveis?
- Declaração de Variáveis
- Tipos de Dados
- Declaração Sem Especificar o Tipo de Dados
- Declaração Especificando o Tipo de Dados
- Padronização de Nomenclatura de Variáveis
- Declaração por Sufixos
- Escopo de Variáveis
- Vetores
- Constantes
Introdução
Variáveis são elementos nomeados e podem armazenar uma informação ou referência sobre um procedimento ou objeto. Normalmente, são empregadas para reduzir o tempo gasto no desenvolvimento de um programa, facilitar a leitura do código e/ou melhorar o desempenho na execução.
Basicamente, você primeiro dá um valor à variável e depois utiliza esse valor conforme sua necessidade. O termo técnico empregado para dar um valor a uma variável é atribuição.
Variáveis devem, obrigatoriamente, possuir um nome. As regras para dar nome a uma variável são as mesmas que se aplicam a um procedimento, que são:
- Iniciar com uma letra;
- Ter de 1 até um máximo de 255 caracteres;
- Não ter espaços (no entanto, é permitido o uso de sublinhado, exemplo:
Endereço_Comercial
) - Não ter nome igual a uma das palavras chaves do VBA, como
If
,End
,Next
,String
, etc.
Atribuição de Variáveis
O exemplo abaixo faz atribuição da variável Idade
ao valor 20:
Sub Atribuição1() Idade = 20 MsgBox "O valor da variável 'Idade' é " & Idade & "." End Sub
O VBA utiliza o símbolo de igualdade para representar uma atribuição, o que pode confundir um pouco iniciantes. Nunca faça analogia de atribuições com equações matemáticas. Idealmente, uma representação adequada de atribuição no VBA seria, em minha opinião:
Tecnicamente, o VBE está avaliando a expressão à direita da igualdade e então aloca esse resultado à variável que está à esquerda da equação. Idade
está recebendo o valor 20. Outro exemplo:
Idade = 8 + 12
O VBE avalia a expressão à direita e então atribui esse valor à variável Idade
. Nesse caso, é semelhante em atribuir diretamente o valor 20.
Veja a linha de código abaixo:
Idade = Idade + 1
É um exemplo em que realmente não devemos interpretar atribuições como equações matemáticas. No exemplo acima, Idade
passará a ter um novo valor, que será seu valor atual acrescido de um.
Você pode utilizar variáveis para fazer atribuição de outras variáveis:
Sub Atribuição2() SalárioBruto = 1250.57 Impostos = 113.26 SalárioLíquido = SalárioBruto - Impostos MsgBox "Salário líquido: " & SalárioLíquido End Sub
Note que o separador decimal no VBA é vírgula, e não ponto. Isso acontece porque o VBA é baseado no sistema de unidades americano, e o separador decimal desse sistema é o ponto. Por outro lado, eles utilizam a vírgula como separador de milhares. Logo, 1.234.567,89 no Brasil escreve-se 1,234,567.89 nos Estados Unidos.
Você pode alterar o valor de variáveis várias vezes durante a execução de uma macro.
Por Que Usar Variáveis?
Considere o código abaixo, numa aplicação em Excel:
Sub Usar1() Range("A1").Value = Range("B2").Value Range("A3").Value = Range("B2").Value * 2 Range("A4").Value = Range("B2").Value * 3 Range("A6").Value = Range("B2").Value * 4 End Sub
Esse código atribui valores às células A1, A3, A4 e A6 para algum múltiplo do valor da célula B2, que poderia representar na prática uma taxa de juros.
A expressão Range("B2").Value
aparece quatro vezes. Isso torna a leitura do código confusa para o programador, além de que escrevê-la dá trabalho, já que possui 17 caracteres.
Pode ser que não entenda esses detalhes agora, mas vale a pena expor: toda a vez que se faz referência a um objeto Range
dessa forma, o VBA procura o endereço da célula B2 numa planilha, avalia o objeto e então avalia sua propriedade Value
, aumentando o overhead do programa (overhead é um conjunto de instruções implícitas processadas pelo VBA que você não vê nas linhas de código do VBE). No exemplo acima, a expressão que obtém o valor da célula B2 é responsável por fazer essa maratona de processamentos acontecer quatro vezes.
Uma forma de melhorar o código é mostrada a seguir:
Sub Usar2() Juros = Range("B2").Value Range("A1").Value = Juros Range("A2").Value = Juros * 2 Range("A3").Value = Juros * 3 Range("B2").Value = Juros * 4 End Sub
Criamos uma variável chamada Juros
e estamos atribuindo o valor Range("B2").Value
a ela. Observe como a leitura do código ficou mais clara. Além disso, escrever Juros
é bem mais fácil que escrever toda a expressão que retorna o valor da célula B2.
Em termos de desempenho, houve também melhoria. A expressão Range("B2").Value
é avaliada apenas uma vez para passar seu valor à Juros
, poupando overheads desnecessários e aumentando a velocidade de execução do programa. Claro que nesse pequeno exemplo a questão de desempenho quase não faz diferença, mas é importante se educar em relação a esses detalhes desde cedo, já que seus programas assumirão maior complexidade e tempo gasto para executar.
É importante ressaltar que nesse exemplo o valor da variável Juros
não está vinculado ao valor da célula B2. Isto é, se você alterar o valor da célula B2, terá que atribuir novamente Juros
a seu valor, no contrário, Juros
manterá seu valor original.
Declaração de Variáveis
A declaração de uma variável tem a finalidade de avisar ao compilador a sua existência.
No VBA, a palavra chave para declarar uma variável é Dim
. O código abaixo declara as variáveis FirstName
, HouseNumber
, MonthlyTax
e BirthDate
:
Sub Declaração() Dim FirstName Dim HouseNumber Dim MonthlyTax Dim BirthDate FirstName = "Felipe" Debug.Print FirstName HouseNumber = 12 Debug.Print HouseNumber MonthlyTax = 1.15 Debug.Print MonthlyTax BirthDate = "10/05/1983" Debug.Print BirthDate End Sub
Você deve declarar uma variável antes de utilizá-la. Boas práticas de programação sugerem que você faça todas as declarações de variáveis no início de um procedimento. Não há problemas em declarar variáveis e não utilizá-las no código, mas isso é considerado uma má prática de programação, pois confundir o entendimento do mesmo.
Você não pode declarar duas variáveis com o mesmo nome num procedimento. Se tentar fazer isso, obterá o erro de compilação a seguir:
Declaração de Variável Obrigatória
É possível que o VBE te obrigue a declarar as variáveis que usa num módulo procedimento. Isso é recomendado e possui vantagens. Para ilustrar uma delas, veja o simples código a seguir, que deve exibir sempre a mensagem de pontos referente ao apelido de Felipão:
Sub Obrigar() sApelido = "Benzadeus" Select Case sApelido Case "Benzadeus": PontosTabelaA = 28 Case "Creuza": PontosTabelaA = 24 Case "Doutor": PontosTabelaA = 7 End Select MsgBox sApelido & " tem " & PotosTabelaA & " pontos!" End Sub
Esse código compilará normalmente, mas não funcionará como esperado, mostrando a mensagem abaixo:
Se você observar bem, há um erro ortográfico na variável PontosTabela
na expressão que exibe a caixa de mensagem. Esse tipo de erro é difícil e desgastante para um programador detectar. Se num código desse tamanho já é suficiente para nos fazer perder tempo, imagine quando o projeto possui centenas de linhas de código.
Option Explicit
Você pode digitar a instrução Option Explicit
na Seção de Declaraçãoo módulo para obrigar a declarar todas as variáveis que utiliza nos procedimentos desse módulo.
Se você executar uma macro e o VBE notar que no procedimento a ser interpretado há uma ou mais variáveis que não foram declaradas, você obterá um erro de compilação. Ao tentar executar o código acima, será notificado que há uma variável não declarada e o VBE irá indica-la:
Agora, vamos declarar as variáveis que estamos utilizando (sApelido
e PontosTabela
) e tentar executar o código novamente. O VBE ainda nos notificará que existe uma variável não declarada:
É nesse momento em que o programador interpreta o erro e chega à conclusão que errou ao escrever o nome de uma das variáveis que vai usar em sua macro. Agora, basta corrigir PotosTabelaA
para PontosTabelaA
, executar o código normalmente e verificar o resultado esperado:
Requerer Declaração de Variável
É possível que o VBE insira automaticamente a instrução Option Explicit
no início de todos os módulos que você criar. Para tal, vá no menu Ferramentas >> Opções:
Na aba Editor, habilite a caixa de seleção Requerer declaração de variável e então em OK:
Tipos de Dados
O VBA trabalha com vários tipos de dados, como números, textos e objetos. Para prosseguir o estudo de declaração de variáveis, é fundamental entender quais tipos de dados o VBA suporta e os limites de cada um. Leia a página a seguir:
Declaração Sem Especificar o Tipo de Dados
Voltemos às declarações de variáveis já usadas nesta página:
Dim FirstName Dim HouseNumber Dim MonthlyTax Dim BirthDate
FirstName
, HouseNumber
, MonthlyTax
e BirthDate
são variáveis declaradas que tem seu valor posteriormente atribuídos por tipos de dados de texto, numérico e data, respectivamente. Como o VBA não sabe qual tipo de dados cada variável irá assumir, ele atribui inicialmente um tipo de dados Variant
a elas. Logo, a seção de declaração desse exemplo é equivalente às declarações mostradas abaixo:
Dim FirstName As Variant Dim HouseNumber As Variant Dim MonthlyTax as Variant Dim BirthDate As Variant
As declarações acima estão qualificadas porque estamos informando ao VBA o tipo de dados de cada variável, no caso, todas Variant
.
Variant
é opcional, indico-o na declaração para melhor coesão na leitura das declarações.A Atribuição Implícita do Tipo de Dados Variant
O exemplo abaixo ilustra melhor como as variáveis sofrem alterações em seu tipo de dados:
Sub Flexões() Dim FirstName As Variant Dim HouseNumber As Variant Dim MonthlyTax As Variant Dim BirthDate As Variant Debug.Print TypeName(FirstName) 'Empty FirstName = "Felipe" Debug.Print TypeName(FirstName) 'String Debug.Print TypeName(HouseNumber) 'Empty HouseNumber = 12 Debug.Print TypeName(HouseNumber) 'Integer Debug.Print TypeName(MonthlyTax) 'Empty MonthlyTax = 1.15 Debug.Print TypeName(MonthlyTax) 'Double Debug.Print TypeName(BirthDate) 'Empty BirthDate = "10/05/1983" Debug.Print TypeName(BirthDate) 'Date End Sub
Veja como o tipo de dados Variant
flexiona ao decorrer da macro. É interessante notar que ele define como padrão um tipo de dados Integer
para números inteiros e Double
para decimais. Claro, se você atribuísse um valor maior que o limite do tipo de dados Integer
como 100.000, o VBA flexionaria o tipo de dados dessa variável a um Long
. E se utilizasse um valor maior que Long
, haveria conversão para um Double
.
Como se não bastasse, uma variável Variant
pode alterar seu tipo de dados várias vezes numa macro:
Sub VáriasFlexões() Dim var As Variant var = "Benzadeus" Debug.Print TypeName(var) 'String var = 125345647 Debug.Print TypeName(var) 'Long var = 1.15 Debug.Print TypeName(var) 'Double var = "10/05/1983" Debug.Print TypeName(var) 'Date End Sub
O nome dessa capacidade do tipo de dados Variant
é atribuição implícita de tipo de dados.
Declaração Especificando o Tipo de Dados
O código abaixo declara as variáveis FirstName
como um tipo de dados de texto String
, HouseNumber
como número inteiro Long
e, MonthlyTax
como um número decimal Single
e BirthDate
como uma data Date
:
Sub Qualificada() Dim FirstName As String Dim HouseNumber As Long Dim MonthlyTax As Single Dim BirthDate As Date FirstName = "Felipe" HouseNumber = 12 MonthlyTax = 1.15 BirthDate = "10/05/1983" End Sub
Você poderia fazer a declaração no exemplo acima como mostrado a seguir também, caso quisesse:
Dim FirstName As String, HouseNumber As Long, MonthlyTax As Single, BirthDate As Date
No entanto, pessoalmente prefiro declarar cada variável numa linha.
Quando você especifica o tipo de dados numa declaração, não pode atribuir tipos de dados diferentes dos quais seu tipo de dados aceita. Por exemplo, se você declarar uma variável como Long, mas atribuir um texto a ela, como mostrado abaixo:
Sub AtribuiçãoInválida() Dim MyVar As Long MyVar = "Benzadeus" MsgBox MyVar End Sub
Ao executar o código a seguinte tela de erro será apresentada:
Evite, sempre que possível, declarar variáveis como Variant
. Uma Variant
aloca um espaço grande na memória no tempo de compilação e sua conversão implícita de tipo de dados durante a execução gera um overhead desnecessário na macro.
Se você utiliza macros que processam muitas vezes uma variável que é um número inteiro, declare como Long
. Se for texto, String
e números decimais, Single
. Se for números decimais ou inteiros muito grandes, utilize Double
. O tipo de dados Decimal
é utilizado apenas em situações muito específicas.
Você pode restringir o tamanho de uma sequência de texto declarando uma variável como String
, inserindo um sinal de multiplicação e o número de caracteres máximo que a variável armazenará:
Sub Limitado() Dim sNome As String * 15 sNome = "Felipe Costa Gualberto" 'Mostrará apenas os 15 primeiros caracteres, isto é Felipe Costa Gu Debug.Print sNome End Sub
Nesse caso, se você fizer uma atribuição que seja maior que o espaço alocado pela variável, ela armazenará um valor truncado.
Cuidado ao Declarar mais de uma Variável numa Instrução
Fique atento porque o código a seguir:
Dim lNumber1 As Long Dim lNumber2 As Long Dim lNumber3 As Long
É diferente de:
Dim lNumber1, lNumber2, lNumber3 As Long
Neste último, apenas lNumber
está declarado como tipo de dados Long. lNumber1
e lNumber2
estão sem o tipo de dados especificados, então assumem o tipo de dados Variant
. Essa declaração é equivalente a:
Dim lNumber1 As Variant, lNumber2 As Variant, lNumber3 As Long
Logo, numa declaração de mais de uma variável, você é obrigado a especificar o tipo de dados de cada variável declarada:
Dim lNumber1 As Long, lNumber2 As Long, lNumber3 As Long
Padronização de Nomenclatura de Variáveis
Se você se deparar num extenso código com uma variável chamada MeuNome
, sem ver sua declaração, poderá deduzir com baixas chances de errar que ela é um tipo de dados String
. No entanto, se encontrar um chamado MeuValor
, não saberá se é um número inteiro ou decimal; pior, não saberá nem se é um número.
Algumas práticas de programação sugerem que é interessante representar no nome da variável o tipo de dados ao qual ela se refere, na forma de sufixo. Então, a variável Nome
, se é um tipo de dados String
, deverá ser chamada de sNome
(se o programador optou por usar três letras de prefixo) ou strNome
(se o programador optou por usar o mínimo de letras de prefixo possíveis). A tabela abaixo exemplifica a como nomear variáveis com a regra de prefixos:
A seguir, a tabela para tipos de dados não numéricos:
Já utilizei essa técnica de nomenclatura extensivamente. No entanto, ultimamente tenho preferido dar nome às variáveis como DataNascimento
(que obviamente é uma data), PrimeiroNome
(que obviamente é um texto). Como este site é antigo, você verá várias notações diferentes, pois já mudei meus hábitos várias vezes.
Existe uma discussão interessante sobre esse assunto neste link/.
Declaração por Sufixos
Ao invés de escrever na forma literal o tipo de dados desejado, você pode declara-los por um sufixo. A tabela a seguir mostra as equivalências dos tipos de dados com seus respectivos símbolos:
As declarações a seguir são equivalentes:
Sub SufixosLiterais() Dim sNome As String Dim lIdade As Long Dim dPosição As Double End Sub Sub SufixosSímbolos() Dim sNome$ Dim lIdade& Dim dPosição# End Sub
Pessoalmente, faço uso da forma SufixosLiterais
. É mais claro e não exige que decoremos símbolos desnecessariamente. Minha dica é: fuja de declarações por sufixo, elas são terríveis.
Escopo de Variáveis
Dependendo de como se declara uma variável, ela pode assumir escopo de nível de procedimento, de módulo ou global. Esse importante assunto é discutido na página a seguir:
Vetores
Vetores são elementos nomeados ou expressões que podem armazenar mais de um dado. Clique no link a seguir para ler a página sobre vetores:
Constantes
O valor de uma variável pode alterar durante a execução de um programa. No entanto, precisamos às vezes nos referir a valores que nunca alteram. Para essas entidades, damos o nome de constantes.
Usar constantes em seu programa ao invés de representar seu valor literal é uma boa ideia, já que se você precisar alterar o nome desse valor literal, fará isso somente uma vez.
Suponha que você tenha um programa que exiba centenas de caixas de mensagem distintas, e que o título de cada caixa seja o nome do seu programa. O código de uma das caixas de mensagem é mostrado abaixo:
MsgBox "Erro durante a execução do programa", , "South Refining"
Se um dia você quiser criar um novo sistema para a empresa North Refining, terá que revisitar todo código de seu projeto e fazer as alterações de um nome por outro, com o risco de deixar algo para trás ou errar na substituição. Essa é uma ótima situação de se utilizar uma constante ao invés de expressar um valor literal.
No geral, se uma expressão literal aparece no meu código mais de uma vez, crio uma constante para usa-la em seu lugar.
Usar constantes é prático porque em sua declaração você já atribui seu valor. Assim como variáveis, a regra de escopo se aplica também em constantes: você pode trabalhar com constantes de nível de procedimento, módulo e globais.
O exemplo abaixo mostra a declaração de cada uma dessas constantes:
Public Const PI = 3.1415 'Global Const MODULE_NAME = "AmbienteXL" 'Nível de módulo Sub Main() Const PROGRAM_NAME = "North Refining" 'Nível de procedimento '...código... End Sub
Você pode especificar o tipo de dados de uma constante, se quiser:
Const PROGRAM_NAME As String = "North Refining"
Se você tentar atribuir um valor a uma constante, obterá um erro de compilação:
Constantes Pré-Definidas
O VBA e os aplicativos Office disponibilizam muitas constantes pré-definidas, e você pode utiliza-las sem declarar nem precisar saber seu valor. O exemplo a seguir mostra uma caixa de mensagem com um ícone de informação:
MsgBox "Relatório gerado com sucesso!", vbInformation
A constante vbInformation
é passada ao argumento Buttons
da caixa de mensagem, e quando esse argumento tem o valor de vbInformation
(que na verdade é 64), MsgBox
exibe o ícone de informação. A vantagem dessas constantes é que é bem mais fácil saber que vbInformation
se relaciona com uma caixa de mensagem de informação, em detrimento do número solto 64.
Outra vantagem é o fato do VBE exibir, em tempo de desenvolvimento, as possíveis constantes numa janela suspensa chamada Intellisense:
Na verdade, vbInformation
é o membro de uma enumeração, mais especificamente da enumeração vbMsgBoxStyle
. Recomendo ler mais sobre enumerações na página a seguir:
Deixar um comentário
Você precise estar logged in para postar um comentário.