Loop to copy data from cells in a column - excel

I need to copy data in a loop.
Dim i As Integer, intvaluetofind As String
intvaluetofind = "Value"
For i = 1 To 500
If Cells(i, 2).Value = intvaluetofind Then
Cells(i, 5).Formula = "='Data'!C2"
End If
Next i
When it finds "Value" in B it applies the formula. Now, I have three blank spaces before the loop finds "Value" next time, but it applies "='Data'!C2" again.
I would like it to apply Cells(i, 5).Formula = "='Data'!C3" on the next loop and so on until it runs out of values.

You could just add another counter variable which increments each time the value is found.
Sub x()
Dim i As Long, intvaluetofind As String, j As Long
intvaluetofind = "Value"
j = 2
For i = 1 To 500
If Cells(i, 2).Value = intvaluetofind Then
Cells(i, 5).Formula = "='Data'!C" & j
j = j + 1
End If
Next i
End Sub
However, you could do this with a formula, something along these lines
=IF(B1="Value",INDEX(Data!C:C,COUNTIF($B$1:B1,"Value")+1),"")
which I haven't tested

Related

Looping through an array in Excel

Trying to loop through a sheets"data".Range"AM1:AS12" and copy the data to range beginning at BD1 as long as the data doesn't equal "#N/A"
My code works with copying the first column, but doesn't do anything with the data after that. Where am I going wrong?
Set S2 = Sheets("data").Range("AM:AM")
Set S3 = Sheets("data").Range("BD:BD")
Dim i As Integer, j As Integer
j = 1
For i = 1 To 12
If S2.Cells(i, 1).Value <> "#N/A" Then
S3.Cells(j, 2).Value = S2.Cells(i, 1).Value
j = j + 1
End If
Next i
Replace:
<> "#N/A"
By:
Not(Application.WorksheetFunction.IfNa(...))
This works when i tested it.
Sub CopyCell()
Set S2 = Sheets("data").Range("A:A")
Set S3 = Sheets("data").Range("M:M")
Dim i As Integer, j As Integer
For j = 1 To 2
For i = 1 To 12
If S2.Cells(i, j).Value <> "#N/A" Then
S3.Cells(i, j).Value = S2.Cells(i, j).Value
End If
Next i
Next j
Call DeleteBlank
End Sub
Sub DeleteBlank()
Dim x As Integer
Dim y As Integer
For y = 13 To 16 'Range numbers for the columns the data is copied to
For x = 1 To 10 ' Number of cells of data you want to loop through
If Cells(x, y).Value = "" Then
Cells(x, y).Delete Shift:=xlUp
End If
Next x
Next y
End Sub
the best thing to is not to check if it is equal to "#N/A"
The best is to check if it is an error : If Not (IsError(S2.Cells(i, 1).Value)) Then

If value is "AA" , store all the values of column G in one variable that contains letters "AA"

I've been asked to create a script that will loop through one year of stock data for each run and return the total volume each stock had over that year.
I also need to display the ticker symbol to coincide with the total stock volume.
My result should look as follows (note: all solution images are for 2015 data).
https://tec.bootcampcontent.com/Tecnologico-de-Monterrey-Coding-Boot-Camp/TECMC201905DATA2/raw/master/Week%202%20-%20VBA%20Scripting/Homework/Instructions/Images/easy_solution.png
Sub Button1_Click()
Dim i As Long, j As Long
Dim counter As Long
Dim x As Double
For i = 1 To 1000
If Cells(i, 1).Value = "A" Then
Range("I2").Value = "A"
counter = counter + Cells(i, 7).Value
Range("J2").Value = counter
ElseIf Cells(i, 1).Value = "AA" Then
Range("I3").Value = "AA"
counter = counter + Cells(i, 7).Value
Range("J3").Value = counter
End If
Next i
End Sub
I expect to get all the sums in "x" cell in total volume for each ticker, I accomplished the first one, but as the count gets the last value the second one gets another result
It can be done a number of ways but i just modifying your code a little for correct working.
Since You are counting two parameters, you should use two counters. One for "A" another for "AA".
No need to Keep lines writing results (like Range("I2").Value = "A" Range("J2").Value = Counteretc) within loop. Finally write values to the desired cell after completion of loop
Final code would be
Sub Button1_Click()
Dim i As Long, j As Long
Dim Counter As Long, Counter2 As Long
Dim x As Double
For i = 1 To 1000
If Cells(i, 1).Value = "A" Then
Counter = Counter + Cells(i, 7).Value
ElseIf Cells(i, 1).Value = "AA" Then
Counter2 = Counter2 + Cells(i, 7).Value
End If
Next i
Range("I2").Value = "A"
Range("J2").Value = Counter
Range("I3").Value = "AA"
Range("J3").Value = Counter2
End Sub
The Simplest VBA solution may be
Sub Button1_Click()
Range("I2").Value = "A"
Range("J2").Value = WorksheetFunction.SumIf(Range("A1:A1000"), "A", Range("G1:G1000"))
Range("I3").Value = "AA"
Range("J3").Value = WorksheetFunction.SumIf(Range("A1:A1000"), "AA", Range("G1:G1000"))
End Sub

How to create a nested loop to check if a value exists in a second list

I am trying to compare values in two lists. I want my code to compare a value in the first list and check all the entries in the second list. If there is a match then the code will print true next to the value in the first list and if not it will print false.
The problem I am having is that my code only compares values that are in the same row.
The code runs and I have tried it on a two smaller lists to make sure the data types are to same and there aren't any extra spaces or commas in the lists that would lead to a "False" output. I have also tried changing the order of the for and if statements but this doesn't work either.
Sub findvalues()
For i = 2 To 16
For j = 2 To 16
If Cells(i, 3).Value = Cells(i, 1).Value Then
Cells(i, 4).Value = "TRUE"
ElseIf Cells(i, 3).Value = Cells(j + 1, 1).Value Then
Cells(i, 4).Value = "TRUE"
Else
Cells(i, 4).Value = "FALSE"
End If
Next j
Next i
End Sub
Here are the two lists I am testing the code on
Slight mods to your code based on the data you provided in columns 1 & 3. As always, things could be improved but this should get you going ...
Sub findvalues()
Dim i As Long, j As Long, bResult As Boolean
For i = 2 To 16
strValueToLookFor = Cells(i, 1)
For j = 2 To 16
bResult = False
If strValueToLookFor = Cells(j, 3).Value Then
bResult = True
Exit For
End If
Next j
Cells(i, 6).Value = bResult
Next i
End Sub
... you may just need to flick the columns over so the first list searches on the second list or vice versa.
I don't see any need for VBA - formulas are the way to go - but to avoid two loops one could do this:
Sub findvalues()
Dim i As Long
For i = 2 To 130
Cells(i, 4).Value = IsNumeric(Application.Match(Cells(i, 1).Value, Range("C2:C130"), 0))
Next i
End Sub
Update: this does not cater for multiple matches.
There are many was to achieve that. one of them is by using IF & COUNTIF
Formula
=IF(COUNTIF($E$2:$E$6,A2)>0,"TRUE","FALSE")
Results:
VBA CODE
Option Explicit
Sub findvalues()
Dim i As Long
Dim rng As Range
With ThisWorkbook.Worksheets("Sheet1") 'Change if needed
Set rng = .Range("A2:A130") 'set rng to includes values from column A, rows 2:130
For i = 2 To 130 'Loop from row 2 to 130
'Check if the values in column C includes in the rng
If Application.WorksheetFunction.CountIf(rng, .Range("C" & i).Value) > 0 Then
.Range("D" & i).Value = "TRUE"
Else
.Range("D" & i).Value = "FALSE"
End If
Next i
End With
End Sub
VBA code to reconcile two lists.
Sub Reconciliation()
Dim endRow As Long
Dim ICount As Long
Dim Match1() As Variant
Dim Match2() As Variant
Dim ws As Worksheet
Set ws = Worksheets("Recon")
ICount = 0
endRow = ws.Cells(ws.Rows.Count, 2).End(xlUp).Row
endRow1 = ws.Cells(ws.Rows.Count, 11).End(xlUp).Row
Match1 = Sheet1.Range("b2:b" & endRow)
Match2 = Sheet1.Range("K2:K" & endRow1)
For i = LBound(Match1) To UBound(Match1)
For j = LBound(Match2) To UBound(Match2)
If Match1(i, 1) = Match2(j, 1) Then
ICount = ICount + 1
Sheet1.Range("C" & i + 1).Value = ICount
Sheet1.Range("L" & j + 1).Value = ICount
Else
End If
Next j
Next i
End Sub

Compare each and every cell in a colum by custom macro (unhandy for loop)

i'm currently trying to compare each and every cell in a column with each other in order to find duplicates. I wrote below code, i know it as possible via default Excel functions, but i would like to write a macro with the above mentioned function. Excel currently doesn't respond when i run my code, my guess is that i run a double for loop with 14K cells to compare is each resulting in 14.000*14.000 loops, which is kinda unhandy. Any help will be appreciated :).
Sub findidentical()
Dim i As Integer
Dim j As Integer
Dim x As Integer
Dim ColumnG As Integer
x = 0
ColumnG = Application.WorksheetFunction.CountA(Range("G:G"))
'ColumnG is 14K cells long'
For i = 2 To ColumnG
For j = 1 + 1 To ColumnG
If Cells(i, 7).Value = Cells(j, 7).Value Then
x = x + 1 & Cells(i, 7).Font.Bold = True & Cells(j, 7).Font.Bold = True
End If
Next j
Next i
Range("L25").Text = "Amount of duplicates"
Range("L26").Value = x
End Sub
Try this:
Sub findidentical()
Dim i As Integer
Dim j As Integer
Dim x As Integer
Dim ColumnG As Integer
x = 0
ColumnG = Application.WorksheetFunction.CountA(Range("G:G"))
'ColumnG is 14K cells long'
For i = 2 To ColumnG
For j = i + 1 To ColumnG
If Cells(i, 7).Value = Cells(j, 7).Value Then
x = x + 1
Cells(i, 7).Font.Bold = True
Cells(j, 7).Font.Bold = True
End If
Next j
Next i
Range("L25").Text = "Amount of duplicates"
Range("L26").Value = x
End Sub
First you need to make each command in the if statement its own line or separate them with : instead of &. & is a string concatenation not a command separator.
Second there is no reason to start Loop j at 2 it has already been compared to everything above. So start it at i+1

Excel VBA: Can we refer a column by its name?

I want to refer a column by its header name.
Currently column is 4th one and header name is "Preference".
And the column consists of "Yes" or "No"
5th column header is "Reason"
And it is filled only when "Preference" column is "No"
My code is
Private Sub CommandButton1_Click()
Dim i As Integer
Dim MyWorksheetLastRow As Byte
Dim MyWorksheetLastColumn As Byte
MyWorksheetLastRow = Worksheets(1).Cells(Rows.Count, "A").End(xlUp).Row
MyWorksheetLastColumn = Worksheets(1).Cells(1, Columns.Count).End(xlToLeft).Column
Worksheets(1).Cells(1, MyWorksheetLastColumn + 1).Value = "Result"
For i = 2 To MyWorksheetLastRow
If Cells(i, 4).Value = "Yes" Then
Cells(i, MyWorksheetLastColumn + 1).Value = Cells(i, 4).Value
Else: Cells(i, MyWorksheetLastColumn + 1).Value = Cells(i, 5).Value
End If
Next i
End Sub
What I want is instead of Cells(i,4) , I want to call the it by column header example: Cells(i,"Preference").
Because I won't the column number of "Preference" in prior. And I use excel vba because I have to deal 20-30 similar files.
Further to my comments, if you want to do it direct, you would have to do this:
cells(i,Application.WorksheetFunction.Match("Preference", Range("1:1"), 0)).
Here is a function to find the column for X instance. I have put a subroutine in there to call it as an example for you.
Sub ColInstanceExample()
Dim MyColInstance As Long
MyColInstance = ColInstance("Preference", 2) 'Pass in what you are searching for and the instance you want to return the column number for
If MyColInstance = 0 Then
MsgBox "Not Found"
Else
MsgBox "Found at column: " & MyColInstance
End If
End Sub
Function ColInstance(HeadingString As String, InstanceNum As Long)
Dim ColNum As Long
On Error Resume Next
ColNum = 0
For X = 1 To InstanceNum
ColNum = (Range("A1").Offset(0, ColNum).column) + Application.WorksheetFunction.Match(HeadingString, Range("A1").Offset(0, ColNum + 1).Resize(1, Columns.Count - (ColNum + 1)), 0)
Next
ColInstance = ColNum
End Function

Resources