⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 ofdm_simulation_program.m

📁 这是我见过的最详细可读性非常高的ofdm仿真程序
💻 M
📖 第 1 页 / 共 2 页
字号:
% END OF PLOTTING
%
%--------1---------2---------3---------4---------5---------6---------7---------8
%
% Apply a Window Function to each time waveform
% - NOTE THAT WINDOWING IS CURRENTLY COMMENTED OUT, i.e. NO WINDOWING
% - each time waveform (row of time_wave_matrix) represents one symbol
% period for all carriers
% - the IFFT result has discontinuities at each end
% - when the time waveforms are serialized (concatenated), the discontinuites
% will introduce unwanted frequency components
% - the window function deemphasizes the signal at the end
% points (at the discontinuites)
% - this reduces the effects of the discontinuities
% - it also distorts the desired frequency response (undesired side effect)
% - between Blackman, Hanning, and Hamming: Hamming introduces less distortion
% - note that the transpose of the Hamming function is
% used (because a row vector is needed)
%
% Since all imaginary values of time_wave_matrix are practically equal to zero,
% only the real part is retained for windowing.
%
for i = 1:symbols_per_carrier + 1
%windowed_time_wave_matrix(i,:) = real(time_wave_matrix(i,:)) .* hamming(IFFT_bin_length)';
windowed_time_wave_matrix(i,:) = real(time_wave_matrix(i,:));
end
%
% Serialize the modulating waveform
% - sequentially take each row of windowed_time_wave_matrix and construct a row vector
% - the row vector will be the modulating signal
% - note that windowed_time_wave_matrix is transposed, this is to account for the way the
% Matlab 'reshape' function works (reshape takes the columns of the target matrix and
% appends them sequentially)
%
ofdm_modulation = reshape(windowed_time_wave_matrix', 1,IFFT_bin_length*(symbols_per_carrier+1));  %reshape前转置保证操作将每个符号连在一起
%
% PLOT OFDM SIGNAL (time)

temp_time = IFFT_bin_length*(symbols_per_carrier+1);
figure (5)
plot(0:temp_time-1,ofdm_modulation)
grid on
ylabel('Amplitude (volts)')
xlabel('Time (samples)')
title('OFDM Time Signal')

% PLOT OFDM SIGNAL (spectrum)
symbols_per_average = ceil(symbols_per_carrier/5);  %每次取的符号数
avg_temp_time = IFFT_bin_length*symbols_per_average;  %每次取的采样点数=每次取的符号数*一个符号的采样点数
averages = floor(temp_time/avg_temp_time);%进行平均的次数=总采样点数/每次所取采样点数
average_fft(1:avg_temp_time) = 0;     %初始化
for a = 0:(averages-1)
subset_ofdm = ofdm_modulation(((a*avg_temp_time)+1):((a+1)*avg_temp_time)); %
subset_ofdm_f = abs(fft(subset_ofdm));  %每次进行FFT,并求其幅值
average_fft = average_fft + (subset_ofdm_f/averages);  %符号平均
end
average_fft_log = 20*log10(average_fft);
figure (6)
plot((0:(avg_temp_time-1))/avg_temp_time, average_fft_log)   %对X轴进行归一化作图,
hold on
plot(0:1/IFFT_bin_length:1, -35, 'rd')
grid on
axis([0 0.5 -40 max(average_fft_log)])
ylabel('Magnitude (dB)')
xlabel('Normalized Frequency (0.5 = fs/2)')
title('OFDM Signal Spectrum')

% ENDPLOT
%
%--------1---------2---------3---------4---------5---------6---------7---------8
%
% Upconversion to RF
%
% For this model, the baseband will be inserted directly into the channel
% without conversion to RF frequencies.
%
Tx_data = ofdm_modulation;
%
%--------1---------2---------3---------4---------5---------6---------7---------8
%
% CHANNEL
% ======================================================================
%
% The channel model is Gaussian (AWGN) only
% - Rayleigh fading would be a useful addition
%
Tx_signal_power = var(Tx_data);
%
linear_SNR = 10^(SNR/10);
noise_sigma = Tx_signal_power/linear_SNR;
noise_scale_factor = sqrt(noise_sigma);
%
noise = randn(1, length(Tx_data))*noise_scale_factor;
Rx_Data = Tx_data + noise;
%
%
% RECEIVE
% <<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<
%
%
% Convert the serial input data stream to parallel (according to symbol length
% and number of symbols)
% - each column is a symbol period
% - the length of each symbol (samples per symbol) is the length of the
% IFFT that was used to generate it
%
Rx_Data_matrix = reshape(Rx_Data, IFFT_bin_length, symbols_per_carrier + 1);  %列为符号
%
% Transform each symbol from time to frequency domain
% - take the fft of each column
%
Rx_spectrum = fft(Rx_Data_matrix);%
% PLOT BASIC FREQUENCY DOMAIN REPRESENTATION
%
%--------1---------2---------3---------4---------5---------6---------7---------8

figure (7)
stem(0:IFFT_bin_length-1, abs(Rx_spectrum(1:IFFT_bin_length,2)),'b*-')
grid on
axis ([0 IFFT_bin_length -0.5 1.5])
ylabel('Magnitude')
xlabel('FFT Bin')
title('OFDM Receive Spectrum, Magnitude')
figure (8)
plot(0:IFFT_bin_length-1, (180/pi)*angle(Rx_spectrum(1:IFFT_bin_length,2)), 'go')
hold on
stem(carriers-1, (180/pi)*angle(Rx_spectrum(carriers,2)),'b*-')
stem(conjugate_carriers-1, (180/pi)*angle(Rx_spectrum(conjugate_carriers,2)),'b*-')
axis ([0 IFFT_bin_length -200 +200])
grid on
ylabel('Phase (degrees)')
xlabel('FFT Bin')
title('OFDM Receive Spectrum, Phase')

% END OF PLOTTING
%--------1---------2---------3---------4---------5---------6---------7---------8
%
% Extract the carrier FFT bins
% - only keep the fft bins that are used as carriers
% - take the transpose of the result so that each column will represent
% a carrier
% - this is in preparation for using the diff( ) function later to decode
% differential encoding
% - format following this operation is:
%
% C1-s1 C2-s1 C3-s1 ...
% C1-s2 C2-s2 C3-s2 ...
% C1-s3 C2-s3 C3-s3 ...
% . . .
% . . .
%
% - IMPORTANT MATLAB NOTE CONCERNING TRANSPOSING AND CONJUGATION
% - it appears that each time a matrix is transposed, the conjugate of
% each value is taken
% - if an even number of transposes are done, then it is transparent
% - obviously, this does not affect real numbers
%
Rx_carriers = Rx_spectrum(carriers,:)';
%
%--------1---------2---------3---------4---------5---------6---------7---------8
%
% PLOT EACH RECEIVED SYMBOL
%
figure (9)
Rx_phase_P = angle(Rx_carriers);
Rx_mag_P = abs(Rx_carriers);
polar(Rx_phase_P, Rx_mag_P,'bd');
%
% END PLOT
%
% Find the phase (angle) of each FFT bin (each carrier)
% - convert from radians to degrees
% - normalize phase to be between 0 and 359 degrees
%
Rx_phase = angle(Rx_carriers)*(180/pi);
phase_negative = find(Rx_phase < 0);
Rx_phase(phase_negative) = rem(Rx_phase(phase_negative)+360,360);
%
% Extract phase differences (from the differential encoding)
% - the matlab diff( ) function is perfect for this operation
% - again, normalize the result to be between 0 and 359 degrees
%
Rx_decoded_phase = diff(Rx_phase);
phase_negative = find(Rx_decoded_phase < 0);
Rx_decoded_phase(phase_negative) = rem(Rx_decoded_phase(phase_negative)+360,360);
%
%--------1---------2---------3---------4---------5---------6---------7---------8
%
% Convert phase to symbol
% - calculate the base phase which is the phase difference between each
% consecutive symbol
% - for example, if there are 2 bits per symbol, base phase is 90 and the
% symbols are represented by 0, 90, 180, and 270 degrees
% - calculate the maximum deviation from the base phase that will still be
% decoded as base phase
% - for example, if base phase is 90, then delta phase is 45, and anything
% within 45 degrees of base phase is accepted as base phase
% - continuing the above example, a symbol represented by 180 will be
% decoded as 180 as long as it is within the range 180+45 and 180-45
% - generate a symbol matrix where the results of the phase decode
% will be placed
% - note that since the matrix is created as a zero matrix, then the zero
% values do not have to be decoded
% - zero is therefore the default value after decoding, if a value is not
% decoded as anything else, then it is zero
% - this actually save alot of trouble since the zero phase spans the
% lowest and highest phase values and therefore requires special
% processing
% - it is also efficient in that it eliminates a pass through the loop
%
base_phase = 360/2^bits_per_symbol;
delta_phase = base_phase/2;
Rx_decoded_symbols = zeros(size(Rx_decoded_phase,1),size(Rx_decoded_phase,2));
%
for i = 1:(2^bits_per_symbol - 1)
center_phase = base_phase*i;
plus_delta = center_phase+delta_phase;
minus_delta = center_phase-delta_phase;
decoded = find((Rx_decoded_phase <= plus_delta) & (Rx_decoded_phase > minus_delta));
Rx_decoded_symbols(decoded)=i;
end
%
% Convert the matrix into a serial symbol stream
%
Rx_serial_symbols = reshape(Rx_decoded_symbols',1,size(Rx_decoded_symbols,1)*size(Rx_decoded_symbols,2));
%
% Convert the symbols to binary
%
for i = bits_per_symbol: -1: 1
if i ~= 1
Rx_binary_matrix(i,:) = rem(Rx_serial_symbols,2);
Rx_serial_symbols = floor(Rx_serial_symbols/2);
else
Rx_binary_matrix(i,:) = Rx_serial_symbols;
end
end
baseband_in = reshape(Rx_binary_matrix,1,size(Rx_binary_matrix,1)*size(Rx_binary_matrix,2));
%
% Find bit errors
%
bit_errors = find(baseband_in ~= baseband_out);
bit_error_count = size(bit_errors,2);
%--------1---------2---------3---------4---------5---------6---------7-----
%----8

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -