Токи были странными из-за неправильного определения перехода через ноль и преждевременного открытия тиристоров. Добавлен полосовой фильтр на напряжения, чтобы коммутации тиристоров не смещали переход через ноль
А также: - общий rms ток считается через сумму rms фаз, а не по векторам - в установку угла добавлен аргумент коррекции - пока только смщеение между фазными и линейными. Фильтр практически не смещает, но еще посмотрим - коэф пид приведены к диапзону 0-1 - ПИД надо еще донастраивать. не нравится пока как он работает И еще не были проверены тайминги. Мб это не будет успевать рассчитываться)))
This commit is contained in:
@@ -2,10 +2,11 @@
|
||||
clear all; close all; clc;
|
||||
|
||||
%% Параметры моделирования
|
||||
Fs = 100000; % Частота дискретизации [Гц]
|
||||
Fs = 1/25e-6; % Частота дискретизации [Гц]
|
||||
T = 0.5; % Время моделирования [с]
|
||||
t = 0:1/Fs:T-1/Fs; % Временной вектор
|
||||
N = length(t); % Количество отсчетов
|
||||
Fsrez = 50;
|
||||
|
||||
%% Уровни шума для разных каналов
|
||||
noise_levels.voltage = 0.2; % 2% шума для напряжений
|
||||
@@ -17,28 +18,28 @@ fprintf('=== АВТОМАТИЧЕСКИЙ РАСЧЕТ КОЭФФИЦИЕНТО
|
||||
|
||||
% 1. Полосовой фильтр 45-55 Гц для напряжений
|
||||
% [b_bpf, a_bpf, coeffs_bpf] = BiquadFilterDesigner.bpf(20, 10, Fs);
|
||||
[b_bpf, a_bpf, coeffs_bpf] = BiquadFilterDesigner.lpf(100, Fs);
|
||||
[b_bpf, a_bpf, coeffs_bpf] = BiquadFilterDesigner.lpf(Fsrez, Fs);
|
||||
fprintf('1. Полосовой фильтр 45-55 Гц:\n');
|
||||
BiquadFilterDesigner.generate_c_code(coeffs_bpf, 'voltage_bpf');
|
||||
|
||||
% 2. ФНЧ 100 Гц для токов
|
||||
[b_lpf_current, a_lpf_current, coeffs_lpf_current] = BiquadFilterDesigner.lpf(100, Fs);
|
||||
[b_lpf_current, a_lpf_current, coeffs_lpf_current] = BiquadFilterDesigner.lpf(Fsrez, Fs);
|
||||
fprintf('2. ФНЧ 100 Гц (токи):\n');
|
||||
BiquadFilterDesigner.generate_c_code(coeffs_lpf_current, 'current_lpf');
|
||||
|
||||
% 3. ФНЧ 10 Гц для температур
|
||||
[b_lpf_temp, a_lpf_temp, coeffs_lpf_temp] = BiquadFilterDesigner.lpf(10, Fs);
|
||||
fprintf('3. ФНЧ 10 Гц (температуры):\n');
|
||||
BiquadFilterDesigner.generate_c_code(coeffs_lpf_temp, 'temperature_lpf');
|
||||
%
|
||||
% % 3. ФНЧ 10 Гц для температур
|
||||
% [b_lpf_temp, a_lpf_temp, coeffs_lpf_temp] = BiquadFilterDesigner.lpf(10, Fs);
|
||||
% fprintf('3. ФНЧ 10 Гц (температуры):\n');
|
||||
% BiquadFilterDesigner.generate_c_code(coeffs_lpf_temp, 'temperature_lpf');
|
||||
|
||||
% Вывод коэффициентов в консоль
|
||||
fprintf('\n=== РАСЧЕТНЫЕ КОЭФФИЦИЕНТЫ ===\n');
|
||||
fprintf('Напряжение (BPF 45-55 Гц): b = [%.6f, %.6f, %.6f], a = [1, %.6f, %.6f]\n', ...
|
||||
b_bpf, a_bpf(2), a_bpf(3));
|
||||
fprintf('Ток (LPF 100 Гц): b = [%.6f, %.6f, %.6f], a = [1, %.6f, %.6f]\n', ...
|
||||
b_lpf_current, a_lpf_current(2), a_lpf_current(3));
|
||||
fprintf('Температура (LPF 10 Гц): b = [%.6f, %.6f, %.6f], a = [1, %.6f, %.6f]\n\n', ...
|
||||
b_lpf_temp, a_lpf_temp(2), a_lpf_temp(3));
|
||||
% fprintf('Ток (LPF 100 Гц): b = [%.6f, %.6f, %.6f], a = [1, %.6f, %.6f]\n', ...
|
||||
% b_lpf_current, a_lpf_current(2), a_lpf_current(3));
|
||||
% fprintf('Температура (LPF 10 Гц): b = [%.6f, %.6f, %.6f], a = [1, %.6f, %.6f]\n\n', ...
|
||||
% b_lpf_temp, a_lpf_temp(2), a_lpf_temp(3));
|
||||
|
||||
%% Генерация тестовых сигналов
|
||||
|
||||
@@ -53,25 +54,25 @@ f_current = 50;
|
||||
current_clean = 1 * sin(2*pi*f_current*t); %.* ...
|
||||
%(1 + 0.2 * sin(2*pi*2*t)); % амплитудная модуляция 2 Гц
|
||||
|
||||
% 3. Температура (медленно меняющийся сигнал)
|
||||
temperature_clean = 25 + 2 * sin(2*pi*0.1*t) + ... % медленные колебания 0.1 Гц
|
||||
0.5 * sin(2*pi*1*t); % быстрые колебания 1 Гц
|
||||
% % 3. Температура (медленно меняющийся сигнал)
|
||||
% temperature_clean = 25 + 2 * sin(2*pi*0.1*t) + ... % медленные колебания 0.1 Гц
|
||||
% 0.5 * sin(2*pi*1*t); % быстрые колебания 1 Гц
|
||||
|
||||
%% Добавление шума
|
||||
voltage_noisy = voltage_clean + noise_levels.voltage * randn(size(t));
|
||||
current_noisy = current_clean + noise_levels.current * randn(size(t));
|
||||
temperature_noisy = temperature_clean + noise_levels.temperature * randn(size(t));
|
||||
% temperature_noisy = temperature_clean + noise_levels.temperature * randn(size(t));
|
||||
|
||||
%% Фильтрация сигналов
|
||||
voltage_filtered = filter(b_bpf, a_bpf, voltage_noisy);
|
||||
current_filtered = filter(b_lpf_current, a_lpf_current, current_noisy);
|
||||
temperature_filtered = filter(b_lpf_temp, a_lpf_temp, temperature_noisy);
|
||||
% temperature_filtered = filter(b_lpf_temp, a_lpf_temp, temperature_noisy);
|
||||
|
||||
%% НОРМАЛИЗАЦИЯ УСИЛЕНИЯ (важно для правильного SNR)
|
||||
% Получаем АЧХ для нормализации
|
||||
[h_bpf, f_bpf] = freqz(b_bpf, a_bpf, 1024, Fs);
|
||||
[h_lpf_curr, f_lpf_curr] = freqz(b_lpf_current, a_lpf_current, 1024, Fs);
|
||||
[h_lpf_temp, f_lpf_temp] = freqz(b_lpf_temp, a_lpf_temp, 1024, Fs);
|
||||
% [h_lpf_temp, f_lpf_temp] = freqz(b_lpf_temp, a_lpf_temp, 1024, Fs);
|
||||
|
||||
% Нормализация полосового фильтра на центральной частоте
|
||||
[~, idx_50hz] = min(abs(f_bpf - 50));
|
||||
@@ -85,11 +86,11 @@ gain_lpf_current = sum(b_lpf_current) / (1 + sum(a_lpf_current(2:end)));
|
||||
if gain_lpf_current > 0
|
||||
current_filtered = current_filtered / gain_lpf_current;
|
||||
end
|
||||
|
||||
gain_lpf_temp = sum(b_lpf_temp) / (1 + sum(a_lpf_temp(2:end)));
|
||||
if gain_lpf_temp > 0
|
||||
temperature_filtered = temperature_filtered / gain_lpf_temp;
|
||||
end
|
||||
%
|
||||
% gain_lpf_temp = sum(b_lpf_temp) / (1 + sum(a_lpf_temp(2:end)));
|
||||
% if gain_lpf_temp > 0
|
||||
% temperature_filtered = temperature_filtered / gain_lpf_temp;
|
||||
% end
|
||||
|
||||
%% ОКНО 1: НАПРЯЖЕНИЕ
|
||||
figure('Name', 'Анализ напряжения');
|
||||
@@ -213,68 +214,68 @@ text(0.1, 0.4, sprintf('Улучшение: %.1f дБ', improvement_current), 'F
|
||||
text(0.1, 0.2, sprintf('Задержка 50 Гц: %.1f мс', gd_lpf_curr(idx_50hz_curr)/Fs*1000), 'FontSize', 12);
|
||||
title('Статистика фильтрации тока');
|
||||
axis off;
|
||||
|
||||
%% ОКНО 3: ТЕМПЕРАТУРА
|
||||
figure('Name', 'Анализ температуры');
|
||||
|
||||
% Временные характеристики
|
||||
subplot(2,3,1);
|
||||
plot(t, temperature_noisy, 'b', 'LineWidth', 1); hold on;
|
||||
plot(t, temperature_filtered, 'r', 'LineWidth', 2);
|
||||
plot(t, temperature_clean, 'g--', 'LineWidth', 1);
|
||||
title('Температура: временная область');
|
||||
legend('С шумом', 'Фильтрованный', 'Идеальный', 'Location', 'best');
|
||||
xlabel('Время [с]'); ylabel('Температура [°C]');
|
||||
grid on;
|
||||
|
||||
% АЧХ фильтра
|
||||
subplot(2,3,2);
|
||||
plot(f_lpf_temp, 20*log10(abs(h_lpf_temp)), 'LineWidth', 2);
|
||||
title('АЧХ: ФНЧ 10 Гц');
|
||||
xlabel('Частота [Гц]'); ylabel('Усиление [дБ]');
|
||||
grid on; xlim([0, 20]);
|
||||
|
||||
% Спектр фильтрованного сигнала
|
||||
subplot(2,3,3);
|
||||
[P_temp, f_temp] = pwelch(temperature_filtered, [], [], 1024, Fs);
|
||||
plot(f_temp, 10*log10(P_temp), 'LineWidth', 2);
|
||||
title('Спектр фильтрованной температуры');
|
||||
xlabel('Частота [Гц]'); ylabel('Мощность [дБ]');
|
||||
grid on; xlim([0, 10]);
|
||||
|
||||
% Групповая задержка
|
||||
subplot(2,3,4);
|
||||
[gd_lpf_temp, f_gd_temp] = grpdelay(b_lpf_temp, a_lpf_temp, 1024, Fs);
|
||||
plot(f_gd_temp, gd_lpf_temp/Fs*1000, 'LineWidth', 2);
|
||||
title('Групповая задержка фильтра');
|
||||
xlabel('Частота [Гц]'); ylabel('Задержка [мс]');
|
||||
grid on; xlim([0, 20]);
|
||||
|
||||
% Детальный вид (последне 0.1 секунды)
|
||||
idx_end_temp = max(1, length(t) - 0.1*Fs + 1):length(t); % последние 100 мс
|
||||
subplot(2,3,5);
|
||||
plot(t(idx_end_temp), temperature_noisy(idx_end_temp), 'b', 'LineWidth', 2); hold on;
|
||||
plot(t(idx_end_temp), temperature_filtered(idx_end_temp), 'r', 'LineWidth', 2);
|
||||
plot(t(idx_end_temp), temperature_clean(idx_end_temp), 'g--', 'LineWidth', 2);
|
||||
title('Температура: УВЕЛИЧЕННЫЙ ВИД (900-1000 мс)');
|
||||
legend('С шумом', 'Фильтрованный', 'Идеальный', 'Location', 'best');
|
||||
xlabel('Время [с]'); ylabel('Температура [°C]');
|
||||
grid on;
|
||||
xlim([t(idx_end_temp(1)) t(idx_end_temp(end))]);
|
||||
|
||||
% Статистика
|
||||
subplot(2,3,6);
|
||||
snr_temp_in = snr(temperature_clean, temperature_noisy - temperature_clean);
|
||||
snr_temp_out = snr(temperature_clean, temperature_filtered - temperature_clean);
|
||||
improvement_temp = snr_temp_out - snr_temp_in;
|
||||
|
||||
[~, idx_1hz] = min(abs(f_gd_temp - 1));
|
||||
text(0.1, 0.8, sprintf('SNR вход: %.1f дБ', snr_temp_in), 'FontSize', 12);
|
||||
text(0.1, 0.6, sprintf('SNR выход: %.1f дБ', snr_temp_out), 'FontSize', 12);
|
||||
text(0.1, 0.4, sprintf('Улучшение: %.1f дБ', improvement_temp), 'FontSize', 12);
|
||||
text(0.1, 0.2, sprintf('Задержка 1 Гц: %.1f мс', gd_lpf_temp(idx_1hz)/Fs*1000), 'FontSize', 12);
|
||||
title('Статистика фильтрации температуры');
|
||||
axis off;
|
||||
%
|
||||
% %% ОКНО 3: ТЕМПЕРАТУРА
|
||||
% figure('Name', 'Анализ температуры');
|
||||
%
|
||||
% % Временные характеристики
|
||||
% subplot(2,3,1);
|
||||
% plot(t, temperature_noisy, 'b', 'LineWidth', 1); hold on;
|
||||
% plot(t, temperature_filtered, 'r', 'LineWidth', 2);
|
||||
% plot(t, temperature_clean, 'g--', 'LineWidth', 1);
|
||||
% title('Температура: временная область');
|
||||
% legend('С шумом', 'Фильтрованный', 'Идеальный', 'Location', 'best');
|
||||
% xlabel('Время [с]'); ylabel('Температура [°C]');
|
||||
% grid on;
|
||||
%
|
||||
% % АЧХ фильтра
|
||||
% subplot(2,3,2);
|
||||
% plot(f_lpf_temp, 20*log10(abs(h_lpf_temp)), 'LineWidth', 2);
|
||||
% title('АЧХ: ФНЧ 10 Гц');
|
||||
% xlabel('Частота [Гц]'); ylabel('Усиление [дБ]');
|
||||
% grid on; xlim([0, 20]);
|
||||
%
|
||||
% % Спектр фильтрованного сигнала
|
||||
% subplot(2,3,3);
|
||||
% [P_temp, f_temp] = pwelch(temperature_filtered, [], [], 1024, Fs);
|
||||
% plot(f_temp, 10*log10(P_temp), 'LineWidth', 2);
|
||||
% title('Спектр фильтрованной температуры');
|
||||
% xlabel('Частота [Гц]'); ylabel('Мощность [дБ]');
|
||||
% grid on; xlim([0, 10]);
|
||||
%
|
||||
% % Групповая задержка
|
||||
% subplot(2,3,4);
|
||||
% [gd_lpf_temp, f_gd_temp] = grpdelay(b_lpf_temp, a_lpf_temp, 1024, Fs);
|
||||
% plot(f_gd_temp, gd_lpf_temp/Fs*1000, 'LineWidth', 2);
|
||||
% title('Групповая задержка фильтра');
|
||||
% xlabel('Частота [Гц]'); ylabel('Задержка [мс]');
|
||||
% grid on; xlim([0, 20]);
|
||||
%
|
||||
% % Детальный вид (последне 0.1 секунды)
|
||||
% idx_end_temp = max(1, length(t) - 0.1*Fs + 1):length(t); % последние 100 мс
|
||||
% subplot(2,3,5);
|
||||
% plot(t(idx_end_temp), temperature_noisy(idx_end_temp), 'b', 'LineWidth', 2); hold on;
|
||||
% plot(t(idx_end_temp), temperature_filtered(idx_end_temp), 'r', 'LineWidth', 2);
|
||||
% plot(t(idx_end_temp), temperature_clean(idx_end_temp), 'g--', 'LineWidth', 2);
|
||||
% title('Температура: УВЕЛИЧЕННЫЙ ВИД (900-1000 мс)');
|
||||
% legend('С шумом', 'Фильтрованный', 'Идеальный', 'Location', 'best');
|
||||
% xlabel('Время [с]'); ylabel('Температура [°C]');
|
||||
% grid on;
|
||||
% xlim([t(idx_end_temp(1)) t(idx_end_temp(end))]);
|
||||
%
|
||||
% % Статистика
|
||||
% subplot(2,3,6);
|
||||
% snr_temp_in = snr(temperature_clean, temperature_noisy - temperature_clean);
|
||||
% snr_temp_out = snr(temperature_clean, temperature_filtered - temperature_clean);
|
||||
% improvement_temp = snr_temp_out - snr_temp_in;
|
||||
%
|
||||
% [~, idx_1hz] = min(abs(f_gd_temp - 1));
|
||||
% text(0.1, 0.8, sprintf('SNR вход: %.1f дБ', snr_temp_in), 'FontSize', 12);
|
||||
% text(0.1, 0.6, sprintf('SNR выход: %.1f дБ', snr_temp_out), 'FontSize', 12);
|
||||
% text(0.1, 0.4, sprintf('Улучшение: %.1f дБ', improvement_temp), 'FontSize', 12);
|
||||
% text(0.1, 0.2, sprintf('Задержка 1 Гц: %.1f мс', gd_lpf_temp(idx_1hz)/Fs*1000), 'FontSize', 12);
|
||||
% title('Статистика фильтрации температуры');
|
||||
% axis off;
|
||||
|
||||
%% Вывод результатов в командное окно
|
||||
fprintf('\n=== ИТОГИ ФИЛЬТРАЦИИ С АВТОРАСЧЕТОМ КОЭФФИЦИЕНТОВ ===\n\n');
|
||||
@@ -288,7 +289,7 @@ fprintf(' SNR вход: %.1f дБ, выход: %.1f дБ, улучшение: %
|
||||
snr_current_in, snr_current_out, improvement_current);
|
||||
fprintf(' Задержка на 50 Гц: %.1f мс\n\n', gd_lpf_curr(idx_50hz_curr)/Fs*1000);
|
||||
|
||||
fprintf('ТЕМПЕРАТУРА (ФНЧ 10 Гц):\n');
|
||||
fprintf(' SNR вход: %.1f дБ, выход: %.1f дБ, улучшение: %.1f дБ\n', ...
|
||||
snr_temp_in, snr_temp_out, improvement_temp);
|
||||
fprintf(' Задержка на 1 Гц: %.1f мс\n\n', gd_lpf_temp(idx_1hz)/Fs*1000);
|
||||
% fprintf('ТЕМПЕРАТУРА (ФНЧ 10 Гц):\n');
|
||||
% fprintf(' SNR вход: %.1f дБ, выход: %.1f дБ, улучшение: %.1f дБ\n', ...
|
||||
% snr_temp_in, snr_temp_out, improvement_temp);
|
||||
% fprintf(' Задержка на 1 Гц: %.1f мс\n\n', gd_lpf_temp(idx_1hz)/Fs*1000);
|
||||
|
||||
Reference in New Issue
Block a user