EXCEL - VBA

윗셀과 같은 값 지우기(2) - while 문

별동산 2020. 7. 10. 05:56
반응형

for문과 while문은 아래와 같은 차이점이 있는데,

for 문 while문
for i=시작값 to 종료값 [step 간격]
    실행문
next

i= 시작값
while i<=종료값 (또는 i>=종료값)
    실행문
    i = i + 1 (또는 i = i - 1)
Wend
시작값, 종료값과 간격을 한 줄에서 지정 시작값, 종료값, 증감식을 별도로 지정

while문을 구체적으로 적용해 보겠습니다.

2. While 문

어제 작업한 아래 파일의 for문 아래에 while 문을 작성하겠습니다.

윗셀과같은셀지우기 (시작).xlsm
0.02MB

가. 공통되는 부분 위로 이동

아래를 보면 dim 변수 선언문과 마지막 줄인 EndRow을 구하는 구문 2줄이 2개의 sub 모듈에 공통적으로 있습니다.

엑셀 매크로

따라서, 맨 위 Option Explicit 아래로 옮기는데, 옮긴 다음 '윗셀과 같은값지우기' 매크로를 실행하면

엑셀 매크로

아래와 같이 EndRow 줄에서 에러가 발생합니다.

엑셀 컴파일 오류

따라서, EndRow 줄은 옮기면 안되므로, EndRow줄은 원상복구하면 아래와 같이 됩니다.

나. While 문 틀 작성

아래에서부터 위로 올라오도록 작성하겠습니다.

Sub 윗셀과같은값지우기3()
    
    EndRow = Range("a1048576").End(xlUp).Row
    
    i = EndRow
    While i >= 3

        i = i - 1
    Wend
    
    
End Sub

따라서, 시작값은 EndRow가 되고, 종료값은 3이 되며, i값을 1씩 줄여야 합니다.

While i >= 3 이란

i가 3보다 크거나 같은 동안 Wend 사이에 있는 실행문을 실행한다는 의미입니다.

 

while문에서는 증감식을 실행문에 넣기 때문에 i = i - 1 이 While 과 Wend 사이에 있는 것입니다.

따라서, 아래와 같이 코드가 작성됩니다.

서브 프로시져명은 끝에 3을 붙였습니다.

다. 실행문 작성

이제 조건문과 내용을 지우는 구문을 추가하면 되는데, 위 서브 프로시져 모듈에서 복사해서 붙여 넣으면 아래와 같이 됩니다.

Sub 윗셀과같은값지우기3()
    
    EndRow = Range("a1048576").End(xlUp).Row
    
    i = EndRow
    While i >= 3
        If Range("a" & i) = Range("a" & i - 1) Then
            Range("a" & i).ClearContents
        End If
        i = i - 1
    Wend
  
End Sub

 

엑셀 아이콘을 눌러 엑셀로 돌아옵니다.

엑셀로 돌아가기

라. 실행

개발도구 - 매크로를 누르고, '윗셀과같은값지우기3' 매크로를 실행합니다.

그러면, 2개이상 있는 시는 시명이 지워진 것을 볼 수 있습니다.

for 문과 비슷한 듯 다르죠. 3행까지 실행해야 하므로 i >=3 이라고 해야 하는 것 주의해야 하며, i > 2 라고 써도 됩니다.

자주 사용하는 매크로라면 개인용 매크로 통합문서, personal.xlsb에 저장해두는 것이 좋습니다.

https://lsw3210.tistory.com/39

 

개인용 매크로 통합문서, personal.xlsb

엑셀에는 함수를 보완하기 위한 사용자 정의함수가 있고, 반복적인 작업을 자동으로 해주는 매크로가 있습니다. 똑같이 개발도구아래 Visual Basic에서 만들지만, 확장자도 사용자 정의함수는 xlam(

lsw3210.tistory.com

 

아래는 PERSONAL.XLAB에 작성되어 있는 윗셀값과같은값제거 매크로입니다.

예전에 작성한 것이라, 위에서 아래로 내려가면서 처리하는 방식이고, 기준되는 컬럼을 Applicaiton.InputBox로 받는 구문이 있고, Range 대신 Cells 함수를 사용했습니다.

3. 시와 구명이 같은 경우 구명 삭제하고, 시 명이 같은 경우 시명 삭제

Sheet2를 선택한 다음, 자료를 보면 광주광역시는 둘 다 광산구로 같은데, 구 명칭이 부산광역시와 대전광역시에 서구가 있고, 서울특별시와 인천광역시는 같은 중구가 있습니다. 따라서, 이와 같이 구명은 같지만 시명이 다른 경우는 시명을 삭제하지 않고, 시와 구명이 같은 경우는 시와 구명을 모두 삭제하도록 조건문을 수정해 보겠습니다.

가. 시와 구명이 일치할 경우, 다시 말해 2개 열이 일치할 경우

두개와 같을 경우는 and로 두개의 조건을 연결하면 됩니다.

서브 프로시져명으로 끝을 4로 수정하고,

Sub 윗셀과같은값지우기4()
    EndRow = Range("a1048576").End(xlUp).Row
    
    For i = EndRow To 3 Step -1
        If Range("a" & i) = Range("a" & i - 1) _
            And Range("b" & i) = Range("b" & i - 1) Then
            Range(Range("a" & i), Range("b" & i)).ClearContents
        End If
    Next    
End Sub

 

if 조건문에서 Range("a" & i) = Range("a" & i - 1) And Range("b" & i) = Range("b" & i - 1) 라는 것은, A열의 작업 줄과 윗 줄이 같을 경우와 B열의 작업 줄과 윗 줄이 같을 경우를 and 로 연결한 것입니다.

If Range("a" & i) = Range("a" & i - 1) _

And Range("b" & i) = Range("b" & i - 1) Then

다만, 특이한 것은 한 줄로 쓰면 길어지므로 _ 를 입력한 다음 다음 줄에 입력한 것인데, _ 는 아래 줄과 한 문장이라는 것을 알려주는 기호입니다..

3줄일 경우에도 2줄이 끝날 때 _ 를 입력하면 3줄이 1줄처럼 인식됩니다.

그리고, 삭제하는 셀도 Range("b" & i)를 추가해서 B열도 지우도록 하려면 아래 줄을 추가하면 되는데,

Range("b" & i).ClearContents

Ai셀에서 Bi셀까지 한꺼번에 지울 때는 앞에 Range 함수를 추가해서 아래와 같이 작성하면 됩니다.

Range(Range("a" & i), Range("b" & i)).ClearContents

다시 말해 range( ) 사이에 Ai셀과 Bi 셀을 넣은 것입니다.



나. 시 명만 일치할 경우, 다시 말해 1개 열만 일치할 경우

위에 해당하지 않으므로, elseif 를 입력하고, '시 명칭이 일치할 경우'란 조건과 A열의 작업 중인 셀을 삭제하는 실행문을 End If 문 위에 추가합니다.

ElseIf Range("a" & i) = Range("a" & i - 1) Then Range("a" & i).ClearContents

VBA 상태에서는 F5키를 누르거나, 세모 모양 아이콘을 눌러 매크로를 실행할 수 있습니다.

매크로를 실행하면 시와 구명이 일치하는 것은 시와 구명이 모두 지워지고, 시명이 같은 것은 시명이 지워지는데, 시와 구명이 윗줄과 다른 것은 시명, 구명 모두 지워지지 않았습니다. 서울특별시 중구가 삭제된 것이 낯설기는 하지만 맞습니다.

윗셀과 같은 값 지우기 매크로 실행 결과

상세한 코드는 아래 파일을 참고하기 바랍니다.

윗셀과같은셀지우기 (완성).xlsm
0.02MB

반응형