VBA 1004 error : Application defined or object defined error - vba

I am a novice at Excel VBA and am running into an error 1004 while compiling a portion of the code:
Cells(i, j).Formula = _"=vlookup(Cells(i,1).Value,SKULifeCycle_Table_Temp!R1C1:R5000C500,match(Cells(1,j).Value,'SKULifeCycle_Table_Temp'!R1C1:R1C500,0),0)"
i and j have been defined previously as integers and are part of a for loop. Could anyone please help me out on this?

A few things wrong there:
First, you're using the literal text "Cells(i, 1).Value" and "Cells(1, j).Value" in the formula string. You would need to concatenate the values into the string like this:
Cells(i, j).FormulaR1C1 = "=vlookup(" & Cells(i,1).Value & ",SKULifeCycle_Table_Temp!R1C1:R5000C500,match(" & Cells(1,j).Value & ",'SKULifeCycle_Table_Temp'!R1C1:R1C500,0),0)"
Second, you used the .Formula property but passed R1C1 style references, so you should use the .FormulaR1C1 property (as I did above).
Third, if the values in the cells that you are using for the lookup values are text, you need to enclose them in quotes:
Cells(i, j).FormulaR1C1 = "=vlookup(""" & Cells(i,1).Value & """,SKULifeCycle_Table_Temp!R1C1:R5000C500,match(""" & Cells(1,j).Value & """,'SKULifeCycle_Table_Temp'!R1C1:R1C500,0),0)"
or use the addresses (in R1C1 format) instead:
Cells(i, j).FormulaR1C1 = "=vlookup(RC1,SKULifeCycle_Table_Temp!R1C1:R5000C500,match(R1C,'SKULifeCycle_Table_Temp'!R1C1:R1C500,0),0)"

One issue that is clear (maybe the cause of the whole error), is that variables are being used within a string. So, what does that mean? I'll simplify using the code below as a template:
Sub Test1()
Dim i as Integer
Dim j as Integer
i = 2
j = 3
Cells(i, j).Value = "The row number is i and the column number is j"
End Sub
In the Cells line, it correctly refers to cell C2, which is the second row and third column. But what value is inserted into the cell? It's literally "The row number is i and the column number is j" using the letters, and not their corresponding numbers. Similarly, in your case, the formula will read: VLOOKUP(CELLS(i,1)... using the letter i, which is incorrect.
Additionally, a cell's formula doesn't use the CELLS syntax. You instead need to build a string using the variables. It would look a lot like:
"=VLOOKUP(" & Cells(i, 1).Address & "SKULifeCycle_Table_Temp!R1C1:R5000C500, Match(" & Cells(i, 1)Address ... "
Try to build out your formula string and refer back to this post with any specific questions.

Related

Writing a formula with concatenated parts into a cell

Scenario: I have a code that should write a formula to a worksheet cells. This formula is for an API to retrieve some value. My formula is inside a loop (this is done for multiple columns) and references the first row for an identifier.
The original formula:
=FS(B1;"FI(DATE,,DATE)")
The modified formula with the floating reference (inside the loop):
For i = 1 To lColumn
If wb.Worksheets("Dates").Cells(i, 1).Value <> "" Then
wb.Worksheets("Dates").Cells(i,2).value = "=FS(" & i & "1;"FI(DATE,,DATE)")"
End If
Next i
Where lColumn is some pre-defined number.
Issue: I keep getting the "Unexpected end of statement" error in the formula part of the loop.
What I already tried: I tried different variations, repositioning the "s and 's, for example:
wb.Worksheets("Dates").Cells(i,2).value = "'"=FS(" & i & "1;"FI(DATE,,DATE)")""
or
wb.Worksheets("Dates").Cells(i,2).value = "'=FS(" & i & "1;"FI(DATE,,DATE)")"
or
wb.Worksheets("Dates").Cells(i,2).value = "'""=FS(" & i & "1;"FI(DATE,,DATE)")"
and so on. But the error still persists.
Question: What is the proper way to do this operation?
Working with formulas in VBA is a little bit tricky:
To write a formula, use the range.formula property, not the .value.
You have to write the formula as if you are using an english Excel. Parameter-separator is comma (not semicolon).
If a formula needs a quote, double it so that the VBA compiler understands that you want a quote within a string.
I find it helpfull to write a formula into a variable before assigning it - you can check in the debugger if it is exactly how it should before assigning it.
To check how the formula should look like, write it into a cell, change to the VBA-editor, open the immediate window and write ? activecell.formula
Try (untested as the formula you need is not valid to us):
with wb.Worksheets("Dates")
dim f as string, adr as string
adr = cells(i, 1).address(false, false) ' get rid of Dollar signs
f = "=FS(" & adr & ",""FI(DATE,,DATE)"")"
.Cells(i, 2).formula = f
end with
wb.Worksheets("Dates").Cells(i,2).formula = "=FS(" & Cells(1, i).Address(0,0) & ";""FI(DATE,,DATE)"")"
There may be a better way to convert the column number to a letter (which is the problem you are having, along with the double quotes)!

How can I insert variable into formula in VBA

Can anyone solve this?
Sub test
Dim i as integer
For I = 1 to 10
ActiveCell.Offset(0, 2).Formula = "=Sum(E15,&i&)"
Next I
End Sub
your actual goal is unclear
you may want to start form this code
Sub test()
Dim i As Integer
For i = 1 To 10
cells(i, 4).Formula = "=Sum(E" & i & ":E15)"
Next
End Sub
and adjust it to your needs, knowing that:
it currently writes in cells "D1:D10"
since cells(i, 4) references a cell in 4th column (i.e.: column "D") 4 and i row, and we're inside a loop where i is looping through 1 to 10
so if:
you want to reference a different column then just change 4 to the proper column index
you want to reference a different row then just change i to the proper row index (may be some i+2 if you need to iterate through 1 to 10 but start writing from row 3)
the formula written in those cells is:
=SUM(E1:E15) in D1,
=SUM(E2:E15) in D2,
....
=SUM(E10:E15) in D10.
so just change "=Sum(E" & i & ":E15)" to your actual needs
You're close, trying to use ampersands (&) to concatenate strings.
ActiveCell.Offset(0, 2).Formula = "=Sum(E15," & i & ")"
Use the ampersands between strings to merge them, not inside strings.

Changing a cell formula based on for loop iteration

I am trying to insert and change a counta formula based on the iteration of the for loop. The problem I am facing is that even though the code runs without error, nothing happens. The totalrow variable is consistently 0. I'm not sure where I am going wrong here. All the variable have been initialized outside the loop. CurrentColname is string, countUsedCols is long, totalRows is long.
For i = 2 To countUsedCols
ActiveSheet.Cells(3, i).Select
currentColName = ActiveSheet.Cells(3, i).Value
If currentColName = "Valid From" Then
totalrow = ActiveWorkbook.Sheets("Customer_Facing_View").Range("AR1").Formula = "=COUNTA($" & i & ":$" & i & ")"
totalrow = ActiveWorkbook.Sheets("Customer_Facing_View").Range("AR1").Value
A couple of things.
In vba when you put X=Y=Z X becomes a Boolean value based on whether y = z or not.
So when you write:
totalrow = ActiveWorkbook.Sheets("Customer_Facing_View").Range("AR1").Formula = "=COUNTA($" & i & ":$" & i & ")"
Totalrow is returning false because the formula in that cell is not the same as the string you have provided.
Second your COUNT A will resolve to a row not a column. i is a number and not a letter.
So remove the totalrow = from the first expression and change the range reference.
ActiveWorkbook.Sheets("Customer_Facing_View").Range("AR1").Formula = "=COUNTA(" & Columns(i).Address &")"
I guess you would like to write a formula into Cell AR1 to calculate the number of rows (with the first totalrow statement); and get that value back (with the second totalrow statement). But I believe the first totalrow statement is wrong as Scott indicated. You need change it.
Also for the Counta formula you need to include your original worksheet name otherwise it just count the column in the Customer_Facing_View worksheet.

Convert Excel array formula VBA

I'm trying to do "vlookup" with 2 different criteria(Column A and G values) using "Index" and "Match" functions.
and here is the line i used for the Excel command.
=INDEX(Database!A:KG,MATCH(1,(Database!A:A='TempSheet'!A2)*(Database!G:G='TempSheet'!G2),0),10)
How would I do it with VBA? It's keep giving me the error message "Compile error: Expected end of statement".
Selection= _
"=Index(DB.Range("A:KG"), Match(1, (DB.Range("A" = Temp.Range("A" & i).Value)) * (DB.Range("G" = Temp.Range("G" & i).Value)), 0), 10)"
Thanks
Every time you use a spreadsheet formula inside a VBA code, you need to precede it with <Excel.WorksheetFunction.> or <Application.WorksheetFunction.>.
For example:
Application.WorksheetFunction.Match
instead of Match only.
I have had little luck getting array formulas to work correctly via VBA, and use the 'IFERROR' as a workaround like so:
=IFERROR(VLOOKUP(A1, Database!A:Z,1,FALSE),VLOOKUP(B1, Database!A:Z,1,FALSE))
This function will attempt to match A1, and in case of a #VALUE error, it will match B1.
To get this kind of formula populated on a sheet in VBA, you can loop down your sheet using the '.formula' approach.
' get length of source data
Dim RowCount As Long
RowCount = ThisWorkbook.Sheets("Database").Cells(Rows.Count, 1).End(xlUp).Row
' now starting from row 2 to preserve headings
For i = 2 To RowCount
ThisWorkbook.Sheets("Summary").Cells(i, 1).Formula = "=IF(ISERROR(SEARCH(""ISO"",V" & i & ")),""Order type not supported"",""Transit"")"
ThisWorkbook.Sheets("Summary").Cells(i, 6).Formula = "=IFERROR(TEXT(VLOOKUP(B" & i & ",Database!A:N,7,FALSE),""dd-mmm-yyyy HH:MM AM/PM""),"""")"
Next
Not exactly what you were after, but hope it helps!

Excel VBA Match function not working

I'm using INDEX and MATCH functions to pull data which is concatenated string of G2 and H2 from column D (sorry I don't have enough points to attach pic). Column D has INDEX(column A and column B) and columns A and B have values till 12th row. MATCH is working fine giving me the position as 6 on the worksheet. But when I use this in VBA code as shown below,INDEX is working in the VBA code (can be seen through MsgBox) but MATCH function which would allot value to the variable 'check' isn't working. I have been breaking my head for really long. Need help from experts here. Somebody please tell me where am I going wrong?
Sub testindex()
Dim check As Long
Set sh = Sheets("Sheet1")
For j = 1 To 11
'Index value is correctly shown
MsgBox "Index Value=" & Application.WorksheetFunction.Index(sh.Range("A2:B12"), j, 1) & Application.WorksheetFunction.Index(sh.Range("A2:B12"), j, 2)
'Cells(7, 4)=ISA737775 same as G2&H2
MsgBox "Cells(7,4)=" & Cells(7, 4)
check = Application.WorksheetFunction.Match(Cells(7, 4), Application.WorksheetFunction.Index(sh.Range("A2:B12"), j, 1) & Application.WorksheetFunction.Index(sh.Range("A2:B12"), j, 2), 0)
Next j
End Sub
Thanks
Match expects the second paramater to be in the form of a range. When you call match through VBA that range actually needs to be a range object, not just some string like "A1:A12" or whatever it is that your concatenated Index formulas output.
At any rate, you are iterating already, so why not just call those values directly instead of pulling their values through Index?
check = Application.WorksheetFunction.Match(Cells(7, 4), sh.Range("A" & 2 + j).value & sh.Range("B" & 2 + j), 0)
Which is writing the same exact thing but without having to use a taxing INDEX function in VBA to do it. Note that this still won't work because the second parameter of match is still just a string which is a concatenated value from Column A and Column B. You could convert to a range by sticking them in the range object with:
check = Application.WorksheetFunction.Match(Cells(7, 4), sh.Range(sh.Range("A" & 2 + j).value & sh.Range("B" & 2 + j)), 0)
I'm assuming that the values in A and B are actual cell names that when concatenated will make a range. Like when j=1 then the it would be like check=Match(Cells(7,4), sh.Range("G2:H50"), 0) or something...