Insert a variable inside Formula - excel

I have a cell in that contains the following:
=$H$10+1&","&B5+I10&","&(2*$D$2+$E$2)/2
The result of this formula is in this format:
14649,28.25,5.5
I want to use the formula VBA code. I want the number 1 in the $H$10+**1**&" to be the i of the for loop and the I10 in "&B5+I10&" to also change with the loop.
For i=1 to lastrow
.Range("X" & 13+i & "").Formula = "=$H$10+" & i & "" & "," & "B5+I" & i + 10 & "" & "," & "(2*$D$2+$E$2)/2"
Next i

Here code that can be used:
Sub mySub()
'=$H$10+1&","&B5+I10&","&(2*$D$2+$E$2)/2
Dim myRange As Range
Set myRange = Range("H:H").SpecialCells(xlCellTypeLastCell)
Dim myStr As String
'A=10 is for assigning first row in H as your data, hope no data upward from row 9 to row 1
For Baris = 10 To myRange.Row
On Error Resume Next
myStr = "=$H$10+" & Baris - 9 & "&"",""&B5+I" & Baris & "&"",""&(2*$D$2+$E$2)/2"
Range("K" & Baris).Formula = myStr
Next
End Sub

Related

How to Apply Formula to every cell in range and print result for each cell in cell zz new line

My goal is to be able to "translate" for lack of a better term; each cell in a sheet range into VBA.
This means I can instantly take an existing workbook and produce VBA to recreate it.
So I put this UDF together. It shows a cell as it would appear in VBA. R1C1 format
Function showformula(rng As Range)
If rng.HasArray = True Then
showformula = "{" & rng.Formula & "}"
Else
showformula = "Sheets(""" & ActiveSheet.Name & """). Range(""" & rng.Address & """)" & ".FormulaR1C1 = " & """" & rng.FormulaR1C1 & """"
End If
End Function
So 1)show a user select box for specifying a range. Then Click Proceed and 2) the above UDF reads for every cell in the specified range and 3) prints each cell's result on a new line in cell ZZ.
1 is easy enough to googlefu
but 2) & 3) I do not know how I would write it
https://www.reddit.com/r/excel/comments/brndla/how_to_apply_formula_to_every_cell_in_range_and/
Solution Occurred here
Sub BuildList()
Dim c As Range
Dim rngInput As Range
Dim rngOutput As Range
Dim i As Long
'Ask our user for stuff
Set rngInput = Application.InputBox("What cells do you want to read?", "Input", , , , , , 8)
Set rngOutput = Application.InputBox("Where do you want output to go?", "Output", , , , , , 8)
Application.ScreenUpdating = False
'Write the answers
For Each c In rngInput.Cells
rngOutput.Cells(1).Offset(i).Value = ShowFormula(c)
i = i + 1
Next c
Application.ScreenUpdating = True
End Sub
Function ShowFormula(rng As Range)
If rng.HasArray = True Then
ShowFormula = "{" & rng.Formula & "}"
Else
ShowFormula = "Sheets(""" & ActiveSheet.Name & """). Range(""" & rng.Address & """)" & ".FormulaR1C1 = " & """" & rng.FormulaR1C1 & """"
End If
End Function

Is there any way to step through more then one range of cells during the same For Each loop?

I am currently trying to create a loop that steps through 2 ranges of data. First range is b16-b35 next range is j16-j35. Currently I can only get 1 of the 2 loops to step through.
I started with a For While loop. Using i as a variable for 16-35. When I tried this method I couldnt get the msgbox to print the data. I moved to a For each loop. This gave me the ability to step through 1 cell but not the other.
If [D8] = 2 Then
Dim r As Range
Dim j As Range
Dim jcell As Range
Dim cell As Range
Set r = Range("B16:B35")
Set j = Range("J16:J35")
For Each cell In r
For Each hcell In j
If cell = "" Or cell = "N/A" Then GoTo ENDGAME
MsgBox "pn is " & cell & " route is " & jcell
Next jcell
Next cell
ENDGAME:
End IF
Current method causes the loop to step through all of J for each r. I have tried combining the for each loops with an and statement and it bugs the code.
It seems like really you have one loop (process), it's just that your data feels to be in two different places. Let's loop through B16:B35, referencing the corresponding values in column J as we go:
Sub looper()
Dim r As Range
Dim cell As Range
If [D8] = 2 Then
Set r = Range("B16:B35")
For Each cell In r
If cell = "" Or cell = "N/A" Then GoTo ENDGAME
MsgBox "pn is " & cell & " route is " & cell(1, 9)
Next cell
ENDGAME:
End If
End Sub
So cell is the range object, starting with B16... you can reference a different cell by its offset from a range object... cell(1, 9) means take the cell, look at the same row (1), but the 9th column (count column B as "one", column C as two; column J is nine).
It's normally a good idea to declare variables at the top of the sub, that's why I moved the Dims. Not strictly necessary for this code to work.
Use a counter as the For loop, and use that to set a reference into each range
Dim r As Range
Dim j As Range
Dim jcell As Range
Dim rcell As Range
Dim i as Long
Set r = Range("B16:B35")
Set j = Range("J16:J35")
For i = 1 to r.Rows.Count
Set rcell = r.Cells(i, 1)
Set jcell = j.Cells(i, 1)
MsgBox "pn is " & rcell.Address & " route is " & jcell.Address
Next i
Not completely sure what you are trying to do, but the following should do perform what you would like to..
Btw, defining cell as a range etc. is not best practice. it is better to give it a name other than a function, etc name.
with thisworkbook.sheets(1)
if .range("B8").value = 2 then
for i = 16 to 35
if .range("B" & i).value = "" or .range("B" & i).value = "N/A" then
goto EndGame
else
msgbox "pn is " & .range("B" & i).value & " route is " & .range("J" & i).value
end if
next i
EndGame:
end if
end with
If you want to do 2 loops, first for B , than for J, you can do this. However, if one of the cells in one of the loops contains nothing or n/a -> function will stop. If you want to go to the next (i) ; iteration. you should put the:
EndGame:
just before:
next i
--
dim First_Range_Done as boolean
with thisworkbook.sheets(1)
if .range("B8").value = 2 then
for i = 16 to 35
if First_Range_Done = false then
if .range("B" & i).value = "" or .range("B" & i).value = "N/A" then
goto EndGame
else
msgbox "pn is " & .range("B" & i).value & " route is " & .range("J" & i).value
end if
end if
if First_Range_Done = true
if .range("J" & i).value = "" or .range("J" & i).value = "N/A" then
goto EndGame
else
msgbox "pn is " & .range("B" & i).value & " route is " & .range("J" & i).value
end if
if i = 35 then exit sub
end if
if i = 35 then
First_Range_Done = true
i = 15
end if
next i
EndGame:
end if
end with
Dim r1 As Range
Dim r2 As Range
Dim u As Range
Dim res As String
Set r1 = Range("A1:B1")
Set r2 = Range("C3:D3")
Set u = Union(r1,r2)
res = ""
For Each cell In u
res = res + cell.Value2
Next cell
MsgBox res
Assuming cells have following values:
-------------------
| Address | Value |
-------------------
| A1 | a1 |
| B1 | b1 |
| C3 | c3 |
| D3 | d3 |
-------------------
You would get a1b1c3d3 as result being displayed by MsgBox.
With this method you have the added bonus, you can combine ranges of different dimensions.

VBA Formula creation uses the name of the Variable rather than the value

Im trying to create a code which will allow me to pull the average of 6 rows from a sheet called 'Raw Data' and dump it into a cell in a different worksheet, and then pull the average of the next 6 rows from 'Raw Data' and so on.
E.G. average('RawData'! A1:A6) in a new sheet A1
then
average('Raw Data'! A7:A12) In new sheet A2
etc.
So far I have managed to make the code loop in a way that I want however Im having trouble writing the actual formula in new sheet A1 and A2.
so far I have tried:
Dim address13 As String
address13 = "'Raw Data'" & "!" & Cells(start_row, RPM1300).Address & ":" & _
Cells(end_row, RPM1300).Address
ActiveCell.Offset(0, -4).Select
'1300
ActiveCell.Formula = "=Average(""" & address13 & """)"
However this returns the correct formula but with "" around it - rendering it useless.
I have also tried:
Sheets("Raw Data").Select
Dim address9 As Range
Set address9 = Range(Cells(start_row, RPM900).Address(), Cells(end_row, RPM900).Address())
Sheets("New Sheet").Select
rCell.Activate
ActiveCell.Offset(0, -5).Select
ActiveCell.Formula = "=Average(address9)"
However this just returns the name of the variable address9 in the formula rather than the actual range.
Note that RPM1300, RPM900, start_row, end_row and rCell are all variables in order for the code to loop and paste into the correct places.
Any help would be greatly apreciated
Try replacing your line:
ActiveCell.Formula = "=Average(""" & address13 & """)"
With:
ActiveCell.Formula = "=AVERAGE(" & address13 & ")"
The reason: the variable address13 is already defined as a String, that's why you don't need the extra " inside the brackets.
Code (use your first method:)
Dim address13 As String
address13 = "'Raw Data'!" & Cells(start_row, RPM1300).Address & ":" & _
Cells(end_row, RPM1300).Address
ActiveCell.Offset(0, -4).Select
ActiveCell.Formula = "=AVERAGE(" & address13 & ")"
Note: Try avoid using Select and ActiveCell , instead use referenced Ranges and Worksheets.
For instance, let's say you start from Cell A1, and you want this formula to be in Cell A5, you can use:
Range("A1").Offset(4, 0).Formula = "=AVERAGE(" & address13 & ")"
It is probably a bug in your version of Excel. Instead of
ActiveCell.Formula = "=Average(""" & address13 & """)"
try using
ActiveCell.Formula = '=Average("' & address13 & '")'
(single quotes around strings with double quotes and using only 1 double quote then).
Instead of
ActiveCell.Formula = "=Average(""" & address13 & """)"
Try
ActiveCell.Formula = "=Average("& chr(34) & address13 & chr(34) & ")"
At least here chr(34) returns the quotes you want. This may be tweaked if needed. Just change the number inside the ( )
Try using this:
Sub CellValue()
Dim adr As String
Dim sht As String
sht = "'Raw Data'"
adr = "A1:A3"
ActiveCell.Formula = "=AVERAGE(" & sht & "!" & adr & ")"
End Sub
Hope it helps :)
This formula will give you the same result and you'd be able to autofill it by dragging the cell handle.
=AVERAGE(OFFSET('Raw Data'!$A$2,ROW(A1)*6-7,0,6,1))
Filling in both formulas
Sub FillFormulas()
Const BASE_FORMULA = "=AVERAGE('Raw Data'!#Address)"
Dim lastRow As Long, x As Long
Dim Formulas
With Worksheets("Raw Data")
lastRow = .Range("A" & .Rows.Count).End(xlUp).Row / 6
End With
ReDim Formulas(1 To lastRow, 1 To 1)
With Worksheets("New Sheet")
For x = 1 To lastRow
Formulas(x, 1) = Replace(BASE_FORMULA, "#Address", .Cells((x * 6) - 5, 1).Resize(6).Address)
Next
.Range("A1").Resize(lastRow).Formula = Formulas
.Range("C1").Resize(lastRow).Formula = "=AVERAGE(OFFSET('Raw Data'!$A$2,ROW(A1)*6-7,0,6,1))"
End With
End Sub

Excel VBA - add zero's inbetween two values

I've done quite a bit of searching around for this one...and I'm not getting anywhere.
I have a spreadsheet(specific column) with values such as:
42153-95
54126-3
13613-6331
16136-336
My goal is to add zero's after the - and before the existing #'s(to 4 places). Like:
42153-0095
54126-0003
13613-6331
16136-0336
I've tried a a lot of different options within the quotes of NumberFormat:
Worksheets("Sheet1").Columns("C"). _ NumberFormat = "00000-0000"
No luck so far. :(
Any help would be greatly appreciated.
Thanks!
Sub testFunc()
MsgBox addZero("54126-3")
End Sub
'/ Function to add Zeros
Public Function addZero(strVal As String) As String
Dim arrTemp
Dim strTemp
arrTemp = Split(strVal, "-")
strTemp = arrTemp(0) & "-" & String(4 - Len(arrTemp(1)), "0") & arrTemp(1)
addZero = strTemp
End Function
As #tigeravatar stated it can be done with a formula. With the Evaluate function we can use an array form of the formula he gave in his comment.
You can apply this to your values in column C:
Worksheets("Sheet1").Range("C1:C4").Value = Worksheets("Sheet1").Evaluate("=INDEX(LEFT(C1:C4,6) & TEXT(--MID(C1:C4,7,LEN(C1:C4)),""0000""),)")
If your range is dynamic and you have the final row in a variable like lstrow you can replace all the C4 with C" & lstrow & "
Worksheets("Sheet1").Range("C1:C" & lstrow).Value = Worksheets("Sheet1").Evaluate("=INDEX(LEFT(C1:C" & lstrow & ",6) & TEXT(--MID(C1:C" & lstrow & ",7,LEN(C1:C" & lstrow & ")),""0000""),)")
Select the cells you wish to process and run:
Sub dural()
Dim r As Range
bry = Array("0000", "000", "00", "0", "")
For Each r In Selection
ary = Split(r.Value, "-")
ary(1) = bry(Len(ary(1))) & ary(1)
r.Value = Join(ary, "-")
Next r
End Sub
Before:
and after:

VBA sum loops in Formula Arrays

If I have defined named ranges for some blocks - say for example, 2 by 2 blocks named Apple1, Apple2, Apple3, Apple4
and I want to create a Total Block being the sum of the above (in excel, the formula array formula would be {Apple1 + Apple2 + Apple3 + Apple4}
With the FormulaArray command - am I on the right lines in my thought process below?
For i = 1 to 2
range("Total").formulaarray = "=" & "Apple" & i
next i
I've not understand why you need FormulaArray for such task, but you can use this:
Sub test()
Dim i%, Apples$
For i = 1 To 4
Apples = Apples & "+SUM(Apple" & i & ")"
Next i
[Total].FormulaArray = "=" & Mid(Apples, 2, Len(Apples))
End Sub
After my experiment, I find the behavior of FormulaArray is more complicated.
sub test()
dim i as long, Apples1 as variant, Apples2 as variant
for i = 1 to 3
Apples1 = Apples1 & "Apple" & i & "+"
Apples2 = Apples2 & "Apple" & i & ","
next i
range("total1").FormulaArray = "=sum(" & left(Apples1, len(Apples1)-1) & ")"
range("total2").FormulaArray = "=sum(" & Apples2 & ")"
range("total3").FormulaArray = "=" & left(Apples1, len(Apples1)-1)
end sub
the outcome is
If any cells in Apple1, Apple2 or Apple3 are string, the outcome is

Resources