Matching two values for multiple columns. i cant figure how to approach it - excel

i have 6 columns
Grade,Date, ID number, Grade Old, date old and ID number
I need the grade to look for value in grade old and also date old of the grade needs to be within 2 weeks of the date then the ID number is same.
for example:
if grade = A then it needs to look for A in Grade Old and also compare the dates, if the date old is 2 weeks of date then ID number stays the same.
(There can be multiple Grades i.e. Grade old can have multiple entries as A, just need to pick the right one by comparing dates.)
I have no idea how do i achieve this. I tried a few codes but in vain.
Thank you for your time. I appreciate your help.

Give this code a try. This should do what you want, based on your comments above.
Note on data structure:
Grade is in column A, Row 1 are the headers.
My sheet is called "Grades"
Change the code according to your sheet structure.
Sub grades()
Dim wb As Workbook
Dim ws As Worksheet
Dim firstrow, lastrow As Integer
Dim firstAddress As String
Dim tmpFind As Range
Dim grade As String
Dim dateLeft As Double
Dim dateOld As Double
Dim found As Boolean
Set wb = ThisWorkbook
Set ws = wb.Worksheets("Grades") 'change "Grades" to the name of your sheet
With ws
firstrow = 2
lastrow = .Range("A1000000").End(xlUp).Row
For r = firstrow To lastrow
found = False
grade = .Range("A" & r).Value
dateLeft = .Range("B" & r).Value
Set tmpFind = .Range("D" & firstrow & ":D" & lastrow).Find(grade, LookIn:=xlValues, LookAt:=xlWhole, SearchDirection:=xlNext, MatchCase:=False)
If Not tmpFind Is Nothing Then
firstAddress = tmpFind.Address
Do
dateOld = .Range("E" & tmpFind.Row).Value
'check if dateOld is within + - two weeks. if + 2 weeks not required, remove 'And dateOld <= dateLeft + 14' from below
If dateOld >= dateLeft - 14 And dateOld <= dateLeft + 14 Then
.Range("F" & tmpFind.Row).Value = .Range("C" & r).Value 'writes ID-left to ID-right
found = True
End If
Set tmpFind = .Range("D" & firstrow & ":D" & lastrow).FindNext(tmpFind)
Loop While Not tmpFind Is Nothing And tmpFind.Address <> firstAddress And found = False
End If
Next r
End With
End Sub

Are you looking for a Excel Macro to do this?
You may use the below formulae
=IF(ISERROR(MATCH(,A:A, 0)), "No Match", "Match")
=IF(G2="Match",IF(B2-E2<15,C2,F2),)
If you are looking for an excel macro then you may use try using the same sort of validation in your logic. Hope this helps.. thanks.
-Codekavi.

Related

VBA Looping cells and Copy based on criteria

[Copy A2 to E2 till the end of row of the table and check if the cell is within the same month](https://i.stack.imgur.com/Q7YAx.png)
Hi,
I would like to loop through rows from a sheet table from column A2 to E2 to A3 to E3... till the end of the table Ai to Ei by defining a variable and counting the last row of the table.
As the second step, I would like to copy the cells into another sheet and fill it the corresponding months.
[Desired Output--> it will copy the data and return to another sheet in the corresponding month] (https://i.stack.imgur.com/zhgYh.png)
Instead, I've changed the data type into a number format and have set up two condition to loop through.
eg. 1/1/2017 change to 42736
28/2/2017 change to 42794
Sub Mike_Copy_cell()
Dim i As Long 'for looping inside each cell
Dim myvalue As Variant
Dim Lastrow As Long
Const StartRow As Byte = 2
Dim LastMonth As Long
("Mike Filter").Select
Lastrow = Range("A" & StartRow).End(xlDown).Row
For i = StartRow To Lastrow
myvalue = Range("H" & i).Value
If myvalue \< Sheets("Automate Report").Range("A" & i).Value \_
'First data Feb Data 42794 \< Jan Category 42736
Then Sheets("Automate Report").Range("B" & i).Value = ""
'leave the cells in blanks and loop through next cell
If myvalue > Sheets("Automate Report").Range("A" & i).Value _
'First data Feb Data 42794 > Jan Category 42736
Then Range("A" & i, "E" & i).Copy Sheets("Automate Report").Range("B" & i, "F" & i)
'Copy the cells into corresponding category
Next i
End sub()
In my output, it is able to loop through and copy all the cells. However, I am wondering the reason why VBA output is not able leave any blank cells when the first condition is met ?
**I am expecting some blanks in the table if it is not data is not within the same month or in my case is less than criteria I have set. **
The output of my code
If myvalue < Sheets("Automate Report").Range("A" & i).Value _
Then Sheets("Automate Report").Range("B" & i).Value = ""
Greatly appreciate if you can advise the flaws in my code. Massive Thanks.
Best regards,
Kenneth
I'll try to help. But before, may I give you two suggestions that might help you?
First, for me the best way to find the last row is, instead of using xldown from the first row, using xlup from the very last row of excel. This way, if there is a blank in any middle row, the code still gives you the last row with value.
Second, I found that referring to any cells with the "range" method may limit you sometimes when using variables in this reference. I think using the "cells(row, column)" method is more useful.
Why not trying this?
Lastrow = Cells(Rows.Count, 1).End(xlUp).Row
Sorry for the suggestions, It's just that I wish someone had taught them to me sooner.
Back to the topic, I think the problem is how you structure the "if" statement. Allow me to change it a bit:
Lastrow = Cells(Rows.Count, 1).End(xlUp).Row
For i = StartRow To Lastrow
myvalue = cells(i, 8).Value
'if myvalue date is equal or previous to the one found in Ai...
If myvalue <= Sheets("Automate Report").cells(i, 1).Value then
Sheets("Automate Report").cells(i, 2).Value = ""
'but if myvalue is later than Ai...
else
sheets("Automate Report").select
range(cells(i, 1), cells(i, 5).select
selection.copy
cells(i, 2).select
activesheet.paste
end if
Next i
Hope this helps. Best regards,
Mike
I'm not sure what your code is doing but consider using an array(12) of row numbers, one for each month. Copy lines into corresponding month and increment the row number for that month. For example ;
Option Explicit
Sub Mike_Copy_cell()
Const LINES_MTH = 5 ' lines per month
Dim wb As Workbook
Dim wsIn As Worksheet, wsOut As Worksheet
Dim lastrow As Long, rIn As Long, rOut(12) As Long
Dim uid As String, prevuid As String
Dim dAVD As Date, m As Long, n As Long
Set wb = ThisWorkbook
Set wsIn = wb.Sheets("Mike Filter")
Set wsOut = wb.Sheets("Automate Report")
' space out months
For n = 0 To 11
rOut(n + 1) = 2 + n * LINES_MTH
wsOut.Cells(rOut(n + 1), "A").Value2 = MonthName(n + 1)
Next
n = 0
With wsIn
lastrow = .Cells(.Rows.Count, "A").End(xlUp).Row
For rIn = 2 To lastrow
dAVD = .Cells(rIn, "D")
' create a unique ID to skip duplicates
uid = .Cells(rIn, "A") & Format(.Cells(rIn, "D"), "YYYY-MM-DD")
If uid <> prevuid Then
m = Month(dAVD)
.Cells(rIn, "A").Resize(, 5).Copy wsOut.Cells(rOut(m), "B")
rOut(m) = rOut(m) + 1
n = n + 1
End If
prevuid = uid
Next
End With
MsgBox n & " lines copied to " & wsOut.Name, vbInformation
End Sub

Populate blank cells in a column until all populated from repeating list

I need to use VBA code to populate a list of filtered blank cells. I decided to make a picture with small example to explain it easier. Column D should be populated with names from col A repeating until each ID has a name.
I have absolutely no idea how to loop it to make it work - it's mind boggling! I have been searching the web for hours so I am now asking for help. Please note that column C and D are filtered with criteria blanks for column D.
Here is working code to populate blank cells of a filtered list with the same 3 names alternating.
Sub Macro1()
Dim last As Long
Dim counter As Integer
Dim nameRange As Range
Dim cell As Range
last = Range("A2").End(xlDown).Row
Set nameRange = Range("D2:D" & last).SpecialCells(xlCellTypeVisible)
counter = 1
For Each cell In nameRange
If counter = 1 Then
cell.Value = "Carrie"
counter = counter + 1
ElseIf counter = 2 Then
cell.Value = "Lisa"
counter = counter + 1
Else
cell.Value = "Bob"
counter = 1
End If
Next
End Sub
thanks for everyone's input - Hopefully, this will help someone else in the future.
This will do it without the need of filtering the data.
Sub foo()
Dim ws As Worksheet
Dim lastrowa As Long
Dim lastrowd As Long
Dim counta As Long
Dim rng As Range
counta = 2 'First row of name list in column A
Set ws = Sheets("Sheet1")
With ws
lastrowa = .Range("A" & .Rows.Count).End(xlUp).Row
lastrowd = .Range("D" & .Rows.Count).End(xlUp).Row
For Each rng In .Range(.Cells(2, 5), .Cells(lastrowd, 5))
If rng.Value = "" Then
rng.Value = .Cells(counta, 1).Value
If counta = lastrowa Then
counta = 2
Else
counta = counta + 1
End If
End If
Next rng
End With
End Sub
Range("D2:D4").Value = Range("A2:A4").Value
Range("D2:D4").AutoFill Destination:=Range("D2:D11")
If you don't know where column C ends that is easy enough to work out. Something like
Range("D2:D4").Value = Range("A2:A4").Value
Range("D2:D4").AutoFill Destination:=Range(Range("D2"), _
Range("C2").End(xlDown).Cells(1, 2))
If you don't know how far the data extends in column A:
Dim last As Integer
last = Range("A2").End(xlDown).Row
Range("D2:D" & last).Value = Range("A2:A" & last).Value
Range("D2:D" & last).AutoFill Destination:=Range(Range("D2"), _
Range("C2").End(xlDown).Cells(1, 2))
My example doesn't work perfectly, or even well... Its late :)
Create a named range that encapsulates all your "names" (called namesRange in my example).
In your "assigned" column put the following formula:
=INDEX(namesList,ROW()-((INT(ROW()/ROWS(namesList))*ROWS(namesList))),1)
Update...
Thought about it, and remembered how to excel a little more.. The following is what I was trying to do in my first example.
=INDEX(namesList,MOD(ROW()-1,ROWS(namesList)-1)+1,1)

How to check range/column of cells based on month and copy them

So essentially, what I'm trying to do is this:
------A--------B-------C-------D------
1 Date Weight Misc ID*
2 2014-06-12 210 445556
3 2014-07-13 150 546456
4 2014-08-14 265 546456
5 2014-09-15 655 655654
6 2014-10-16 87 546656
7 2014-10-17 1552 545488
8 2014-11-18 225 546545
I have a button and I want it to run a macro that checks if the dates in Column A fall within the current month. I've tried using
Month(Date)
but it checks the entire date, not the month only.
If the month in the cell in colmumn A equals the current month, I want it to copy the entire row of information corresponding to that particular cell. For example: When the current month is november, I want it to copy A8+B8+C8+D8, then I will paste that information in a whole different workbook.
Keep in mind that I'm completely new to VBA, but this is what I've come up with so far:
Sub dat()
Dim rng As Range
Dim dat As Date
dat = Month(Date)
For Each rng In Range("A2:A100")
If rng.Value = dat Then
Range("???").Copy
Range("A1").PasteSpecial
End If
Next
End Sub
Nothing really happens. If I change it to dat=Date then it only works for this particular day, and it takes forever to run through 1000 cells.
I was thinking if I could use Cells(Rows.Count, "A").End(xlUp).Value = Month(Date) somehow. Is this even possible?
EDIT: To paste in a different workbook I used the following commands:
Dim wb As Workbook
Set wb = Workbooks.Open("C:\Users\....DOCUMENT.xlsm")
And then to paste:
wb.Sheets("Sheet1").Range("A" & NextDest & ":F" & NextDest).PasteSpecial
Just change the "Destination Sheet" to the name of the sheet you want to copy to.
Sub dat()
Dim LastRow As Long
Dim CurRow As Long
Dim NextDest As Long
Dim ws As Worksheet
Set ws = Sheets("SOURCE SHEET")
LastRow = ws.Range("A" & Rows.Count).End(xlUp).Row
For CurRow = 2 To LastRow
If IsDate(ws.Range("A" & CurRow).Value) = True Then
If Month(ws.Range("A" & CurRow).Value) = Month(Date) Then
ws.Range("A" & CurRow & ":D" & CurRow).Copy
NextDest = Sheets("DESTINATION SHEET").Range("A" & Rows.Count).End(xlUp).Row + 1
Sheets("DESTINATION SHEET").Range("A" & NextDest & ":D" & NextDest).PasteSpecial
Else
End If
Else
ws.Cells(CurRow, 1).Interior.Color = RGB(255,0,0)
End If
Next CurRow
End Sub
Edit: Your DESTINATION SHEET will now add rows after the last used row. Also, the code will check if the value is a date first and will highlight if not a date.
Change this
If rng.Value = dat Then
To
If month(rng.Value) = dat Then

Excel-VBA: Do a calculation only if cells involve contain values

I have the code that nicely calculates the average I want. But now I want it to only run the calculation if the referenced cells contain values. I am totally stumped on how to feed conditions into my code.
Dim i%
Dim rng As Range
Dim last&
last = Range("A65536").End(xlUp).Row
For i = 2 To last
Range("F" & i).FormulaR1C1 = _
"=AVERAGE(R[-4]C[-2],R[-2]C[-2],RC[-2],R[2]C[-2],R[5]C[-2],)"
Next i
End Sub
I tried working with AVERAGEIF, but I can't get it to work either. the range gives me a #Value in the range whenever I try to set it using the function wizard. So I have no idea how to make it work in VBA.
Any and all help would be appreciated.
*Edit - I only want the average line to appear in the cells, but I want to test the cells for values before doing the calculation. (Siddharth, thanks for your answer anyway!) To clarify:
Dim i%
Dim rng As Range
Dim last&
last = Range("A65536").End(xlUp).Row
For i = 2 To last
'test for all cells having values here
Range("F" & i).FormulaR1C1 = _
"=AVERAGE(R[-4]C[-2],R[-2]C[-2],RC[-2],R[2]C[-2],R[5]C[-2],)"
Next i
End Sub
***Edit 2: To be more clear as to what I'm looking for, I want something like this:
Dim i%
Dim last&
last = Range("A65536").End(xlUp).Row
For i = 2 To last
While Range("D" & i - 4).Value <> "" And Range("D" & i + 4).Value <> ""
Range("F" & i).FormulaR1C1 = _
"AVERAGE(R[-4]C[-2],R[-2]C[-2],RC[-2],R[2]C[-2],R[5]C[-2]))"
Wend
Next i
But my while statement is giving me trouble, as I keep getting an error when I reach that point in the code. I also have tried:
While Range("D" & i - 4 And "D" & i + 4).Value <> ""
Which gives me run time error 13: type mismatch.
If I understand you correctly then you need to check if the number of cells in a range equal the number of filled values. For example
Sub a()
Dim i%
Dim rng As Range
Dim last&
last = Range("A65536").End(xlUp).Row
For i = 2 To last
Range("F" & i).FormulaR1C1 = "=if(" & _
"Rows(R[-4]C[-2])+Rows(R[-2]C[-2])+Rows(RC[-2])+Rows(R[5]C[-2])<>" & _
"COUNTA(R[-4]C[-2],R[-2]C[-2],RC[-2],R[2]C[-2],R[5]C[-2],)-2,""Blank""," & _
"AVERAGE(R[-4]C[-2],R[-2]C[-2],RC[-2],R[2]C[-2],R[5]C[-2],))"
Next i
End Sub

countif statement what wont count 00:00

Any help would be appreciated. I need the CountIf statement to count all the data points that are equal to 00:00. The column is formatted for 24hr time due to other formulas. The 00:00 is a product of an if statement. I have tried many options but it won’t calculate unless I reformat the column to general, but in doing that it messes up my time formation which I need to be 24hr format. Thanks.
Sub Sample()
Dim result As Long, firstrow As Long, lastrow As Long
Dim ws As Worksheet
Dim rng As Range
'~~> Set this to the relevant worksheet
Set ws = ThisWorkbook.Sheets("Sheet1")
With ws
'~~> Find Lastrow in Col D
lastrow = .Range("V" & .Rows.Count).End(xlUp).Row
'~~> Set First row
firstrow = 16
'~~> Set your range
Set rng = .Range("V" & firstrow & ":V" & lastrow)
'~~> Put relevant values
.Range("U" & lastrow + 3).Value = "No Slip Time"
.Range("V" & lastrow + 3).Value = _
Application.WorksheetFunction.CountIf(rng, "*00:00")
End With
End Sub
Notes:
The string "00:00" and time 0 are not the same.
Date and time is a number where 0 is midnight, 1 a day and 0.5 is 12 hours.
Based on your comments you have the following formula in column v, =IF((K16="NA"),"00:00",IF(K16<>"na",K16)), use this instead.
=IF(Upper(K16)="NA",0,K16)
If you have #N/A in cell K16 you need to replace the above "NA" with NA().
Also once done you can use the countif as follows.
Application.WorksheetFunction.CountIf(rng.value2 , "0")

Resources