Makro do wyszukiwania daty w zakresie kolumn, wstawiania wierszy i wklejania danych

1

Chcę mieć makro, które:

  1. Wykryj na stronie („Oryginał”) wartość komórki (E8 $, data)
  2. Przejdź do innej strony („Transfer”), (nazwa strony jest różna, ale odpowiednia nazwa strony pojawia się w „Oryginale” $ Z $ 1).
  3. Spójrz w dół do kolumny „Transfer”, która zawiera listę w każdy poniedziałek (zakres dat zaczyna się od A20, tekst powyżej).
  4. Znajdź poniedziałek przed datą E8 $ (więc dla E8 = 17 sobota, znalazłby się pon. 12)
  5. Wstaw wiersz BENEATH w ten poniedziałkowy wiersz (czyli przed wierszem z poniedziałkiem 19)
  6. Skasuj ten wiersz (więc wiersz przechodzi od Pon-12, puste, Pon-19
  7. Wytnij / Kopiuj z („Original $ E8”) z zakresu A8: H8
  8. Przejdź do strony „Transfer”
  9. Wstaw zaznaczenie A8: H8 do wiersza utworzonego na 5.
  10. Zapętlić i zrobić to samo za E9 $, dopóki wszystkie informacje nie zostaną umieszczone w „Transfer”.

Komórki, które podałem, to właściwe komórki, daty, które właśnie wymyśliłem (i tak różnią się dla każdego konta).

Eric bardzo uprzejmie podał mi zmodyfikowany przeze mnie kod:

 Public Sub do_stuff()
 Dim date_to_look_for As String
 Dim row As Integer

 date_to_look_for = Range("'Original'!K8").Value
                    '^L: This is the cell that you are reading from. Ensure it is the MONDAY formula
 row = 20
 '^L: This is where the Transfer date values start

 Do Until row = Range("'Transfer'!A1").End(xlDown).row + 1  'create our loop.
 'Notice that the .end function will find the end of the data in a column

If Range("'Transfer'!A" & row).Value = date_to_look_for Then
        '^L: Look for Original (X) Value specified above (make sure it's Monday).

    Range("'Transfer'!" & row + 1 & ":" & row + 1).Insert Shift:=xlDown, CopyOrigin:=xlFormatFromLeftOrAbove
          '^L: Once

    Range("'Transfer'!A" & row + 1 & ":H" & row + 1).Value = Range("'Original'!A8:H8").Value

         '^L:This is WHERE it will paste                           '^L: This is what will copy
    Exit Sub 'no sense in running loop more if already found
End If
 row = row + 1
 Loop

 'If code gets here then the date was never found! so tack to end of list
 Dim endrow As Integer
 endrow = Range("'Transfer'!A1").End(xlDown).row

 Range("'Transfer'!A" & endrow & ":H" & endrow).Value = 
 Range("'Original'!A8:H8").Value
 '^L: What is this?

 End Sub

(Wiadomości L: są moimi notatkami, gdy opracowałem, co zrobiły poszczególne sekcje - prosimy o poprawienie mnie, jeśli źle zrozumiałem. Inne zielone „notatki są Erica i nie jestem pewien, czy rozumiem te fragmenty. Nie rozumiem Naprawdę muszę to robić, o ile działa, ale jeśli chcesz nauczyć mnie kodowania, nie krępuj się: D)

Mój problem polega teraz na tym, jak zrobić pętlę, aby działała w dół do oryginalnych wartości (w tym przypadku kolumna K, więc idzie do K9, K10 itp. I robi to samo? Czy to może CIĘĆ zamiast KOPIOWAĆ i usunąć z oryginalnego arkusza po przeniesieniu?

Dzięki wszystkim, którzy pomagali, jesteście świetni!

Lauren
źródło
Nie rozumiem, dlaczego nie mogę uzyskać pomocy, mówiąc szczerze. Równie dobrze spróbuj rzucić szerszą sieć, aby uzyskać pomoc. Nie umiem kodować i spędziłem nad tym kilka dni - po prostu nie mogę sprawić, żeby działało.
Lauren
I zamieściłem dwa istniejące kody. Powiedziałeś, że żadne nie zadziała bez wyjaśnienia, dlaczego. Chociaż czasami tak jest - miałem nadzieję, że mogę to zmodyfikować. A kiedy pokazałem błąd, który spowodował awarię, nie pomogłeś. Jeśli nie możesz lub nie chcesz pomóc, to dobrze. Ale może ktoś inny to zrobi.
Lauren
Odpowiedziałeś tutaj, ale nie tam. Mogłem tylko założyć, że albo nie chciałeś, albo nie mogłeś pomóc. Gdy próbuję uruchomić makro współpracownika, zawiesza się, gdy dochodzi do: „Jeśli nie znaleziono, to nic”. Program Excel zawiesza się i jeśli go nie wyłączę, ulega awarii. "@ScottCraner
Lauren
Lauren, czy mogłabyś zrobić zrzut ekranu zarówno arkusza roboczego „Original”, jak i „Transfer”? Możesz unieważnić dane, chciałbym tylko zobaczyć strukturę arkusza. Mogę ci pomóc
Nate
Właśnie przejrzałem twój stary kod i to, co tu umieściłeś. Kilka ogólnych uwag, które mogą pomóc w rozwiązaniu problemu. Przede wszystkim wartość Range („Arkusz1”! A2 ”). To dobry sposób na odniesienie do wartości komórek zamiast konieczności wybierania, a następnie wykonywania wszystkich innych czynności, które wykonuje rejestrator makr. Kiedy „goto” lub „transfer”, większość można zrobić w formacie podobnym do Range („Arkusz2”! A2 ”). Wartość = Zakres („ „Arkusz1”! A2 ”). Wartość. Ponieważ większość Twojego postu dotyczy kopiowania i wklejania, ta metoda powinna wyjaśnić większość tego, co robisz. Wystarczy wymienić nazwy arkuszy, kolumny i wiersze
Eric F

Odpowiedzi:

1

To powinno zrobić to, czego szukasz. Skomentowałem kod, abyś mógł dokładnie przeczytać, co się dzieje. Zauważ, że ten kod używa zmiennej typu Range, co oznacza, że ​​zmienne rTransfer i rOriginal odnoszą się do rzeczywistych komórek w arkuszu.

Mam nadzieję że to pomoże! Powodzenia!

Sub TransferMyData()
'Declare the variables to be used in the code
Dim wsTransfer As Worksheet, wsOriginal As Worksheet
Dim rTransfer As Range, rOriginal As Range, rCopyRange As Range
Dim dMonday As Variant
Dim iRow As Integer

'Set the worksheet variable, this makes is easier than constantly referencing each sheet in the code all the time
Set wsTransfer = ThisWorkbook.Worksheets("Transfer")
Set wsOriginal = ThisWorkbook.Worksheets("Original")

'Set rOriginal to reference range E8, the first cell we are checking for a date to transfer
Set rOriginal = wsOriginal.Range("E8")

'Run this loop over and over until the cell referenced in rOriginal is blank.
'At the bottom of the loop we shift rOriginal down by one
Do While rOriginal <> ""
    'Find the Monday of the week for rOriginal
    dMonday = rOriginal - Weekday(rOriginal, 3)

    'Format dMonay to match the Transfer worksheet - Commented out
    'dMonday = Format(dMonday, "dd-mm-yy")

    'Set the cell of rTransfer using the Find function (Search range A:A in wsTransfer for the monday we figured out above)
    Set rTransfer = wsTransfer.Range("A:A").Find(dMonday)

    'Error check. If rTransfer returns nothing then no match was found
    If rTransfer Is Nothing Then
        MsgBox ("Can't find the Monday for ") & rOriginal & ". Searching for Value " & dMonday
        Exit Sub
    End If

    'Check if there was already some data transfered in for that week (rTransfer.Offset(1,4) references the 'E' column of the row below).
    'If there is a value there, shift down by one and check again
    Do Until rTransfer.Offset(1, 4) = ""
        Set rTransfer = rTransfer.Offset(1, 0)
    Loop

    'Insert a blank row below rTransfer using the offset function
    rTransfer.Offset(1, 0).EntireRow.Insert

    'Set iRow to be the row number of rOriginal to be used below
    iRow = rOriginal.Row

    'Set the range rCopyRange to be the range A:H of the row for iRow (See https://www.mrexcel.com/forum/excel-questions/48711-range-r1c1-format-visual-basic-applications.html for explanation)
    Set rCopyRange = wsOriginal.Range(Cells(iRow, 1).Address, Cells(iRow, 8).Address)

    'Copy the range rCopyRange into the blank row we added
    rCopyRange.Copy rTransfer.Offset(1, 0)

    'Offset our rOriginal cell down by one and restart the loop
    Set rOriginal = rOriginal.Offset(1, 0)

    'Clear out the copied range. Can replace with rCopyRange.Delete if you want to delete the cells and have everything shift up
    rCopyRange.Clear

    'Simple error check, if for some reasone you're stuck in an endless loop this will break out
    If rOriginal.Row > 999 Then
        MsgBox "Error! Stuck in Loop!"
        Exit Sub
    End If
Loop

End Sub
Nate
źródło
Wygląda naprawdę dobrze, dziękuję Nate, ale nie ma wartości. Pojawia się błąd „nie mogę znaleźć poniedziałku na 22.11.16”. Wartość Original-E8, 22/11/16, była wtorek, więc powinna była się przesunąć między wierszem Transfer-A, mówiąc 21 i 28. jakieś pomysły?
Lauren
Jest to formowanie wartości dMonday. Google funkcji Format () i dodaj wiersz dMonday = Format (dMonday, „Twój format tutaj”) przed znalezieniem. Spróbuj i daj mi znać, będę zajęty przez następną chwilę.
Nate
Zmodyfikowałem powyższy kod, aby błąd pokazywał dokładnie, czego szuka. Pomoże ci to dowiedzieć się, dlaczego nie można znaleźć dopasowania. MsgBox ("Can't find the Monday for ") & rOriginal & ". Searching for Value " & dMonday
Nate
Tam również dodałem wiersz, aby naprawić formatowanie. Jestem pewien, że to wystarczy.
Nate
Dzięki Nate, Eric wydaje się działać w porządku, ale wciąż mam kilka rzeczy do poprawienia. Zmienię OP, jeśli nie masz nic przeciwko temu? Dzięki bardzo BTW!
Lauren
0

Oto przykład, który moim zdaniem oddaje to, co próbujesz zrobić w sensie ogólnym. Skonfigurowałem dwie zakładki w moim skoroszycie oznaczone jako Przeniesienie i Oryginał, tak jak Ty. Skonfigurowałem kartę Original, aby wyglądała następująco:

wprowadź opis zdjęcia tutaj

Dane w A, B, C, D tak naprawdę nie mają znaczenia. Mam kolumnę F i G, aby ustalić, która data jest „ostatnim poniedziałkiem”. Można to oczywiście zrobić w jednej komórce, ale podzieliłem ją na części, aby lepiej zrozumieć. W tym przykładzie moja komórka F2 ma wartość = WEEKDAY (A2) -2, ponieważ funkcja WEEKDAY zwraca dzień tygodnia jako liczbę. Mam G2 ustawione na = A2-F2, aby faktycznie pokazywać „datę ostatniego poniedziałku”.

Mój arkusz przelewu wygląda następująco:

wprowadź opis zdjęcia tutaj

Od tego momentu musimy sprawdzić makro, który wiersz jest ostatnią datą poniedziałku na karcie Transfer. Musimy także upewnić się, że istnieje. W moim przykładzie, jeśli nie istnieje, po prostu przykleję go do dołu ...

Oto, co napisałem dla mojego przykładu z wieloma komentarzami:

Public Sub do_stuff()
Dim date_to_look_for As String
Dim row As Integer

date_to_look_for = Range("'Original'!G2").Value
row = 2 'whichever row is your start row for the data on the Transfer tab

Do Until row = Range("'Transfer'!A1").End(xlDown).row + 1  'create our loop.
'Notice that the .end function will find the end of the data in a column

    If Range("'Transfer'!A" & row).Value = date_to_look_for Then
        'row found for Monday! Do our magic here!

        'insert a blank spot at the row found + 1
        Range("'Transfer'!" & row + 1 & ":" & row + 1).Insert Shift:=xlDown, CopyOrigin:=xlFormatFromLeftOrAbove
        'now copy data here
        Range("'Transfer'!A" & row + 1 & ":E" & row + 1).Value = Range("'Original'!A2:E2").Value
        Exit Sub 'no sense in running loop more if already found
    End If
row = row + 1
Loop

'If code gets here then the date was never found! so tack to end of list
Dim endrow As Integer
endrow = Range("'Transfer'!A1").End(xlDown).row

Range("'Transfer'!A" & endrow & ":E" & endrow).Value = 
Range("'Original'!A2:E2").Value

End Sub

Zauważ, jak mogę skopiować dane za jednym razem za pomocą funkcji wartości Range (). Zwróć też uwagę, jak mogę również określić zakres.

Po uruchomieniu pokazanego powyżej makra powinieneś zobaczyć to na karcie Transfer:

wprowadź opis zdjęcia tutaj

Eric F.
źródło
Komentarze nie są przeznaczone do rozszerzonej dyskusji; ta rozmowa została przeniesiona do czatu .
DavidPostill