Excel 如何在每一行上运行相同的宏,直到表结束?

Excel 如何在每一行上运行相同的宏,直到表结束?,excel,vba,loops,Excel,Vba,Loops,我需要你的帮助。我试图在表的每一行上运行一个宏。我想与列表中的所有客户进行第一次和最后一次互动。我在宏上已经做过的是从sheet2复制第一个日期并粘贴到sheet1上以获得第一个日期,然后按住CTRL键并使用下一个日期再次执行该操作以获得最后一个日期。然而,因为它不是一个循环,它只在我做的细胞上做。(下面是我的密码)。我希望代码在每个单元格上执行相同的操作,直到表的末尾 我附上了两张纸的截图。我希望我说清楚了,希望有人能帮你 我看得出你对这个很陌生,这很好,我们都曾经是!使用录制的宏是查看ex

我需要你的帮助。我试图在表的每一行上运行一个宏。我想与列表中的所有客户进行第一次和最后一次互动。我在宏上已经做过的是从sheet2复制第一个日期并粘贴到sheet1上以获得第一个日期,然后按住CTRL键并使用下一个日期再次执行该操作以获得最后一个日期。然而,因为它不是一个循环,它只在我做的细胞上做。(下面是我的密码)。我希望代码在每个单元格上执行相同的操作,直到表的末尾

我附上了两张纸的截图。我希望我说清楚了,希望有人能帮你


我看得出你对这个很陌生,这很好,我们都曾经是!使用录制的宏是查看excel如何查看您当时正在做的事情的一个好方法,但与可能的情况相比,它的效率极低。正如Ron所提到的,
select
确实不是高效代码的朋友。例如,您的前四行可以重写为一行,如下所示:

Sheets("Total").Range("D6923").End(xlDown).copy
然而,即使这样也不是最好的方法。我将假设你从工作表的顶部工作到底部,并根据我认为你正在努力做的事情回答你的问题。我还假设你的时间表是表1,总计是表2。在总数中,我假设可以有任意数量的条目,而不仅仅是给出的三个示例中所示的两个条目

Sub ExampleCode()
  'Variables, you can create and store things in VBA to make life easier for you
  Dim Wb as Workbook            'This is the workbook you are using
  Dim wsTimeline as Worksheet   'This is your worksheet called Timeline
  Dim wsTotal as Worksheet      'This is your worksheet called as Total
  Const rMin as byte = 5        'This is where the loop will start, I'm assuming row 5. As _
                                   this won't change throughout the code and we know it at the _
                                   start it can be a constant
  Dim rMax as long              'This will be the last row in your loop
  Dim r as long                 'This will be how your loop knows which row to use
  Dim timelineRow as long       'This will be the row that the data is pasted in Timeline
  Dim timelineLastRow as Long   'This is the last row of data in your timeline sheet
  
  Set Wb = Thisworkbook                   'Your whole workbook is now stored in the variable Wb
  Set wsTimeline = Wb.Sheets("Timeline")  'As the workbook was stored in Wb we can use it as _
                                             shorthand here. Now the sheet Timeline is in wsTimeline
  Set wsTotal = Wb.Sheets("Total")        'Same as above, this sheet is now stored

  rMax = wsTotal.Cells(Rows.Count, 1).End(xlUp).Row  'This is the equivalent of starting at the _
                                                        bottom row in column A and pressing _
                                                        Ctrl+Up. This takes you to the last _
                                                        row of data in column A. …(Rows.Count, 2)… _
                                                        would be column B etc.
  timelineLastRow = wsTimeline.Cells(Rows.Count, 1).End(xlUp).Row
  
  'This is the bit where you start to loop, the line below basically says "Do the code in this _
     loop for every value between rMin and rMax, each time make 'r' that value (r for row!)

  With wsTotal                                'Means that anything below starting with '.' will _
                                                 be the same as 'wsTotal.'
    For r = rMin To rMax
      'Ensure working on a line with data
      If .Cells(r, 1) = "" Then
        r = .Cells(r, 1).end(xlDown).row
        If r > rMax Then
          End With                            'Closes the With statement above as no longer needed.
          Exit For                            'Exits the loop as we have ended up beyond rMax
        End if
      End if
      
      'This will look for the person in wsTimeline and if they aren't there then add them
      If IsError(Application.Match(.Cells(r, 1), wsTimeline.Range("A3:A" & timelineLastRow), 0)) Then
        wsTimeline.Cells(timelineLastRow + 1, 1) = wsTotal.Cells(r, 1)
        timelineRow = timeLineLastRow + 1
        timelineLastRow = timelineRow
      Else
        timelineRow = Application.Match(.Cells(r, 1), wsTimeline.Range("A3:A" & timelineLastRow), 0)
      End If

      'I'm assuming that all records in 'Total' are chronologically ascending with no gaps between _
         each row for a single person.
      wsTimeline.Cells(timelineRow, 3) = .Cells(r + 2, 4)
      If .cells(r + 3, 4) <> "" then
        wsTimeline.Cells(timelineRow, 4) = .Cells(r + 2, 4).End(xlDown)
      Else
        wsTimeline.Cells(timelineRow, 4) = .Cells(r + 2, 4).End(xlDown)
      End If
      
      'Now that the data has been brought across from Total to Timeline we can move on to _
         the next row.
    Next r     'This will add one to the value stored in r and start the code again where _
                  the loop started
  End With

  'The loop has now ended having gone through every row in your worksheet called Total.
End Sub
子示例code()
'变量,您可以在VBA中创建和存储内容,使您的生活更轻松
“将Wb设置为工作簿”这是您正在使用的工作簿
将wsTimeline设置为工作表“这是您的工作表,称为时间线
Dim wsTotal as WORKEM'这是您的工作表,称为总计
Const rMin as byte=5'这是循环开始的地方,我假设是第5行。作为_
这在整个代码中都不会改变,我们知道这一点_
开始,它可以是一个常数
Dim rMax as long“这将是循环中的最后一行
Dim r as long'这将是循环知道使用哪一行的方式
Dim timelineRow as long“这将是数据粘贴到时间线中的行
Dim TimelineAstrow Long“这是时间轴表中的最后一行数据
Set Wb=thiswoolk“您的整个工作簿现在存储在变量Wb中
设置wsTimeline=Wb.Sheets(“时间线”),因为工作簿存储在Wb中,所以我们可以将其用作_
这里是速记。现在,工作表时间线位于wsTimeline中
设置wsTotal=Wb.Sheets(“Total”)'与上面相同,现在存储此工作表
rMax=wsTotal.Cells(Rows.Count,1).End(xlUp).Row'这相当于从_
A列中的底行并按_
Ctrl+Up。这会把你带到最后_
列A中的数据行…(行数,2)_
将是B列等。
TimeLineAstrow=wsTimeline.Cells(Rows.Count,1).End(xlUp).Row
这是你开始循环的地方,下面的一行基本上是说“在这里做代码”_
循环rMin和rMax之间的每个值,每次将“r”设为该值(r表示行!)
With wsTotal“表示以下以“.”开头的任何内容都将_
与“wsTotal”相同
对于r=rMin到rMax
'确保在有数据的线路上工作
如果.Cells(r,1)=“那么
r=.Cells(r,1).end(xlDown).row
如果r>rMax,则
结束于'关闭上述不再需要的With语句。
“退出”退出循环,因为我们已经超过了rMax
如果结束
如果结束
'这将查找wsTimeline中的人员,如果他们不在那里,则添加他们
如果IsError(Application.Match(.Cells(r,1),wsTimeline.Range(“A3:A”和timelineastrow),0))那么
wsTimeline.Cells(TimeLineAstrow+1,1)=wsTotal.Cells(r,1)
timelineRow=TimeLineAstrow+1
TimeLineAstrow=timelineRow
其他的
timelineRow=Application.Match(.Cells(r,1),wsTimeline.Range(“A3:A”和TimeLineAstrow),0)
如果结束
我假设“Total”中的所有记录都是按时间顺序递增的,没有间隔_
每排一个人。
wsTimeline.Cells(timelineRow,3)=.Cells(r+2,4)
如果.cells(r+3,4)“,则
wsTimeline.Cells(timelineRow,4)=.Cells(r+2,4).End(xlDown)
其他的
wsTimeline.Cells(timelineRow,4)=.Cells(r+2,4).End(xlDown)
如果结束
“现在数据已经从总量到时间线,我们可以继续_
下一排。
下一个r'这将在r中存储的值中添加一个,并在以下位置再次启动代码_
循环开始了
以
'循环现在已经结束,它遍历了工作表中名为Total的每一行。
端接头

你有没有研究过如何在Excel VBA中执行循环?如果有,请更新你的问题-你尝试过的循环代码以及失败的地方。你应该简化你的代码并使其更加健壮,方法是去掉@Scott HoltzmanI一直在准备的所有代码,但我不清楚如何将其应用于此代码。我是这方面的新手。威尔,我是我马上就来试试。非常感谢你!你做对了,我在这方面很新。我真诚地感谢你抽出时间来帮助我。祝你玩得愉快!
Sub ExampleCode()
  'Variables, you can create and store things in VBA to make life easier for you
  Dim Wb as Workbook            'This is the workbook you are using
  Dim wsTimeline as Worksheet   'This is your worksheet called Timeline
  Dim wsTotal as Worksheet      'This is your worksheet called as Total
  Const rMin as byte = 5        'This is where the loop will start, I'm assuming row 5. As _
                                   this won't change throughout the code and we know it at the _
                                   start it can be a constant
  Dim rMax as long              'This will be the last row in your loop
  Dim r as long                 'This will be how your loop knows which row to use
  Dim timelineRow as long       'This will be the row that the data is pasted in Timeline
  Dim timelineLastRow as Long   'This is the last row of data in your timeline sheet
  
  Set Wb = Thisworkbook                   'Your whole workbook is now stored in the variable Wb
  Set wsTimeline = Wb.Sheets("Timeline")  'As the workbook was stored in Wb we can use it as _
                                             shorthand here. Now the sheet Timeline is in wsTimeline
  Set wsTotal = Wb.Sheets("Total")        'Same as above, this sheet is now stored

  rMax = wsTotal.Cells(Rows.Count, 1).End(xlUp).Row  'This is the equivalent of starting at the _
                                                        bottom row in column A and pressing _
                                                        Ctrl+Up. This takes you to the last _
                                                        row of data in column A. …(Rows.Count, 2)… _
                                                        would be column B etc.
  timelineLastRow = wsTimeline.Cells(Rows.Count, 1).End(xlUp).Row
  
  'This is the bit where you start to loop, the line below basically says "Do the code in this _
     loop for every value between rMin and rMax, each time make 'r' that value (r for row!)

  With wsTotal                                'Means that anything below starting with '.' will _
                                                 be the same as 'wsTotal.'
    For r = rMin To rMax
      'Ensure working on a line with data
      If .Cells(r, 1) = "" Then
        r = .Cells(r, 1).end(xlDown).row
        If r > rMax Then
          End With                            'Closes the With statement above as no longer needed.
          Exit For                            'Exits the loop as we have ended up beyond rMax
        End if
      End if
      
      'This will look for the person in wsTimeline and if they aren't there then add them
      If IsError(Application.Match(.Cells(r, 1), wsTimeline.Range("A3:A" & timelineLastRow), 0)) Then
        wsTimeline.Cells(timelineLastRow + 1, 1) = wsTotal.Cells(r, 1)
        timelineRow = timeLineLastRow + 1
        timelineLastRow = timelineRow
      Else
        timelineRow = Application.Match(.Cells(r, 1), wsTimeline.Range("A3:A" & timelineLastRow), 0)
      End If

      'I'm assuming that all records in 'Total' are chronologically ascending with no gaps between _
         each row for a single person.
      wsTimeline.Cells(timelineRow, 3) = .Cells(r + 2, 4)
      If .cells(r + 3, 4) <> "" then
        wsTimeline.Cells(timelineRow, 4) = .Cells(r + 2, 4).End(xlDown)
      Else
        wsTimeline.Cells(timelineRow, 4) = .Cells(r + 2, 4).End(xlDown)
      End If
      
      'Now that the data has been brought across from Total to Timeline we can move on to _
         the next row.
    Next r     'This will add one to the value stored in r and start the code again where _
                  the loop started
  End With

  'The loop has now ended having gone through every row in your worksheet called Total.
End Sub