1

生成されて Excel にコピーされたフォームをクリーンアップするマクロに取り組んでいます。余分な数式を含む行を削除する必要がある最後の段階まで、すべてを把握しています。例:

400000  |  Smith, John| 2.4   | 5.66|   =C1+D1
400001  |  Q, Suzy    | 4.6   | 5.47|   =C2+D2
400002  |  Schmoe, Joe| 3.8   | 0.14|   =C3+D3
Blank   |             |       |     |   #VALUE
Blank   |             |       |     |   #VALUE

列「A」を列「E」と比較し、「A」に値がないが「E」に値があるすべての行を削除する式はありますか?

空の「A」列のみを使用する基本的なループ式を試してみましたが、保持したい情報の下の行を永久に削除するまで機能し、このWebサイト(brettdjから)でフィルターを処理する式を見つけましたが、必要なものを適切にキャプチャするために編集する方法がわかりませんでした。

これは私がbrettdjから持っているものです:

Sub QuickKill()
Dim rng1 As Range, rng2 As Range, rng3 As Range
Set rng1 = Cells.Find("*", , xlValues, , xlByColumns, xlPrevious)
Set rng2 = Cells.Find("*", , xlValues, , xlByRows, xlPrevious)
Set rng3 = Range(Cells(rng2.Row, rng1.Column), Cells(1, rng1.Column))
Application.ScreenUpdating = False
Rows(1).Insert
With rng3.Offset(-1, 1).Resize(rng3.Rows.Count + 1, 1)
    .FormulaR1C1 = "=OR(RC1="",RC1<>"")"
    .AutoFilter Field:=2, Criteria1:="TRUE"
    .EntireRow.Delete
    On Error Resume Next
    'in case all rows have been deleted
    .EntireColumn.Delete
    On Error GoTo 0
End With
Application.ScreenUpdating = True

その他の情報:

無視したいシートの最初の 5 行には、列のタイトルやレポート名などが含まれています。

40#### の変更によって埋められた行の数なので、単純にマクロで行 4 を削除することはできません。

私は(明らかに)マクロの広範な知識を持っていないので、特定の部分がどのように機能するかについての詳細な説明をいただければ幸いです. 助けてくれてありがとう。

4

2 に答える 2

2

はい、ループを必要としない方法があります

数式 (Excel スプレッドシート内) は次のようになります。

=IF(AND(A:A="",E:E<>""),"DELETE THIS ROW","LEAVE THIS ROW")

これで、数式を取得して、テストで True を返す行にエラーを入れることができます。これを行う理由は、SpecialCells と呼ばれる Excel の機能です。

Excelで空のセルを選択し、数式バーにタイプします

=NA()

次に、F5 または CTRL+G ( [編集] メニューの [移動]) を押してから、[特殊] ボタンをクリックして [特殊セル]ダイアログを表示します。

そのダイアログで、[数式] の横にあるラジオをクリックし、その下にあるチェックボックスをオフにして、[エラー] のみが選択されるようにします。[OK] をクリックします。

Excel は、エラー ( #N/A ) を持つワークシート内のすべてのセルを選択する必要があります。

以下のコードは、このトリックを利用して、削除するすべての行に#N/Aを入れる数式を列 H に作成し、SpecialCells を呼び出して行を見つけ、それらをクリア (削除) します...

    Sub clearCells()
    '
    Dim sFormula As String
    '
    ' this formula put's an error if the test returns true, 
    ' so we can use SpecialCells function to highlight the
    ' rows to be deleted!
sFormula = "=IF(AND(A:A="""",E:E<>""""),NA(),"""")"
'
' put a formula into column H, to find the rows that ned to be deleted...
Range("H5:H" & Range("E65536").End(xlUp).Row).Formula = sFormula
'
Stop ' next line clears multiple rows, could also delete the entire row!
' now clear the cells returned by SpecialCells ...
Range("H5:H" & Range("E65536").End(xlUp).Row).SpecialCells(xlCellTypeFormulas, xlErrors).Offset(0, -7).Clear ' ' EntireRow .Delete shift:=xlup
'
' clean up the formula
Range("H5:H" & Range("E65536").End(xlUp).Row).Clear    '
    End Sub

それをコピーして貼り付け、F8を使用してステップスルーします...

それから私たちはあなたをもう少し助けることができます...

それがあなたを始めることを願っています

ところで、本当に必要な場合は、WITH A LOOPも可能です :)

フィリップ

于 2013-03-14T17:39:14.597 に答える
1

Philip がなぜループの使用を悪いことだと決めつけたのか、私にはわかりません。Column Aこれは、すべての行を調べて、空でColumn E何らかの値を持つ行を削除する単純なマクロです。

コードがオンになっていると仮定しますSheet 1。簡単にフォローできるように、コードにコメントを付けました。1-5行の削除を考慮したくない場合は、コード内のコメントにあるようにFor loop値を に設定します。6

totalRows行を削除するとループ内でカウントが変化するため、削除はボトムアップで行われることに注意してください。行の欠落によるループを回避するために、単純に逆の順序で実行しました。

コード

Public Sub DeleteWhereEmpty()
    Dim colARowCount As Integer
    Dim colERowCount As Integer
    Dim totalRows As Integer
    Dim currentRow As Integer
    Dim colA As Integer
    Dim colE As Integer
    Dim colACurrentValue As String
    Dim colECurrentValue As String

    colA = 1
    colE = 5
    colARowCount = Sheet1.Cells(Rows.Count, colA).End(xlUp).Row
    colERowCount = Sheet1.Cells(Rows.Count, colE).End(xlUp).Row

    'set total number of rows to look at
    totalRows = colARowCount
    If colARowCount < colERowCount Then
        totalRows = colERowCount 'E has more rows, so use it
    End If

    'to stop deleting at row 5, replace 'To 1' with 'To 6'
    For currentRow = totalRows To 1 Step -1
        colACurrentValue = Cells(currentRow, colA).Value
        colECurrentValue = Cells(currentRow, colE).Text

        'if A is empty and E has data in it, delete the row
        If colACurrentValue = "" Or IsEmpty(colACurrentValue) _
           And Len(colECurrentValue) > 0 Then
            Cells(currentRow, colA).EntireRow.Delete
        End If
    Next
End Sub

ここに画像の説明を入力

ここに画像の説明を入力

于 2013-03-14T20:53:57.307 に答える