Absolute reference with R1C1 using a variable to dictat row number (VBA) - vba

I have a code that creates a number of separate lists under each other. For each of these lists I'm running a for loop to assign an equation to each row at the end column. This formula should multiply the neighbour cell (a relative reference) with cell at the top of that particular list (an absolute referance). The problem is that the lists are of arbitrary length and generated earlier in the code, so I can't assign the absolute referance beforhand.
I was thinking on saving the row number (row 1 = 1, row 2 = 2 etc) in a variable and then use the variable in the R1C1 notation (= "R(variable)C5*RC[-1]), but I cant seem to get this to work... The variable will be the same throughout the for loop given in the example below, but will change next time the same for loop is entered.
Is this even possible?
(I know the parantheses in the R1C1 are not the proper notation, but this is to show where I want my variable)
...
variable = 3
For i = 1 to count
last = ActiveSheet.Cells(Rows.Count, "C").End(xlUp).Row + 1
Cells(siste, "E").FormulaR1C1 = "=R(variable)C5*RC[-1]"
Next

Just one small change:
Cells(siste, "E").FormulaR1C1 = "=R" & variable & "C5*RC[-1]"

Related

Find cell value, match, cut, move, ...vba

I am a beginner in VBA.
I have components which always consist from 2 parts. (Rotor and a stator, each has its own number). When work is with them it can be damaging some of these parts, however it is necessary to keep a list of damaged parts, where the result is inventory e.g. 200 rotors, stators 150 with different numbers. Before I could scrap it, I need to complete them as proper sets. I.e. rotor "a" stator "a", "b" with "b", etc. It's crazy to work with many numbers to compare them, copy …to find the result of sets qty.
It is possible to solve it with Macro, what I try to do, but I was stuck.
What is the task: In the column "A" I have a list of all damaged parts (mix of rotors, stators different numbers). In the column "C" an information only with help of VlookUP, what should be a counterpart number.
What do I need to solve: In row 5, column. „A“ I have component number , but I know that in the same column, somewhere from row 6 to xx I have a counterpart. What I need is … according to information from column C, same row(5) where is info about the counterpart num. to find counerpart in column A, when found, took it out and put into cell B5. Thus,I get a complete set. Then the next row (6), same action. Macro reading num. in „C“,searching in „A“, when found, cut, and put to „B“ next row 7,8,9,… The result should be a certain qty of pairs + some single numbers if not second part found.
The problem I have is that cycle is working until always found relared counterpart. If the counterpart in row A is not available (no match betwen C-A), the code will stop on that row.
What I need help with is, that if code did not find the counerpart based to info from C just skip this row, make it red and continue with next row till end, it means stop on first empty cell in C. Thanks a lot to everybody who is helping me.
Dim pn As Range,
Dim a
Dim x
x = 5
Dim i As Long, Dim radek As Long
a = Cells(x, 3)
For i = 1 To 500
Range("A:A").Select
Set pn = Selection.Find(What:=a)
If Not pn Is Nothing Then
pn.Select
End If
Selection.Cut
Cells(x, 2).Select
ActiveSheet.Paste
x = x + 1
Next
End Sub

Concatenating Row Number from a match result and a Column Letter and storing the result as a Variable's Address

I'll outline the steps I'm trying to accomplish:
1) Search through a spreadsheet for an acct # via match.
2) If it exists, I'd add offset #__ cells to the right and select that cell.
3) Set the selected cell's formula to Concatenate("ColumnLetter&Match(A1:A1000"",0) + Concatenate("ColumnLetter&Match(A1:A1000"",0)
FX Debt 1,000
Fx Equity 2000
U.S Debt 4,000
U.S Loans 5,000
Recon 1 Recon 2 Diff
11111 $ Debt 0
11112 FX Debt
So, I'd search for, say account "11111" using =match(A1:1000, "11111", 0). If it exists I'd offset to the right of it and then select that cell. I'd then add a formula to the selected cell which would add Cell references.
I'm thinking it would look something alone the lines of:
If Match(A1:A1000,"11111",0)=true
Select(A&(result from match))
Offset(three to right).select
edit
So to make the next step less ambiguous I'll separate it from the rest of the code sample...First let me explain the goal with it, though. The sample data above is divided into two tables...With the first table ending, for example with the general account U.S Loans --- 5,000. The second starting with the Acct # and Recon 1. My goal is to add certain cells that contain the values (not the values themselves, I want to be able to trace back to the accounts using precedents and dependents) of the general acct's in the first table into the selected offset cell. The way I thought I'd go about this was to search for the acct name, for example "FX Debt", the same way David suggested to find the Acct #, I'd then use the similar offset method to add the cell containing 1000, so say B2, into the original offset sell to the right of the Account #.
end edit
edit 2
Dim searchRange as Range
Dim myMatch as Variant
Set searchRange = Range("A1:A1000")
myMatch = Match("11111", searchRange, 0)
If Not IsError(myMatch) Then
rng.Cells(myMatch).Offset(,3).Formula = Sum(Match("U.S Debt", searchRange, 0).Offset(,2)+(Match("U.S Debt", searchRange, 0).Offset(,2))...
End If
Does this make more sense? I'm trying to add the amounts associated with U.S Debt and U.S Loans to the master account ($ Debt).
end edit 2
1) Search through a spreadsheet for an acct # via match.
2) If it exists, I'd add offset #__ cells to the right and select that
cell.
3) Set the selected the cell's formula to
Concatenate("ColumnLetter&Match(A1:A1000"",0) +
Concatenate("ColumnLetter&Match(A1:A1000"",0)
Don't bother with Selecting the cell. It's unnecessary about 99% of the time (probably more). More detail, here:
How to avoid using Select in Excel VBA macros
Also, your Match syntax is wrong. You need to do:
=Match("11111", A1:A1000, 0)
So, putting it all together, something like:
Dim searchRange as Range
Dim myMatch as Variant
Set searchRange = Range("A1:A1000")
myMatch = Match("11111", searchRange, 0)
If Not IsError(myMatch) Then
searchRange.Cells(myMatch).Offset(,3).Formula = ...
End If
I did not attempt to interpret the formula string given below; I'm not sure I understand what it's supposed to be doing:
sum(((Column Number -->)"I" + match(A1:A1000,"",0)+("I"+match(A1:A1000,"",0))
But at the very least we can consolidate your pseudo-code using the myMatch variable:
sum(((Column Number -->)"I" + myMatch+("I"+myMatch)
(A word of caution: the + operator can be used to concatenate strings, but there are several reasons why the & operator is preferable, notably the + operator is ambiguous and defaults to a mathematical + operator when one of the arguments is a numeric type. In other words, it attempts to add a number and a string, which will invariable result in a Mismatch error)
So revise to:
sum(((Column Number -->)"I" & myMatch & ("I"& myMatch)
Even after cleaning it up, I'm still not sure what you're trying to do with the above formula, but if you can try to explain then I can probably assist.

Return values from other workbook

Have a question about formula which will resolve my issue.
In my main workbook I need to compare data from two sources.
One of the columns must retrieve data(amounts) from other workbook.
I want formula which will search for all amounts in column G and will skip all blank cells. Tried to use VLOOKUP, INDEX and SMALL functions but no effect.
Each day amounts are different and I need to match them in main file and find exeptions.
Any ideas?
How about an array formula such as the following?
=INDEX($G$2:$G$20,SMALL(IF(($G$2:$G$20)=0,"",ROW($G$2:$G$20)),ROW()-1)-ROW($G$2:$G$20)+1)
The formula would have to be placed into cell I2 as an array formula (which must be entered pressing Strg + Shift + Enter). Then you can drag down the formula to get all the other values.
It doesn't have to be in column I but it has to be in row 2 because this formula get's the n-th Number from the list which is not = 0. The n-th place is (in this formula) row()-1. So for row 2 it will be 2-1=1 and thus the 1st number. By dragging down the formula you get the 2nd, 3rd, etc. number. If you start with the formula in cell I5 instead then it would have to be adjusted to be as follows:
=INDEX($G$2:$G$20,SMALL(IF(($G$2:$G$20)=0,"",ROW($G$2:$G$20)),ROW()-4)-ROW($G$2:$G$20)+1)
You could loop through the column and store each value >0 in an array and then compare or you loop through the column and compare directly...
something like:
Dim i as Integer = 0
Foreach value in Maintable
Do
If otherworkbook.cells(i,7) = value Then '7 for G
do your stuff
End If
i = i + 1
While i < otherworkbook.rows.count
Next
I think that could be the right approach

Variable number of terms in an Excel VBA Formula?

Is it possible to write a formula in VBA for excel such that there are "n" terms in the formula, with the number of terms changing as the value of "n" does?
For instance, say you wanted to code cell a1 such that it was the sum of a2 and a3. Then you wanted b1 to be the sum of b2,b3,b4,b5 and so on such that each column 1 row 1 cell for a range of cells is the sum of "n" cells below it where "n" varies from column to column. Say that all cell addresses you wanted to use are known and stored in an array.
Here is some code to better explain what I'm asking:
For i = 0 to n
Range(arr1(i)).formula = "=" & range(arr2(i)).value & "-(" _
& Range(arrk(i)).value & "+" & Range(arrk+1(i)).value & "+" _
& Range(arrk+2(i)).value & "+" & ... & ")"
Next i
So what I'm looking for is one piece of VBA code that can make a cell formula contain a dynamic number of terms. The code above would make cell a1's value = a-(b+c+d+...) where the number of terms in the bracket is variable, depending on which cell the formula is applied to.
The image here shows an example of what I want to do. I'd like some code which could take "years income" and subtract a variable amount of "expenses" from it, where the number of expenses varies each year (but the number stays fixed for that year). The code needs to use a formula so that the expenses entries can be modified by the user.
Have you tried Array Formula ? :
Array Formula :
An Excel Array Formula performs multiple calculations on one or more sets of values (the 'array arguments') and returns one or more results.
details : http://www.excelfunctions.net/Excel-Array-Formulas.html
Thanks for the suggestions everyone, I found a solution (not a particularly efficient one, but a solution nonetheless) to the conundrum today.
First I created an array which used the "pattern" of the Junk cells to list every cell address which was to be included.
Taking this array, I used a for loop to create a series of temporary arrays with the application.index command. For each temporary array, I used the Join command to turn the list of cells into a single string which I then inputted into a cell formula. Thanks to #thepiyush13 whose array.formula approach inspired this.
Here's some example code to show what I did:
' hypothetical array containing two sets of cells to use
Dim array1(0 To 1, 0 To 1) As Variant
Dim vartemp As Variant
Dim vartemptransposed As Variant
' col 1 will be used to add I10 and I13, col2 I11 and I14
array1(0, 0) = "$I$10"
array1(1, 0) = "$I$13"
array1(0, 1) = "$I$11"
array1(1, 1) = "$I$14"
For i = 1 to 2
'application.index(arr,row#,col#) to create a new array
vartemp = Application.Index(array1, 0, i)
'error if not transposed
vartemptransposed = Application.Transpose(vartemp)
randomstring = Join(vartemptransposed, ",")
totalvalue = 100
'example formula: a1 = totalvalue - sum(I10,I13). a2 = totalvalue - sum(I11,I14)
Cells(1,i).formula = "=" & totalvalue & "-SUM(" & randomstring & ")"
Next i
I needed the code to run this many many times on large lists which are generated dynamically but always hold the same pattern of where the "junk cells" are. Not included in the code, but I also used another array for the cell addresses of where to place the formula.

Using an array to count coloured cells

Currently I have a worksheet which has different colored cells in it like the one below:
[currentsheet] http://imgur.com/na6nvNH
I am using an array to count the colored cells per column. Here is my a snippet of my code:
Dim difference(0 To 41) As Long
For Each mycell In ActiveWorkbook.Worksheets("Differences").UsedRange
Dim col As Long
col = mycell.Column
If ActiveWorkbook.Worksheets("Differences").Cells(mycell.Row,mycell.Column).Interior.Color = vbRed Then
difference(col) = difference(col) + 1
End If
Next mycell
Sheets("Summary").Cells(47, 3) = difference(0)
Sheets("Summary").Cells(48, 3) = difference(1)
Sheets("Summary").Cells(49, 3) = difference(2)
etc.
Which will list the amount of colored cells I have per column. I need help breaking this down so I can create a table which shows the number of colored cells per department. I have no idea on how to do this!
To make it easier to view I am looking to create this:
[FinalSheet] http://imgur.com/i6W60m7
I should add: the amount of rows within the sheet can vary, they can also vary per department
Tried applying a column filter beginning with the first department and then counting the colored cells once the filter was applied, however since I am looking at every cell in the code above the result is still per column.
For anyone looking for an answer to this, a rather long method. However, I applied a filter and then set the range to only the visible cells instead of the used range in the whole worksheet
It seems it would be a lot easier to use a multi dimensional array, so you would have Array(4,7) so some sudo code might look like. I could do real code, but you seem to know what your doing.
Select Case mycell.row
Case 1
Array(1,Col) = Array(1,Col) + 1
Case 2
Array(1,Col) = Array(1,Col) + 1
Case 3
Array(2,Col) = Array(2,Col) + 1
end select
The trick to a multi dimensional array is to think of it like a spread sheet, (2,2) = 3 rows, by 3 columns ... (3 because arrays start at 0) The beauty of it is, if you do it this way when it comes to extract the data you simply put a double loop
For I =0 to Ubound(Array)
For II = 0 to Ubound(Array,2)
Cell(I,II).Value = Array(I,II)
next
next