spwm
Signal Processing 중심의 Octave 학습 예제
mylib/inst/spwm.m
함수 시그니처
function dz = spwm(x, fs, fpwm) 전체 코드
전체 코드를 복사해서 Octave에서 바로 실행할 수 있습니다.
function dz = spwm(x, fs, fpwm)
% SPWM(Sinusoidal Pulse Width Modulation) 신호 생성 함수
%
% 입력:
% x: 1차원 배열, 사인파 신호
% fs: 샘플링 주파수 (Hz)
% fpwm: 원하는 PWM 주파수 (Hz)
% 출력:
% dz: SPWM 변환된 1차원 배열 (0과 1로 구성된 이진 신호, 이후 [-0.5, 0.5] 변환)
%
% 동작 방식:
% - 주어진 샘플링 주파수(fs)와 PWM 주파수(fpwm)를 이용해 n_wind 결정.
% - 입력 신호 x의 변화율을 정규화하여 각 구간에서 듀티 비율을 계산.
% - 윈도우마다 0과 1을 배분하여 SPWM 신호를 생성.
% - 생성된 이진 신호를 [-0.5, 0.5] 범위로 변환.
rmin = 2;
nn = length(x);
n_wind = round(fs / fpwm); % SPWM 한 주기당 샘플 개수 결정
dx = diff([x(1), x]); % 신호 변화율 계산
dx = dx / max(dx); % 정규화
m_idx = 1:n_wind:nn; % 윈도우 시작 인덱스 설정
num_segments = length(m_idx);
dz = zeros(1, nn); % SPWM 출력 배열 초기화
for k = 1:num_segments
m = m_idx(k);
dr = 0.5 * (dx(m) + 1); % 듀티 비율 계산
r1 = floor(n_wind * (1 - dr)); % Low 상태 지속 시간
r2 = n_wind - r1; % High 상태 지속 시간
% 최소 펄스폭(rmin) 보장
r1 = max(min(r1, n_wind - rmin), rmin);
r2 = max(min(r2, n_wind - rmin), rmin);
idx_start = n_wind * (k - 1) + 1;
idx_end = min(idx_start + n_wind - 1, nn);
dz(idx_start:idx_start + r1 - 1) = 0;
dz(idx_start + r1:idx_end) = 1;
end
dz = dz - 0.5; % [-0.5, 0.5] 범위로 변환
end
# ### **`n_wind`의 영향을 더 깊이 고찰**
# #### **1. `n_wind`와 SPWM 신호의 주파수 관계**
# SPWM(Sinusoidal Pulse Width Modulation) 신호는 펄스의 폭(듀티 비율)에 따라 결정된다.
# - `n_wind`가 클수록 하나의 주기가 길어지고, 출력되는 SPWM 신호의 주파수는 낮아진다.
# - 반대로 `n_wind`가 작을수록 주파수가 높아지고, 더 정밀한 제어가 가능하다.
# 즉, `n_wind`는 **SPWM 신호의 유효 주파수를 조정하는 요소**가 된다.
# #### **2. `n_wind`와 출력 신호의 분해능**
# SPWM 신호는 이진 값(0 또는 1)으로만 구성되므로, 출력 신호가 얼마나 부드럽게 원 신호를 표현하는지는 `n_wind`에 의해 좌우된다.
# - `n_wind`가 크면 0과 1의 개수가 많아져, 더 부드러운 출력이 가능하다.
# - `n_wind`가 작으면 급격한 듀티 변화가 발생하여, 고해상도이지만 출력이 거칠어진다.
# #### **3. `n_wind`와 `r1`, `r2`의 관계**
# - `r1`(0의 개수)와 `r2`(1의 개수)는 항상 `r1 + r2 = n_wind`를 만족해야 한다.
# - `dx(m)`이 크면 `r2`가 커지고 `r1`이 줄어들며, 반대의 경우도 성립한다.
# - 하지만 `r1`, `r2`에는 `rmin`이라는 최소 제한이 있어서 극단적인 변화를 방지한다.
# - 결과적으로, `n_wind`가 클수록 `r1`, `r2`의 변화 폭이 커지므로 SPWM 신호의 가변성이 증가한다.
# #### **4. `n_wind`가 너무 크거나 작을 때의 문제**
# - **너무 크면:** SPWM 신호가 원 신호를 제대로 반영하지 못하고, 반응 속도가 느려질 수 있다.
# - **너무 작으면:** 출력이 지나치게 빠르게 변하면서, 실제 하드웨어(PWM 드라이버 등)에서 처리하기 어려워질 수 있다.
# #### **결론**
# - `n_wind`는 **SPWM 신호의 주파수, 해상도, 부드러움, 그리고 반응 속도를 조절하는 핵심 매개변수**다.
# - 적절한 값을 설정해야 신호가 입력 데이터를 효과적으로 반영하면서도 안정적으로 동작할 수 있다.
코드 해설
목적
Signal Processing 중심의 Octave 학습 예제
입력
- 파라미터: x
- 파라미터: fs
- 파라미터: fpwm
출력
- 반환값: dz
실행 흐름
- 입력
- 출력
- - 입력 신호 x의 변화율을 정규화하여 각 구간에서 듀티 비율을 계산
- - `n_wind`가 클수록 하나의 주기가 길어지고, 출력되는 SPWM 신호의 주파수는 낮아진다
- #### **2. `n_wind`와 출력 신호의 분해능**
- - `n_wind`가 크면 0과 1의 개수가 많아져, 더 부드러운 출력이 가능하다
- - `n_wind`가 작으면 급격한 듀티 변화가 발생하여, 고해상도이지만 출력이 거칠어진다
- - 적절한 값을 설정해야 신호가 입력 데이터를 효과적으로 반영하면서도 안정적으로 동작할 수 있다
핵심 함수/주제
maxmindxdzlengthdifffloorm_idx
실습 과제
- 샘플링 주파수나 입력 주파수를 바꿔 스펙트럼 변화를 비교해보세요.
- 핵심 함수 max의 인자를 한 가지 바꿔 결과 변화를 기록해보세요.
- "입력 -> 출력" 흐름을 함수 단위로 분리해 리팩터링해보세요.
학습 팁
같은 카테고리의 다른 코드
- clamp
mylib/inst/clamp.m - decibell_overall
mylib/inst/decibell_overall.m - generate_impulse_force
mylib/inst/generate_impulse_force.m - generate_sinusoid
mylib/inst/generate_sinusoid.m - load_struct_txt
mylib/inst/load_struct_txt.m - make_axes
mylib/inst/make_axes.m - my_diff
mylib/inst/my_diff.m - my_mean
mylib/inst/my_mean.m - my_rms
mylib/inst/my_rms.m - my_std
mylib/inst/my_std.m