Проблемы с синтаксисом Vlookup и пользовательским вводом
-
20-12-2019 - |
Вопрос
Я пытаюсь создать макрос, который сравнивает два пользовательских листа, а затем перемещает различия на разные листы в зависимости от того, почему они отличаются.
Код сначала запрашивает ввод новейших данных и открывает этот лист.Затем он запрашивает местоположение старых данных для сравнения, но не открывает их.Он добавляет необходимые листы для копирования.
Затем он просматривает столбец ячейка за ячейкой в поисках соответствующего серийного номера во второй рабочей книге (в основном это делается для того, чтобы убедиться в правильности сравнения данных в случае, если форматирование отключено).Как только он находит соответствующий серийный номер, он сравнивает второй серийный номер для обеих записей и в зависимости от того, отличается ли он от нового ввода на одном из листов.
Основная проблема, с которой я столкнулся, связана с VLookup.Он содержит несколько ошибок 424, 1004 и ошибок выражения компиляции.Мне нужно небольшое руководство относительно того, почему у него возникают эти проблемы.Я искал и нашел много информации о необходимости использования скобок для ссылки на файл, но когда я точно следую этим форматам, это выдает ошибку выражения.
Любой совет приветствуется.
Sub Compare()
'Open workbooks
''Worksheet 1
Dim filter As String
Dim caption As String
Dim WB1FN As String
Dim WB1 As Workbook
filter = "Excel Sheets (*.xlsx),*.xlsx"
caption = "Please select newest equipment file"
MsgBox (caption)
WB1FN = Application.GetOpenFilename(filter, , caption)
If WB1FN = "False" Then
MsgBox "File not selected to import"
Exit Sub
End If
Set WB1 = Application.Workbooks.Open(WB1FN)
''Worksheet 2
Dim caption2 As String
Dim WB2FN As String
filter = "Excel Sheets (*.xlsx),*.xlsx"
caption2 = "Please select previous equipment file"
MsgBox (caption2)
WB2FN = Application.GetOpenFilename(filter, , caption)
If WB2FN = "False" Then
MsgBox "File not selected to import"
Exit Sub
End If
'Comparing data
''MS find and compare
Dim MS1 As String
Dim ESN1 As String
Dim ESN2 As String
Dim LastRow As Long
Dim i As Integer
Dim d As Integer
Dim n As Integer
Dim Filename As String
d = 4
n = 4
Set WB1 = ActiveWorkbook
'Create sheets
Sheets.Add(After:=ActiveWorkbook.Sheets(ActiveWorkbook.Sheets.Count)).Name = "A"
Sheets.Add(After:=ActiveWorkbook.Sheets(ActiveWorkbook.Sheets.Count)).Name = "B"
Sheets.Add(After:=ActiveWorkbook.Sheets(ActiveWorkbook.Sheets.Count)).Name = "C"
'Gets the last row number
ActiveWorkbook.Sheets(1).Activate
LastRow = ActiveSheet.UsedRange.SpecialCells(xlCellTypeLastCell).Row
For i = 4 To LastRow
''Assigning MS1,ES1,ES2
MS1 = Cells(i, 6)
ESN1 = Cells(i, 15)
ESN2 = Application.WorksheetFunction.VLookup(MS1, '[" & WB2FN & "]Sheet1'! [R3C6:R10000C15], 10, False)
''Compare ESN and copy data
If ESN2 <> ESN1 Then
cell.EntireRow.Copy Sheets(2).Cells(d, 1)
n = d + 1
ElseIf Application.WorksheetFunction.IsNA(ESN2) = "TRUE" Then
cell.EntireRow.Copy Sheets(4).Cells(n, 1)
n = n + 1
End If
Next i
'X find and copy
Dim OEM As String
ActiveWorkbook.Sheets(2).Activate
LastRow = ActiveSheet.UsedRange.SpecialCells(xlCellTypeLastCell).Row
n = 3
i = 3
For i = 3 To LastRow
''Check for X
OEM = Cells(i, 4)
If OEM = "x" Then
cell.EntireRow.Copy Sheets(3).Cells(n, 1)
n = n + 1
End If
Next i
MsgBox "Compare successful"
End Sub
Решение
have brackets to reference a file
Вы можете использовать этот подход, только если вы присваиваете формулу ячейке или диапазону.
Пример:
Dim myformula As String
myformula = "=VLOOKUP(" & MS1 & _
",'[" & WB2FN & "]Sheet1'! [R3C6:R10000C15], 10, False)"
Range("A1").Formula = myformula
Но если вы используете Функция рабочего листа VBA, вам нужно каким-то образом получить доступ к базе данных или таблице, из которых вы извлекаете данные во время выполнения.Это означает, что вы должны передавать объекты с аргументами, а не строки, как вы делаете выше.
Что -то вроде:
'~~> the rest of your code before Vlookup here
Dim wb As Workbook
Dim mytable As Range
Set wb = Workbooks.Open(WN2FN, , True) '~~> read only, avoid errors when file in use
Set mytable = wb.Sheets("Sheet1").Range("F3:O10000")
On Error Resume Next '~~> to handle when Vlookup returns #N/A or errors out
ESN2 = Application.WorksheetFunction.VLookup(MS1, mytable, 5, 0)
If Err.Number <> 0 Then myvalue = CVErr(xlErrNA)
On Error GoTo 0 '~~> reset error handling to trap other errors
Debug.Print ESN2
Я только что привел ту часть, где вы используете Функция рабочего листа ВПР.Вы можете использовать остальную часть вашего кода перед этим.В основном приведенный выше код:
- присваивает исходную таблицу переменной и передает ее непосредственно в ВПР аргументы.
- Использование ВПР через Рабочая функция VBA для получения данных.
Примите к сведению OERN (При Возникновении ошибки Возобновите Работу Следующим образом) рутина и OEG0 (При Ошибке Goto 0).
В VBA, когда a Функция рабочего листа возвращает ошибку (например.#N / A для Vlookup), код выдает ошибку и останавливает выполнение.Там нет никакого IFERROR ( ОШИБКА) как у нас в формулах рабочего листа.Поэтому вам нужно справиться с этим, используя процедуры обработки ошибок.
Также обратите внимание, что лучше полностью квалифицировать объекты, над которыми вы работаете.
Это хорошее место для начала оптимизации ваших кодов и избежания ошибок во время выполнения.