我现在正在努力解决VLookup问题。我正在努力做一些真正超出我头脑的事情,但我认为只要稍加帮助,我就可以做到。
]
到目前为止,我有这样的事情:
Sub DeletarIndices()
indice = InputBox("Digite o IC/IV Desejado", "GBG Pneus")
Set planilhaV = Sheets("IV")
Dim vValores As String
sResult = Application.VLookup("Y", planilhaV.Range("A2:B11"), 2)
Application.ScreenUpdating = False
Application.Calculation = xlCalculationManual
Dim i As Long
For i = Range("A" & Rows.Count).End(xlUp).Row To 1 Step -1
If Not (Range("A" & i).Value > sResult) Then
Range("A" & i).EntireRow.Delete
End If
Next i
Application.Calculation = xlCalculationAutomatic
Application.ScreenUpdating = True
End Sub
当我运行代码时,会打开一个输入框并询问将在代码中使用的值。该字母将转换为数字,并将用作比较以删除较低的值。但... 就在这里:
If Not (Range("A" & i).Value > sResult) Then
字母仍然是一个数字,所以当它检查表格时,只会删除低于该值的数字,而不会删除值较低的字母。我需要的就是那个。分析这些字母并删除行,而不是数字。
感谢任何可以帮助我的人!
答案 0 :(得分:1)
假设您的字母优先顺序始终是按字母顺序排列的,那么您不需要将字母转换为数字,您可以简单地将字母与字母进行比较。我还要注意,你确定最后一行(Range("A" & Rows.Count).End(xlUp).Row
)的方法并不好,我建议你找一个更可靠的方法。
假设您的数据以您显示的方式呈现 - 将H列中的数据作为3个字符的代码,其中字母是最后一个字符(例如" 91B"," 89D"等等) - 让我们一步一步:(注意没有查找工作表planilhaV了)
1)声明我们的变量
Dim indice As String ' To hold our user input letter
Dim rowLetter As String ' To hold the current row letter value
Dim firstRow As Long ' First row of your data
Dim lastRow As Long ' Last row of your data
Dim currentRow As Long ' Current row for your loop counter
Dim sht As Worksheet ' To hold the worksheet you're working on
2)分配一些值
Set sht = ThisWorkbook.Worksheets("*WORKSHEET NAME*") ' Use the name of your worksheet
firstRow = 1
lastRow = sht.Range("A" & Rows.Count).End(xlUp).Row
3)获取用户输入
indice = UCase(InputBox("Digite o IC/IV Desejado", "GBG Pneus")) ' Convert user input to upper case and store
4)进行处理
For currentRow = lastRow To firstRow Step -1
rowLetter = UCase(Right(sht.Range("H" & currentRow).Value, 1)) ' Get letter from code in column H, converted to upper case
If rowLetter < indice Then ' Compare the letters, and if smaller than user input...
sht.Rows(currentRow).EntireRow.Delete ' Delete the row
End If
Next currentRow
那应该是这样做的。宣布您计划使用的所有变量是一个好主意,使用Option Explicit
将确保您无需先声明它就可以使用任何内容。
修改强>
@LeonVFX:如果字母的值不总是按字母顺序增加,那么你可以使用查找表,或者你可以在代码中进行比较。
如果您选择使用原始示例中的查找表,则可以按如下方式调整上面的代码:
Dim indice As String ' To hold our user input letter
Dim indiceValue As Long ' To hold the numeric value of our user input letter
Dim rowLetter As String ' To hold the current row letter
Dim rowLetterValue As Long ' To hold the numeric value of the current row letter
Dim firstRow As Long ' First row of your data
Dim lastRow As Long ' Last row of your data
Dim currentRow As Long ' Current row for your loop counter
Dim sht As Worksheet ' To hold the worksheet you're working on
Dim planilhaV As Worksheet ' To hold your lookup worksheet
Set sht = ThisWorkbook.Worksheets("*WORKSHEET NAME*") ' Use the name of your worksheet
Set planilhaV = ThisWorkbook.Worksheets("IV") ' As in your original example
firstRow = 1
lastRow = sht.Range("A" & Rows.Count).End(xlUp).Row
indice = UCase(InputBox("Digite o IC/IV Desejado", "GBG Pneus")) ' Convert user input to upper case and store
indiceValue = CLng(Application.VLookup(indice, planilhaV.Range("A2:B11"), 2, False)) ' Creating numeric indice value with lookup table
For currentRow = lastRow To firstRow Step -1
rowLetter = UCase(Right(sht.Range("H" & currentRow).Value, 1)) ' Get letter from code in column H, converted to upper case
rowLetterValue = CLng(Application.VLookup(rowLetter, planilhaV.Range("A2:B11"), 2, False)) ' Creating numeric value for current row letter with lookup table
If rowLetterValue < indiceValue Then ' Compare the numeric letter values, and if smaller than user input...
sht.Rows(currentRow).EntireRow.Delete ' Delete the row
End If
Next currentRow
如果您发现它一次只删除一行,我的猜测是使用sht.Range("A" & Rows.Count).End(xlUp).Row
查找最后一行是因为您没有A栏中的任何数据?如果您的数据位于原始示例中的H列中,请将代码中的A
更改为H
,您应该没问题,或者尝试找到更可靠的方法来设置{{1变量值。
答案 1 :(得分:0)
在论坛上得到一些帮助之后,我得到了这个答案,如果有人碰到这样的话,我会把它留在这里。
' Verifies if the digit is a number. If it is, returns True, False if it isn't.
Function ehNumero(ByVal digito As String) As Boolean
a = Asc(digito)
If a >= 48 And a <= 57 Then
ehNumero = True
Else
enNumero = False
End If
End Function
' Separates the code in a numeric and a alphabetic part.
Function separaCodigo(ByVal codigo As String, ByRef numero As Integer, ByRef letras As String) As Boolean
p = 0
For i = 1 To Len(codigo)
digito = Mid(codigo, i, 1)
If Not ehNumero(digito) Then ' Found the point break when it finds the first non-numeric digit.
p = i
Exit For
End If
Next i
If p = 0 Or p = 1 Then
numero = 0
letras = ""
separaCodigo = False
Else
codigo = UCase(codigo)
numero = Int(Mid(codigo, 1, p - 1))
letras = Mid(codigo, p)
separaCodigo = True
End If
End Function
' Gets the values from the configuration table.
Function valorDasLetras(ByVal letras As String) As Integer
On Error GoTo trataErro
valorDasLetras = Application.VLookup(letras, Worksheets("Configuração").Range("A2:B11"), 2, False)
Exit Function
trataErro:
valorDasLetras = 0 '
End Function
'Deletes the lines in the table in the interval.
Function deletar(ByVal numero As Integer, letras As String) As Integer
valor = valorDasLetras(letras)
If valor = 0 Then
deletar = -1
Exit Function
End If
limInf = numero
limSup = valor
Dim dados As Worksheet
Set dados = ActiveWorkbook.ActiveSheet
Dim linhasPraDeletar As Range
totalLinhas = 0
linha = 1
Do While True
curCodigo = dados.Cells(linha, 7) ' Using Column G
If curCodigo = "" Then
Exit Do
End If
Dim curNumero As Integer
Dim curLetras As String
If Not separaCodigo(curCodigo, curNumero, curLetras) Then
deletar = -1
Exit Function
End If
' Gets the values for the letters from the table
curValor = valorDasLetras(curLetras)
If curValor = 0 Then
deletar = -1
Exit Function
End If
If curNumero < limInf Or curValor < limSup Then
If linhasPraDeletar Is Nothing Then
Set linhasPraDeletar = dados.Rows(linha)
Else
Set linhasPraDeletar = Union(linhasPraDeletar, dados.Rows(linha))
End If
totalLinhas = totalLinhas + 1
End If
linha = linha + 1
Loop
linhasPraDeletar.Select
linhasPraDeletar.EntireRow.Delete ' <===== Comment to select, but do not delete, the line
deletar = totalLinhas
End Function
' Run the code
Sub LimparValores()
'On Error GoTo trataErro
' Reads the user code
msg = "Input your code"
codigo = InputBox(msg, "Código")
If codigo = "" Then ' Cancelado
Exit Sub
End If
' Separates the user code number from letters
Dim numero As Integer
Dim letras As String
If Not separaCodigo(codigo, numero, letras) Then
MsgBox ("Invalid code: " & codigo)
Exit Sub
End If
' Calls the delete function
linhas = deletar(numero, letras)
If linhas = -1 Then
MsgBox ("There was an error with the code (the letter does not exist in configuration)")
Else
If linhas = 0 Then
MsgBox ("There are no rows in the interval - no row was deleted")
Else
MsgBox (linhas & " rows deleted!")
End If
End If
Exit Sub
trataErro:
MsgBox ("The code is not in the expected format.")
End Sub
希望将来帮助任何人!