깊이별 합성곱(Depthwise Convolution)이란? AI에서 채널마다 따로 공간 특징을 계산하는 방법
TL;DR
깊이별 합성곱은 입력 채널마다 별도의 필터를 적용하고 채널 사이의 값을 섞지 않는 합성곱입니다. 채널별 공간 계산 뒤에 1×1 합성곱을 붙이면 깊이별 분리 합성곱을 구성합니다. 출력 채널 수는 입력 채널 수와 채널당 필터 수로 정해집니다. 가중치와 연산을 줄이는 구조를 이해하는 데 유용하지만 실제 속도·정확도 향상까지 보장하지는 않습니다.[1][2][5]
핵심 3줄 요약
- 핵심 1
채널마다 따로 계산합니다. 하나의 출력은 해당 입력 채널의 공간값만 보고 다른 채널의 값을 더하지 않습니다. - 핵심 2
채널 수가 꼭 줄지는 않습니다. 입력 채널 수에 depth_multiplier를 곱한 만큼 출력 채널이 생깁니다. - 핵심 3
채널을 섞는 단계는 별도입니다. 보통 뒤의 1×1 합성곱이 채널을 조합하며 전체 묶음과 깊이별 연산 하나를 구별합니다.
이 글에서 다룰 내용
- 깊이별 합성곱의 한 문장 정의
- 두 채널의 작은 배열로 보는 독립 계산
- AI 모델에서 쓰는 이유와 작동 순서
- 채널 배수·가중치 모양·패딩과 축 순서
- 일반·그룹·깊이별 분리 합성곱과의 차이
- 구조 점검과 경량화 비교의 실전 순서
- 기존 모델 교체·속도·정확도의 주의점
깊이별 합성곱을 한 문장으로 정의하면 무엇인가요?
깊이별 합성곱은 입력의 각 채널에 전용 공간 필터를 적용해 결과를 채널 축으로 이어 붙이는 연산입니다.
영문명은 Depthwise Convolution이며 뎁스와이즈 합성곱이나 채널별 합성곱이라고도 부릅니다. 여기서는 이미지 특징 맵에 적용하는 2차원 연산을 설명합니다. 깊이라는 말은 신경망 층의 개수나 카메라가 측정한 물체까지의 거리를 가리키지 않습니다. 입력 배열의 채널 방향과 관련된 이름입니다.[1][4]
Keras DepthwiseConv2D 문서는 각 입력 채널에 다른 커널을 적용하며 일반 합성곱과 달리 채널 사이 정보를 섞지 않는다고 설명합니다. 채널은 RGB 세 색일 수도 있고 앞선 층에서 만든 수십 개의 특징 맵일 수도 있습니다. 채널마다 같은 필터를 공유한다는 뜻도 아닙니다.[1]
한 줄 정리: 공간에서는 작은 창을 이동시키되, 채널 사이의 합산은 하지 않는 합성곱입니다.
쉬운 예시로 이해해 볼까요?
감자나라ai님이 두 채널의 2×2 특징 맵을 준비했다고 가정해 보겠습니다. 첫 채널 A의 두 행은
[1, 2]
와
[3, 4]
이고, 둘째 채널 B는
[10, 20]
과
[30, 40]
입니다. 보폭은 1, 패딩은 없고 채널당 필터 하나를 사용합니다. 편향과 활성화 함수는 제외합니다.
- A 전용 필터의 두 행:
[1, 0],[0, -1] - B 전용 필터의 두 행:
[1, 1],[1, 1]
A에서는 같은 위치끼리 곱해 더한
1×1+2×0+3×0+4×(-1)=-3
이 나옵니다. B에서는 네 값을 합해 100이 나옵니다. 출력의 공간 크기는 1×1이고 그 위치의 두 채널은
[-3, 100]
입니다. 두 결과를 더한 97 하나로 만들지는 않습니다.
B의 값만 2배로 바꾸면 출력은
[-3, 200]
입니다. A의 출력은 그대로입니다. 깊이별 단계에서는 B의 변화가 A 전용 계산으로 넘어가지 않기 때문입니다. 처음 출력에 1×1 합성곱으로 두 채널의 가중치 2와 0.5를 적용하면
2×(-3)+0.5×100=44
처럼 채널을 조합한 값이 생깁니다.
이 값들은 Python 표준 라이브러리로 작은 배열의 곱과 합을 직접 검산한 설명용 예시입니다. Keras·TensorFlow·PyTorch를 호출한 실행 결과나 학습된 모델의 성능 실험은 아닙니다. 필터도 계산을 드러내려고 정한 값이며 모든 깊이별 합성곱이 이 필터를 쓰지는 않습니다.
쉬운 예시: 두 장의 투명한 격자에 각자 전용 계산표를 대는 방식과 비슷합니다. 격자별 결과를 쌓아 두는 일과 결과끼리 섞는 일은 다릅니다.
왜 AI에서 깊이별 합성곱이 중요한가요?
공간 계산과 채널 조합을 나누어 봅니다
일반 합성곱은 공간의 이웃값을 살피면서 여러 입력 채널을 합쳐 출력 채널을 만듭니다. 깊이별 합성곱은 이 중 채널별 공간 계산을 맡습니다. 뒤에 채널 조합 단계를 별도로 두면 한 연산에 모였던 연결을 나누어 설계합니다. MobileNets 원 논문은 이 분리를 경량 모델의 기본 구성으로 설명합니다.[3][5]
가중치 수와 연결 구조를 함께 읽습니다
3×3 창, 입력 32채널, 최종 출력 64채널을 가정해 보겠습니다. 편향을 빼면 일반 합성곱의 가중치는
3×3×32×64=18432
개입니다. 채널당 필터 하나인 깊이별 단계는 288개이고 뒤의 1×1 단계는 2,048개이므로 합계는 2,336개입니다. 이 수치는 아래의 연결 수 계산을 검산한 것이며 파일 크기나 지연 시간을 직접 측정한 결과가 아닙니다.[5]
핵심 인사이트: 깊이별 단계 288개만 일반 합성곱 18,432개와 비교하면 채널 조합 비용이 빠집니다. 같은 최종 출력까지 만드는 전체 구성을 비교합니다.
깊이별 합성곱은 어떤 순서로 작동하나요?
1. 입력의 채널과 전용 필터를 대응시킵니다
각 입력 채널에 사용할 공간 필터를 정합니다. 보통 신경망 학습 과정에서 그 가중치를 조정합니다. 채널당 필터 수를 m이라고 하면 각 채널에 m개의 전용 필터가 대응합니다. 필터가 여러 개여도 서로 다른 입력 채널의 값을 한 필터에 모으지는 않습니다.[1][4]
2. 채널 안에서 창별 가중합을 계산합니다
필터를 이동시키며 같은 위치의 입력과 가중치를 곱해 더합니다. 이 글의 예시는 필터를 뒤집지 않는 딥러닝의 교차상관 관례를 따릅니다. 최댓값을 고르거나 정해진 평균만 내는 풀링과 달리 학습할 공간 가중치가 있습니다. 보폭과 팽창률은 창의 이동과 창 내부 간격을 따로 정합니다.[1][3][4]
3. 결과를 출력 채널 축으로 이어 붙입니다
입력이 C채널이고 채널당 필터가 m개이면 깊이별 출력은 C×m채널입니다. 채널끼리 더해서 하나로 줄이지 않습니다. TensorFlow의 연산식은 입력 채널 k의 q번째 결과를 출력 채널
k×m+q
에 놓습니다. 값이 맞아도 채널 순서를 잘못 옮기면 뒤의 층은 다른 입력을 받습니다.[4]
실전 팁: 채널마다 크기가 다른 숫자를 넣어 보세요. 한 채널만 바꾸었을 때 어느 출력들이 바뀌는지 보면 연결 관계를 확인하기 쉽습니다.
주요 설정과 결과는 어떻게 읽나요?
depth_multiplier는 채널당 필터 수입니다
Keras의
depth_multiplier=2
라면 입력 2채널에서 출력 4채널을 만듭니다. 앞 예시에 A용 합계 필터와 B용 대각 차이 필터를 하나씩 더하면 출력 순서는
[-3, 10, 100, -30]
입니다. 각 채널의 필터 수가 늘어난 것이며 전체 채널 수를 2개로 고정하는 설정은 아닙니다.[1][4]
TensorFlow의 필터 모양은
[높이, 너비, 입력채널, 채널배수]
입니다. PyTorch Conv2d에서는
groups=in_channels
이고
out_channels=m×in_channels
인 구성이 깊이별 합성곱입니다. PyTorch의 가중치 모양은
[출력채널, 1, 높이, 너비]
이므로 두 저장 배열을 그대로 복사하지 않습니다.[3][4]
출력 채널과 최종 filters를 구별합니다
Keras DepthwiseConv2D는 입력 채널과 배수로 출력 채널을 정합니다. 한편 SeparableConv2D 문서의
filters
는 뒤에 붙는 포인트와이즈 단계의 최종 출력 채널 수입니다. 깊이별 출력이 32채널이어도 뒤의 조합으로 64채널을 만들 수 있습니다. 서로 다른 단계의 채널 수를 같은 값이라고 읽지 않습니다.[1][2]
보폭·패딩과 팽창률을 따로 확인합니다
Keras의 기본 패딩은
padding="valid"
이며 바깥을 채우지 않습니다.
padding="same"
과 보폭 1을 함께 쓰면 공간 크기를 유지합니다. same이라는 이름만 보고 모든 보폭에서 원래 높이·너비와 같다고 단정하지 않습니다. 채널 배수는 공간 크기를 정하는 설정이 아닙니다.[1]
Keras 문서는 보폭이 1보다 크면서 팽창률도 1보다 큰 조합을 허용하지 않습니다. PyTorch Conv2d의 문자열 same 패딩은 보폭 1만 지원합니다. 같은 이름의 옵션이라도 라이브러리별 허용 조합을 확인합니다. 보폭이 2라는 이유로 필터 안의 점 간격까지 2로 바뀌지는 않습니다.[1][3]
축 순서와 편향·활성화를 분리합니다
Keras의 channels_last 입력은
[배치, 높이, 너비, 채널]
이고 PyTorch Conv2d의 배치 입력은
[배치, 채널, 높이, 너비]
입니다. 입력과 가중치의 축을 각각 확인합니다. Keras는 편향을 더하거나 활성화 함수를 적용할 수 있지만 TensorFlow의 저수준 depthwise_conv2d 함수에는 그 두 설정이 인자로 들어 있지 않습니다.[1][3][4]
깊이별 합성곱과 헷갈리는 용어는 무엇이 다른가요?
일반 합성곱·그룹 합성곱과의 차이
일반 합성곱은 각 출력에서 모든 입력 채널의 기여를 모읍니다. 그룹 합성곱은 채널을 여러 묶음으로 나눠 묶음 안에서 연결합니다. 깊이별 합성곱은 그룹마다 입력 채널 하나를 두는 경우입니다. 예를 들어 입력 4채널의 groups=2는 각 그룹이 2채널을 보므로 아직 깊이별 연산이 아닙니다.[3]
포인트와이즈·깊이별 분리 합성곱과의 차이
포인트와이즈 합성곱은 보통 각 공간 위치에서 1×1 창으로 채널을 조합합니다. 깊이별 공간 계산 뒤에 이 조합을 붙인 전체 구성이 깊이별 분리 합성곱입니다. DepthwiseConv2D 하나만으로 이 두 단계를 모두 수행했다고 설명하면 안 됩니다.[2][5]
활성화와 정규화의 위치도 확인합니다. MobileNets 원 논문의 블록은 깊이별·포인트와이즈 단계 각각에 배치 정규화와 ReLU를 둡니다. Keras SeparableConv2D가 설명하는 출력 편향·활성화 순서만으로 그 블록 전체를 재현했다고 볼 수는 없습니다.[2][5]
최대 풀링·3차원 합성곱과의 차이
최대 풀링은 창의 최댓값을 고르는 고정 규칙입니다. 깊이별 합성곱은 채널별로 학습 가능한 가중합을 계산합니다. 둘 다 보폭으로 공간 크기를 줄일 수 있어도 같은 연산은 아닙니다. 3차원 합성곱의 공간·시간 축을 하나 더 다루는 일과 채널 연결을 분리하는 일도 구별합니다.[1][3]
비교 정리: 깊이별은 채널별 공간 계산, 포인트와이즈는 위치별 채널 조합, 깊이별 분리는 두 계산을 잇는 구성입니다.
실전에서는 어디에 쓰이나요?
경량 이미지 모델의 구성 요소를 읽습니다
MobileNets처럼 제한된 기기의 비전 모델을 설명할 때 깊이별 분리 합성곱을 만납니다. 모델 요약에서 깊이별 층과 그다음 채널 조합 층을 따로 찾으면 가중치와 출력 모양이 왜 달라지는지 이해하기 쉽습니다. 여기서는 원 논문의 구조를 설명하며 특정 기기의 실행 속도를 재현하지 않았습니다.[5]
같은 출력 목표의 후보를 비교합니다
모델 경량화를 검토한다면 일반 합성곱과 분리 구성을 같은 입력·최종 출력 조건으로 비교합니다. 가중치 수, 연산 수, 실제 지연 시간과 업무 오류를 따로 기록합니다. 이는 비교 설계 제안입니다. 구조 이름만 바꾸어도 같은 예측이 나온다거나 항상 더 정확하다고 약속하지 않습니다.
깊이별 합성곱을 적용할 때 어떤 순서로 확인하나요?
1. 채널 연결과 출력 목표를 적습니다
입력 채널 수와 채널당 필터 수, 뒤의 1×1 층 유무 및 최종 채널 수를 표시합니다. 기존 CNN 글이 전체 신경망의 흐름을 설명한다면, 여기서는 한 층이 어떤 채널을 보고 무엇을 출력하는지 확인합니다. 입력이 RGB인지 중간 특징 맵인지도 함께 적습니다.
2. 작은 배열로 값과 순서를 시험합니다
앞 예시처럼 한 채널만 바꾸고 영향을 받는 출력을 확인합니다. 채널 배수를 1과 2로 나누어 시험하고, 음수 출력이 활성화 전후에 어떻게 달라지는지도 따로 봅니다. 입력이 모두 같은 값이면 채널 뒤섞임을 놓치기 쉽습니다. 패딩을 쓰는 경우에는 가장자리도 확인합니다.
3. 전체 모델을 같은 조건에서 평가합니다
원본 모델과 바꾼 모델의 정확도·지연 시간·메모리를 같은 기기와 입력 크기로 비교합니다. 학습·검증·평가 자료를 구분하고 설정 선택에 쓰지 않은 자료를 남깁니다. 층 하나의 산술량과 전체 앱의 처리 시간은 측정 범위가 다르므로 전처리와 데이터 이동의 포함 여부도 기록합니다.
사용할 때 무엇을 주의해야 하나요?
첫째, 학습된 일반 합성곱을 그대로 대체하지 않습니다. 일반 합성곱의 연결을 깊이별·포인트와이즈로 나누면 가중치 구조와 표현 제약이 달라집니다. 가중치를 단순 재배치한 것과 같지 않으며 기존 모델과 같은 출력을 보장하지 않습니다. 모델 변경으로 다루고 학습·평가를 다시 확인합니다.[5]
둘째, 채널 혼합이 필요한 위치를 놓치지 않습니다. 깊이별 연산만 연달아 두어도 서로 다른 채널을 합치는 경로가 저절로 생기지는 않습니다. 뒤의 1×1 층이나 다른 혼합 경로를 확인합니다. 채널 수를 늘리는 설정과 채널 사이 정보를 교환하는 설정은 구별합니다.[1][2]
셋째, 산술량 감소를 속도 배수로 보고하지 않습니다. 메모리 접근, 연산 구현과 장치 지원에 따라 실제 지연 시간이 달라집니다. 앞의 가중치 개수 계산을 휴대전화가 몇 배 빨라졌다는 측정값으로 바꾸지 않습니다. 배치 크기와 정밀도도 같은 조건에서 비교합니다.[5]
넷째, depth_multiplier와 모델 폭 배수를 혼동하지 않습니다. 전자는 채널당 필터 수입니다. MobileNets 원 논문의 width multiplier는 각 층의 채널 폭을 조정하는 별도 설정입니다. 이름에 배수가 있다는 이유로 같은 조절값처럼 설명하지 않습니다.[1][5]
주의: 작은 배열의 계산 통과는 인식 성능 검증과 다릅니다. 연결·축·출력 모양을 확인한 뒤 실제 업무의 오류와 실행 비용을 별도로 측정합니다.
자주 묻는 질문
Q1. 깊이별 합성곱은 입력 채널의 평균을 내나요?
아닙니다. 각 채널의 공간 창에 전용 가중치를 적용합니다. 서로 다른 입력 채널을 평균내거나 더하지 않고 결과를 채널 축으로 모읍니다. 채널당 필터 수가 1이면 출력 채널 수는 입력과 같습니다.[1]
Q2. depth_multiplier가 2이면 출력 채널은 항상 2개인가요?
아닙니다. 입력 채널 수에 2를 곱합니다. 입력이 2채널이면 깊이별 출력은 4채널입니다. 뒤의 포인트와이즈 층이 있다면 그 층의 최종 출력 채널 수는 별도로 정합니다.[1][2]
Q3. groups가 2이면 깊이별 합성곱인가요?
입력 채널 수를 함께 봐야 합니다. PyTorch에서는 groups가 입력 채널 수와 같고 출력 채널 수가 입력의 양의 정수배일 때 깊이별 구성입니다. 입력 4채널에 groups=2인 일반 그룹 구성과 구별합니다.[3]
Q4. 깊이별 합성곱 하나가 SeparableConv2D와 같나요?
같지 않습니다. Keras SeparableConv2D는 깊이별 단계 뒤에 채널을 섞는 포인트와이즈 합성곱을 수행합니다. DepthwiseConv2D는 그 앞 단계에 해당합니다.[1][2]
Q5. 채널별 계산이면 학습할 가중치가 없나요?
전용 필터의 가중치를 학습합니다. 창별 최댓값만 고르는 풀링과 다릅니다. 다만 이 글의 설명용 필터는 손계산을 확인하려고 직접 정한 값이며 실제 훈련 결과가 아닙니다.[1][3]
Q6. 가중치 수가 줄면 원래 모델과 성능이 같나요?
그런 보장은 없습니다. 연결 구조가 달라지고 실제 속도도 기기와 구현에 좌우됩니다. 최종 출력 모양이 같더라도 예측값과 정확도까지 같다는 뜻은 아니므로 같은 평가 조건에서 따로 확인합니다.[5]
출처
마무리
깊이별 합성곱은 채널마다 전용 필터로 공간 특징을 계산하는 연산입니다. 채널당 필터 수와 출력 채널 수를 구별하고, 뒤의 1×1 조합까지 포함했는지 확인하면 모델의 채널 연결을 읽기 쉽습니다.
처음에는 두 채널의 작은 배열에서 한 채널만 바꾸어 보세요. 값·채널 순서·공간 크기를 대조한 뒤 전체 모델의 비용과 오류를 비교합니다. 연결을 줄인 구조라는 설명과 실제 기기에서 빨라지고 필요한 대상을 잘 알아봤다는 검증은 나누어 기록합니다.
