VBA: no coinciden los tipos (error 13 en tiempo de ejecución)

¿Qué es un error de falta de coincidencia de tipo?

A menudo, puede ocurrir un error de falta de coincidencia cuando ejecuta su código VBA. El error evitará que su código se ejecute por completo y señalará mediante un cuadro de mensaje que este error debe resolverse

Tenga en cuenta que si no ha probado completamente su código antes de la distribución a los usuarios, este mensaje de error será visible para los usuarios y provocará una gran pérdida de confianza en su aplicación de Excel. Desafortunadamente, los usuarios a menudo hacen cosas muy peculiares con una aplicación y, a menudo, son cosas que usted, como desarrollador, nunca consideró.

Se produce un error de falta de coincidencia de tipos porque ha definido una variable utilizando la instrucción Dim como un tipo determinado, p. entero, fecha y su código está tratando de asignar un valor a la variable que no es aceptable, por ejemplo cadena de texto asignada a una variable entera como en este ejemplo:

Aquí hay un ejemplo:

Haga clic en Depurar y la línea de código infractora se resaltará en amarillo. No hay ninguna opción en la ventana emergente de error para continuar, ya que se trata de un error importante y no hay forma de que el código pueda ejecutarse más.

En este caso particular, la solución es cambiar la instrucción Dim a un tipo de variable que funcione con el valor que le está asignando a la variable. El código funcionará si cambia el tipo de variable a "Cadena", y probablemente también desee cambiar el nombre de la variable.

Sin embargo, cambiar el tipo de variable necesitará reiniciar su proyecto, y tendrá que ejecutar su código nuevamente desde el principio, lo que puede ser muy molesto si se trata de un procedimiento largo.

Error de falta de coincidencia causado por el cálculo de la hoja de trabajo

El ejemplo anterior es muy simple de cómo se puede producir un error de desajuste y, en este caso, se remedia fácilmente.

Sin embargo, la causa de los errores de desajuste suele ser mucho más profunda que esto y no es tan obvia cuando intenta depurar su código.

Como ejemplo, suponga que ha escrito código para recoger un valor en una determinada posición en una hoja de trabajo y contiene un cálculo que depende de otras celdas dentro del libro de trabajo (B1 en este ejemplo)

La hoja de trabajo se parece a este ejemplo, con una fórmula para encontrar un carácter en particular dentro de una cadena de texto

Desde el punto de vista del usuario, la celda A1 es de formato libre y puede ingresar cualquier valor que desee. Sin embargo, la fórmula busca una aparición del carácter "B" y, en este caso, no se encuentra, por lo que la celda B1 tiene un valor de error.

El código de prueba a continuación producirá un error de falta de coincidencia porque se ingresó un valor incorrecto en la celda A1

1234 Sub TestMismatch ()Atenuar MyNumber como enteroMyNumber = Hojas ("Hoja1"). Rango ("B1"). ValorEnd Sub

El valor en la celda B1 ha producido un error porque el usuario ha ingresado texto en la celda A1 que no se ajusta a lo esperado y no contiene el carácter "B"

El código intenta asignar el valor a la variable "MyNumber" que se ha definido para esperar un número entero, por lo que obtiene un error de falta de coincidencia.

Este es uno de estos ejemplos en los que la verificación meticulosa de su código no proporcionará la respuesta. También debe buscar en la hoja de trabajo de dónde proviene el valor para averiguar por qué sucede esto.

En realidad, el problema está en la hoja de trabajo y la fórmula en B1 debe cambiarse para que se resuelvan los valores de error. Puede hacerlo utilizando la fórmula "SI.ERROR" para proporcionar un valor predeterminado de 0 si no se encuentra el carácter de búsqueda.

Luego puede incorporar código para verificar un valor cero y mostrar un mensaje de advertencia al usuario de que el valor en la celda A1 no es válido

12345678 Sub TestMismatch ()Atenuar MyNumber como enteroMyNumber = Hojas ("Hoja1"). Rango ("B1"). TextoSi MyNumber = 0 entoncesMsgBox "El valor en la celda A1 no es válido", vbCriticalSalir de SubTerminara siEnd Sub

También puede usar la validación de datos (grupo Herramientas de datos en la pestaña Datos de la cinta) en la hoja de cálculo para evitar que el usuario haga lo que quiera y cause errores en la hoja de trabajo en primer lugar. Solo permítales ingresar valores que no causen errores en la hoja de trabajo.

Puede escribir código VBA basado en el evento Change en la hoja de trabajo para verificar lo que se ingresó.

También bloquee y proteja la hoja de trabajo con contraseña, de modo que los datos no válidos no se puedan ingresar

Error de discordancia causado por valores de celda ingresados

Los errores de coincidencia pueden ser causados ​​en su código al traer valores normales de una hoja de trabajo (sin error), pero donde el usuario ha ingresado un valor inesperado, p. un valor de texto cuando esperabas un número. Es posible que hayan decidido insertar una fila dentro de un rango de números para poder poner una nota en una celda que explique algo sobre el número. Después de todo, el usuario no tiene idea de cómo funciona su código y que acaba de desequilibrarlo todo al ingresar su nota.

El siguiente código de ejemplo crea una matriz simple llamada "MyNumber" definida con valores enteros

Luego, el código itera a través de un rango de celdas de A1 a A7, asignando los valores de celda a la matriz, usando una variable "Recuento" para indexar cada valor.

Cuando el código alcanza el valor del texto, se produce un error de falta de coincidencia y todo se detiene.

Al hacer clic en "Depurar" en la ventana emergente de error, verá la línea de código que tiene el problema resaltado en amarillo. Al pasar el cursor sobre cualquier instancia de la variable "Coun" dentro del código, podrá ver el valor de "Coun" donde el código ha fallado, que en este caso es 5

Mirando la hoja de trabajo, verá que los 5th la celda hacia abajo tiene el valor de texto y esto ha causado que el código falle

Puede cambiar su código poniendo una condición que verifique primero un valor numérico antes de agregar el valor de la celda a la matriz

12345678910111213 Sub TestMismatch ()Dim MyNumber (10) como entero, cuenta como enteroCuenta = 1HacerSi Coun = 11 Entonces Salga HacerIf IsNumeric (Sheets ("sheet1"). Cells (Coun, 1) .Value) ThenMyNumber (recuento) = Hojas ("hoja1"). Celdas (recuento, 1) .ValorDemásMyNumber (Coun) = 0Terminara siCuenta = Cuenta + 1CírculoEnd Sub

El código usa la función "IsNumeric" para probar si el valor es realmente un número y, si lo es, lo ingresa en la matriz. Si no es un número, ingresa el valor de cero.

Esto asegura que el índice de la matriz se mantenga en línea con los números de fila de celda en la hoja de cálculo.

También puede agregar código que copie el valor del error original y los detalles de la ubicación en una hoja de trabajo de "Errores" para que el usuario pueda ver qué es lo que ha hecho mal cuando se ejecuta su código.

La prueba numérica usa el código completo de la celda, así como el código para asignar el valor a la matriz. Se podría argumentar que esto debería asignarse a una variable para no seguir repitiendo el mismo código, pero el problema es que necesitaría definir la variable como una "Variante", lo cual no es lo mejor que se puede hacer.

También necesita la validación de datos en la hoja de trabajo y proteger la hoja de trabajo con contraseña. Esto evitará que el usuario inserte filas e ingrese datos inesperados.

Error de discordancia causado al llamar a una función o subrutina mediante parámetros

Cuando se llama a una función, normalmente se le pasan parámetros a la función utilizando tipos de datos ya definidos por la función. La función puede ser una ya definida en VBA, o puede ser una función definida por el usuario que ha creado usted mismo. Una subrutina a veces también puede requerir parámetros

Si no se adhiere a las convenciones de cómo se pasan los parámetros a la función, obtendrá un error de falta de coincidencia

12345678 Sub CallFunction ()Dim Ret como enteroRet = MyFunction (3, "prueba")End SubFunción MyFunction (N como entero, T como cadena) como cadenaMiFunción = TFunción final

Hay varias posibilidades aquí para obtener un error de discrepancia

La variable de retorno (Ret) se define como un número entero, pero la función devuelve una cadena. Tan pronto como ejecute el código, fallará porque la función devuelve una cadena y esta no puede entrar en una variable entera. Curiosamente, ejecutar Debug en este código no detecta este error.

Si coloca comillas alrededor del primer parámetro que se pasa (3), se interpreta como una cadena, que no coincide con la definición del primer parámetro en la función (entero)

Si convierte el segundo parámetro en la llamada a la función en un valor numérico, fallará con una falta de coincidencia porque el segundo parámetro en la cadena está definido como una cadena (texto)

Error de falta de coincidencia causado por el uso incorrecto de funciones de conversión en VBA

Hay una serie de funciones de conversión que puede utilizar en VBA para convertir valores a varios tipos de datos. Un ejemplo es "CInt", que convierte una cadena que contiene un número en un valor entero.

Si la cadena que se va a convertir contiene caracteres alfabéticos, obtendrá un error de discrepancia, incluso si la primera parte de la cadena contiene caracteres numéricos y el resto son caracteres alfabéticos, p. "123abc"

Prevención general de errores de coincidencia

Hemos visto en los ejemplos anteriores varias formas de lidiar con posibles errores de desajuste dentro de su código, pero hay varias otras formas, aunque pueden no ser las mejores opciones:

Defina sus variables como tipo de variante

Un tipo de variante es el tipo de variable predeterminado en VBA. Si no usa una instrucción Dim para una variable y simplemente comienza a usarla en su código, automáticamente se le asigna el tipo de Variant.

Una variable Variant aceptará cualquier tipo de datos, ya sea un entero, un entero largo, un número de precisión doble, un valor booleano o de texto. Esto suena como una idea maravillosa, y te preguntas por qué todos no solo establecen todas sus variables en variante.

Sin embargo, el tipo de datos de la variante tiene varias desventajas. En primer lugar, ocupa mucha más memoria que otros tipos de datos. Si define una matriz muy grande como variante, consumirá una gran cantidad de memoria cuando se esté ejecutando el código VBA y podría causar fácilmente problemas de rendimiento.

En segundo lugar, generalmente tiene un rendimiento más lento que si utiliza tipos de datos específicos. Por ejemplo, si realiza cálculos complejos utilizando números de coma decimal flotante, los cálculos serán considerablemente más lentos si almacena los números como variantes, en lugar de números de doble precisión.

El uso del tipo de variante se considera una programación descuidada, a menos que sea absolutamente necesario.

Utilice el comando OnError para manejar errores

El comando OnError se puede incluir en su código para lidiar con la captura de errores, de modo que si alguna vez ocurre un error, el usuario ve un mensaje significativo en lugar de la ventana emergente de error estándar de VBA

1234567 Sub ErrorTrap ()Atenuar MyNumber como enteroEn caso de error, vaya a Err_HandlerMyNumber = "prueba"Err_Handler:MsgBox "El error" & Err.Description & "ha ocurrido"End Sub

Esto evita efectivamente que el error detenga el buen funcionamiento de su código y permite al usuario recuperarse limpiamente de la situación de error.

La rutina Err_Handler podría mostrar más información sobre el error y a quién contactar al respecto.

Desde el punto de vista de la programación, cuando está utilizando una rutina de manejo de errores, es bastante difícil localizar la línea de código en la que se encuentra el error. Si está revisando el código usando F8, tan pronto como se ejecuta la línea de código ofensiva, salta a la rutina de manejo de errores y no puede verificar dónde está yendo mal.

Una forma de evitar esto es configurar una constante global que sea Verdadero o Falso (booleano) y usar esto para activar o desactivar la rutina de manejo de errores usando una declaración "Si". Cuando desee probar el error, todo lo que tiene que hacer es establecer la constante global en False y el controlador de errores dejará de funcionar.

1 Global Const ErrHandling = Falso
1234567 Sub ErrorTrap ()Atenuar MyNumber como enteroSi ErrHandling = True, entonces en caso de error, vaya a Err_HandlerMyNumber = "prueba"Err_Handler:MsgBox "El error" & Err.Description & "ha ocurrido"End Sub

El único problema con esto es que permite al usuario recuperarse del error, pero el resto del código dentro de la subrutina no se ejecuta, lo que puede tener enormes repercusiones más adelante en la aplicación.

Usando el ejemplo anterior de recorrer un rango de celdas, el código llegaría a la celda A5 y alcanzaría el error no coincidente. El usuario vería un cuadro de mensaje con información sobre el error, pero no se procesará nada de esa celda en adelante en el rango.

Utilice el comando OnError para eliminar errores

Esto utiliza el comando "En caso de error, reanudar a continuación". Esto es muy peligroso de incluir en su código, ya que evita que se muestren errores posteriores. Básicamente, esto significa que mientras su código se está ejecutando, si ocurre un error en una línea de código, la ejecución simplemente se moverá a la siguiente línea disponible sin ejecutar la línea de error, y continuará con normalidad.

Esto puede solucionar una posible situación de error, pero aún afectará a todos los errores futuros en el código. Entonces puede pensar que su código está libre de errores, pero de hecho no lo está y partes de su código no están haciendo lo que usted cree que debería estar haciendo.

Hay situaciones en las que es necesario usar este comando, como si está eliminando un archivo usando el comando 'Kill' (si el archivo no está presente, habrá un error), pero la captura de errores siempre debe volverse a cambiar. inmediatamente después de donde podría ocurrir el error potencial usando:

1 En caso de error Goto 0

En el ejemplo anterior de recorrer un rango de celdas, usando 'On Error Resume Next', esto permitiría que el bucle continúe, pero la celda que causa el error no se transferirá a la matriz, y el elemento de la matriz para ese índice en particular tendría un valor nulo.

Conversión de los datos a un tipo de datos para que coincida con la declaración

Puede usar las funciones de VBA para alterar el tipo de datos de los datos entrantes para que coincida con el tipo de datos de la variable receptora.

Puede hacer esto al pasar parámetros a funciones. Por ejemplo, si tiene un número que se encuentra en una variable de cadena y desea pasarlo como un número a una función, puede usar CInt

Hay varias de estas funciones de conversión que se pueden usar, pero estas son las principales:

CInt: convierte una cadena que tiene un valor numérico (por debajo de + o - 32,768) en un valor entero. Tenga en cuenta que esto trunca los puntos decimales

CLng: convierte una cadena que tiene un valor numérico grande en un entero largo. Los puntos decimales se truncan.

CDbl: convierte una cadena que contiene un número de coma decimal flotante en un número de doble precisión. Incluye puntos decimales

CDate: convierte una cadena que contiene una fecha en una variable de fecha. Depende parcialmente de la configuración en el Panel de control de Windows y su configuración regional sobre cómo se interpreta la fecha

CStr: convierte un valor numérico o de fecha en una cadena

Al convertir de una cadena a un número o una fecha, la cadena no debe contener nada más que números o una fecha. Si hay caracteres alfabéticos, esto producirá un error de discrepancia. A continuación, se muestra un ejemplo que producirá un error de discrepancia:

123 Prueba secundaria ()MsgBox CInt ("123abc")End Sub

Prueba de variables dentro de su código

Puede probar una variable para averiguar qué tipo de datos es antes de asignarla a una variable de un tipo en particular.

Por ejemplo, puede verificar una cadena para ver si es numérica usando la función "IsNumeric" en VBA

1 MsgBox IsNumeric ("123prueba")

Este código devolverá False porque aunque la cadena comienza con caracteres numéricos, también contiene texto, por lo que no pasa la prueba.

1 MsgBox IsNumeric ("123")

Este código devolverá True porque son todos caracteres numéricos

Hay una serie de funciones en VBA para probar varios tipos de datos, pero estas son las principales:

IsNumeric: prueba si una expresión es un número o no

IsDate: prueba si una expresión es una fecha o no

IsNull: prueba si una expresión es nula o no. Un valor nulo solo se puede poner en un objeto de variante; de ​​lo contrario, obtendrá un error "Uso no válido de Nulo". Un cuadro de mensaje devuelve un valor nulo si lo está utilizando para hacer una pregunta, por lo que la variable de retorno debe ser una variante. Tenga en cuenta que cualquier cálculo que utilice un valor nulo siempre devolverá el resultado de nulo.

IsArray: prueba si la expresión representa una matriz o no

IsEmpty: prueba si la expresión está vacía o no. Tenga en cuenta que vacío no es lo mismo que nulo. Una variable está vacía cuando se define por primera vez, pero no es un valor nulo

Sorprendentemente, no hay ninguna función para IsText o IsString, lo que sería realmente útil

Objetos y errores de coincidencia

Si está utilizando objetos como un rango o una hoja, obtendrá un error de falta de coincidencia en el tiempo de compilación, no en el tiempo de ejecución, lo que le advierte que su código no va a funcionar.

123456 Sub TestRange ()Atenuar MyRange como rango, I tan largoEstablecer MyRange = Range ("A1: A2")Yo = 10x = UseMyRange (I)End Sub
12 Función UseMyRange (R como rango)Función final

Este código tiene una función llamada "UseMyRange" y un parámetro que se transmite como un objeto de rango. Sin embargo, el parámetro que se transmite es un entero largo que no coincide con el tipo de datos.

Cuando ejecuta el código VBA, se compila inmediatamente y verá este mensaje de error:

El parámetro infractor se resaltará con un fondo azul.

En general, si comete errores en el código VBA al usar objetos, verá este mensaje de error, en lugar de un mensaje de falta de coincidencia de tipos:

Va a ayudar al desarrollo del sitio, compartir la página con sus amigos

wave wave wave wave wave