├── .gitignore ├── docs ├── AHLogo.png ├── LICENSE ├── README.md ├── _config.yml ├── book_cover.jpg └── book_cover_small.png ├── jupyter ├── Chapter01 │ └── jupyter.ipynb ├── Chapter02 │ ├── apparent_elevation.ipynb │ ├── apparent_range.ipynb │ ├── atmosphere.ipynb │ ├── beam_spreading.ipynb │ ├── cloud_fog.ipynb │ ├── diffraction.ipynb │ ├── ducting.ipynb │ ├── lib_path.py │ ├── plane_waves.ipynb │ ├── rain_attenuation.ipynb │ ├── reflection_transmission.ipynb │ └── vegetation.ipynb ├── Chapter03 │ ├── circular_aperture.ipynb │ ├── circular_array.ipynb │ ├── horn.ipynb │ ├── lib_path.py │ ├── linear_array.ipynb │ ├── linear_wire.ipynb │ ├── loop.ipynb │ ├── planar_array.ipynb │ └── rectangular_aperture.ipynb ├── Chapter04 │ ├── hertzian_dipole.ipynb │ ├── lib_path.py │ ├── loop_gain.ipynb │ ├── maximum_detection_range.ipynb │ ├── minimum_detectable_signal.ipynb │ ├── output_signal_to_noise.ipynb │ ├── output_signal_to_noise_bistatic.ipynb │ ├── output_signal_to_noise_search.ipynb │ ├── ovals_of_cassini.ipynb │ ├── power_aperture.ipynb │ ├── power_at_radar.ipynb │ ├── power_at_radar_bistatic.ipynb │ └── power_density.ipynb ├── Chapter05 │ ├── adc.ipynb │ ├── coherent_detector.ipynb │ ├── envelope_detector.ipynb │ ├── lib_path.py │ ├── low_pass_filter.ipynb │ ├── noise_figure.ipynb │ ├── resolution.ipynb │ └── sensitivity_time_control.ipynb ├── Chapter06 │ ├── binary_integration.ipynb │ ├── cfar.ipynb │ ├── coherent_integration.ipynb │ ├── gaussian_noise_pd.ipynb │ ├── lib_path.py │ ├── non_coherent_integration.ipynb │ ├── optimum_binary.ipynb │ ├── probability_distributions.ipynb │ ├── rayleigh_noise_pd.ipynb │ ├── shnidman_approximation.ipynb │ └── single_pulse_snr.ipynb ├── Chapter07 │ ├── frustum.ipynb │ ├── infinite_cylinder.ipynb │ ├── infinite_cylinder_oblique.ipynb │ ├── infinite_strip.ipynb │ ├── lib_path.py │ ├── rectangular_plate.ipynb │ ├── right_circular_cone.ipynb │ ├── rounded_nose_cone.ipynb │ └── stratified_sphere.ipynb ├── Chapter08 │ ├── barker_ambiguity.ipynb │ ├── frank_ambiguity.ipynb │ ├── lfm_pulse_ambiguity.ipynb │ ├── lfm_train_ambiguity.ipynb │ ├── lib_path.py │ ├── matched_filter.ipynb │ ├── prn_ambiguity.ipynb │ ├── pulse_train_ambiguity.ipynb │ ├── single_pulse_ambiguity.ipynb │ ├── stepped_frequency.ipynb │ └── stretch_processor.ipynb ├── Chapter09 │ ├── alpha_beta.ipynb │ ├── alpha_beta_gamma.ipynb │ ├── kalman_constant_acceleration.ipynb │ ├── kalman_constant_velocity.ipynb │ ├── kalman_epsilon.ipynb │ ├── kalman_sigma.ipynb │ └── lib_path.py ├── Chapter10 │ ├── back_projection_2d.ipynb │ ├── lib_path.py │ └── stripmap_2d.ipynb └── Chapter11 │ ├── burn_through_range.ipynb │ ├── crossover_range.ipynb │ ├── delay_line.ipynb │ ├── jammer_to_signal.ipynb │ └── lib_path.py ├── mlradar ├── Chapter01 │ └── initial_test.m ├── Chapter02 │ ├── apparent_elevation_example.m │ ├── apparent_range_example.m │ ├── atmosphere_example.m │ ├── beam_spreading_example.m │ ├── cloud_fog_example.m │ ├── diffraction_example.m │ ├── ducting_example.m │ ├── plane_waves_example.m │ ├── rain_attenuation_example.m │ ├── reflection_transmission_example.m │ └── vegetation_attenuation_example.m ├── Chapter03 │ ├── circular_aperture_example.m │ ├── circular_array_example.m │ ├── horn_example.m │ ├── linear_array_example.m │ ├── linear_wire_example.m │ ├── loop_example.m │ ├── planar_array_example.m │ └── rectangular_aperture_example.m ├── Chapter04 │ ├── hertzian_dipole_example.m │ ├── loop_gain_example.m │ ├── maximum_detection_range_example.m │ ├── minimum_detectable_signal_example.m │ ├── ouput_signal_to_noise_bistatic_example.m │ ├── output_signal_to_noise_example.m │ ├── output_signal_to_noise_search_example.m │ ├── ovals_of_cassini_example.m │ ├── power_aperture_example.m │ ├── power_at_radar_bistatic_example.m │ ├── power_at_radar_example.m │ └── power_density_example.m ├── Chapter05 │ ├── adc_example.m │ ├── coherent_detector_example.m │ ├── envelope_detector_example.m │ ├── low_pass_filter_example.m │ ├── noise_figure_example.m │ ├── resolution_example.m │ └── sensitivity_time_control_example.m ├── Chapter06 │ ├── binary_integration_example.m │ ├── cfar_example.m │ ├── coherent_integration_example.m │ ├── gaussian_noise_pd_example.m │ ├── non_coherent_integration_example.m │ ├── optimum_binary_example.m │ ├── probability_distributions_example.m │ ├── rayleigh_noise_pd_example.m │ ├── shnidman_example.m │ └── single_pulse_snr_example.m ├── Chapter07 │ ├── fdtd_example.m │ ├── frustum_example.m │ ├── infinite_cylinder_example.m │ ├── infinite_cylinder_oblique_example.m │ ├── infinite_strip_example.m │ ├── po_example.m │ ├── rectangular_plate_example.m │ ├── right_circular_cone_example.m │ ├── rounded_nose_cone_example.m │ └── stratified_sphere_example.m ├── Chapter08 │ ├── PRN_ambiguity_example.m │ ├── barker_ambiguity_example.m │ ├── frank_ambiguity_example.m │ ├── lfm_pulse_ambiguity_example.m │ ├── lfm_train_ambiguity_example.m │ ├── matched_filter_example.m │ ├── pulse_train_ambiguity_example.m │ ├── single_pulse_ambiguity_example.m │ ├── stepped_frequency_example.m │ └── stretch_processor_example.m ├── Chapter09 │ ├── alpha_beta_example.m │ ├── alpha_beta_gamma_example.m │ ├── kalman_ca_example.m │ ├── kalman_cv_example.m │ ├── kalman_epsilon_example.m │ └── kalman_sigma_example.m ├── Chapter10 │ ├── back_projection_3d_example.m │ ├── back_projection_backhoe_example.m │ ├── back_projection_cv_example.m │ ├── back_projection_example.m │ ├── stripmap_cv_example.m │ └── stripmap_example.m ├── Chapter11 │ ├── burn_through_range_example.m │ ├── crossover_range_example.m │ ├── delay_line_example.m │ └── jammer_to_signal_example.m └── libs │ ├── ambiguity │ ├── hamming.m │ ├── hanning.m │ ├── kaiser.m │ ├── lfm_pulse.m │ ├── lfm_train.m │ ├── mls.m │ ├── n_phase_code.m │ ├── phase_coded_waveform.m │ ├── pulse_train.m │ └── single_pulse.m │ ├── antennas │ ├── aperture │ │ ├── circular_te11_ground_plane.m │ │ ├── circular_uniform_ground_plane.m │ │ ├── rectangular_te10_ground_plane.m │ │ ├── rectangular_uniform_free_space.m │ │ └── rectangular_uniform_ground_plane.m │ ├── array │ │ ├── circular_array.m │ │ ├── linear_array.m │ │ ├── planar_array.m │ │ └── tschebyscheff_coefficients.m │ ├── horn │ │ ├── eplane_sectoral_horn.m │ │ ├── hplane_sectoral_horn.m │ │ └── pyramidal_horn.m │ ├── linear_wire │ │ ├── finite_length_dipole.m │ │ ├── infinitesimal_dipole.m │ │ └── small_dipole.m │ └── loop │ │ ├── circular_loop.m │ │ └── small_loop.m │ ├── detection │ ├── Q.m │ ├── binary_integration.m │ ├── cfar.m │ ├── coherent_integration.m │ ├── non_coherent_integration.m │ ├── pd_gaussian.m │ ├── pd_rayleigh.m │ ├── shnidman.m │ ├── single_pulse_snr.m │ ├── single_pulse_snr_swerling.m │ ├── snr_gain.m │ └── snr_reduction.m │ ├── ecm │ ├── burn_through_range_escort.m │ ├── burn_through_range_selfscreen.m │ ├── crossover_range_escort.m │ ├── crossover_range_selfscreen.m │ └── jammer_to_signal.m │ ├── radar_range │ ├── bistatic_equation │ │ ├── output_snr_bistatic.m │ │ ├── output_snr_polar.m │ │ └── power_at_radar_bistatic.m │ ├── hertzian_dipole │ │ ├── directivity.m │ │ ├── electric_field.m │ │ ├── magnetic_field.m │ │ ├── power_density.m │ │ ├── radiation_intensity.m │ │ └── total_radiated_power.m │ ├── range_equation │ │ ├── loop_gain.m │ │ ├── maximum_range.m │ │ ├── minimum_detectable_signal.m │ │ ├── output_snr.m │ │ ├── power_at_radar.m │ │ └── power_density_radar.m │ └── search_eqaution │ │ ├── output_snr_search.m │ │ └── power_aperture.m │ ├── rcs │ ├── cone.facet │ ├── cylinder_oblique_rcs_2d.m │ ├── cylinder_oblique_rcs_3d.m │ ├── cylinder_rcs_2d.m │ ├── cylinder_rcs_3d.m │ ├── double_ogive.facet │ ├── fdtd.cell │ ├── fdtd.m │ ├── frustum.facet │ ├── plate.facet │ ├── po_scattering.m │ ├── rcs_frustum.m │ ├── read_facet_model.m │ ├── read_fdtd_geometry.m │ ├── rectangular_plate.m │ ├── right_circular_cone.m │ ├── rounded_nose_cone.m │ ├── sphere_coefficients.m │ ├── stratified_sphere.m │ └── strip_rcs.m │ ├── receivers │ ├── cascade_noise_figure.m │ ├── chirp.m │ ├── coherent_detector.m │ ├── envelope_detector.m │ ├── quantization.m │ └── sensitivity_time_control.m │ ├── sar │ ├── backprojection.m │ ├── backprojection_3d.m │ └── backprojection_cv.m │ ├── tracking │ └── kalman.m │ ├── utils │ ├── cosint.m │ ├── cosint_arg.m │ ├── db.m │ ├── ecef_to_lla.m │ ├── fftfreq.m │ ├── fresnel.m │ ├── lin.m │ ├── lla_to_ecef.m │ ├── plot_settings.m │ ├── sinc.m │ ├── sinint.m │ └── sinint_arg.m │ └── wave_propagation │ ├── apparent_elevation.m │ ├── apparent_elevation_approximate.m │ ├── apparent_range.m │ ├── atmospheric_attenuation.m │ ├── brewster_angle.m │ ├── cloud_fog_attenuation.m │ ├── critical_angle.m │ ├── diffraction_attenuation.m │ ├── ducting.m │ ├── oxygen_spectral_attenuation.txt │ ├── plane_wave_parameters.m │ ├── rain_attenuation.m │ ├── reflection_transmission.m │ ├── vegetation_attenuation.m │ └── water_vapor_spectral_attenuation.txt └── pyradar ├── Chapter01 ├── RadarBook.py ├── __init__.py └── ui │ ├── RadarBook_ui.py │ └── __init__.py ├── Chapter02 ├── __init__.py ├── apparent_elevation_example.py ├── apparent_range_example.py ├── atmosphere_example.py ├── beam_spreading_example.py ├── cloud_fog_example.py ├── diffraction_example.py ├── ducting_example.py ├── plane_waves_example.py ├── rain_attenuation_example.py ├── reflection_transmission_example.py ├── ui │ ├── ApparentElevation_ui.py │ ├── ApparentRange_ui.py │ ├── Atmosphere_ui.py │ ├── BeamSpreading_ui.py │ ├── CloudFog_ui.py │ ├── Diffraction_ui.py │ ├── Ducting_ui.py │ ├── PlaneWaves_ui.py │ ├── RainAttenuation_ui.py │ ├── ReflectionTransmission_ui.py │ ├── VegetationAttenuation_ui.py │ └── __init__.py └── vegetation_example.py ├── Chapter03 ├── __init__.py ├── circular_aperture_example.py ├── circular_array_example.py ├── horn_example.py ├── linear_array_example.py ├── linear_wire_example.py ├── loop_example.py ├── planar_array_example.py ├── rectangular_aperture_example.py └── ui │ ├── CircularAperture_ui.py │ ├── CircularArray_ui.py │ ├── Horn_ui.py │ ├── LinearArray_ui.py │ ├── LinearWire_ui.py │ ├── Loop_ui.py │ ├── PlanarArray_ui.py │ ├── RectangularAperture_ui.py │ └── __init__.py ├── Chapter04 ├── __init__.py ├── hertzian_dipole_example.py ├── loop_gain_example.py ├── maximum_detection_range_example.py ├── minimum_detectable_signal_example.py ├── output_signal_to_noise_bistatic_example.py ├── output_signal_to_noise_example.py ├── output_signal_to_noise_search_example.py ├── ovals_of_cassini_example.py ├── power_aperture_example.py ├── power_at_radar_bistatic_example.py ├── power_at_radar_example.py ├── power_density_example.py └── ui │ ├── HertzianDipole_ui.py │ ├── LoopGain_ui.py │ ├── MaximumDetectionRange_ui.py │ ├── MinimumDetectableSignal_ui.py │ ├── OutputSNRBistatic_ui.py │ ├── OutputSNRSearch_ui.py │ ├── OutputSNR_ui.py │ ├── OvalsOfCassini_ui.py │ ├── PowerAperture_ui.py │ ├── PowerAtRadarBistatic_ui.py │ ├── PowerAtRadar_ui.py │ ├── PowerDensity_ui.py │ └── __init__.py ├── Chapter05 ├── __init__.py ├── adc_example.py ├── coherent_detector_example.py ├── envelope_detector_example.py ├── low_pass_filter_example.py ├── noise_figure_example.py ├── resolution_example.py ├── sensitivity_time_control_example.py └── ui │ ├── ADC_ui.py │ ├── BinaryIntegration_ui.py │ ├── CFAR_ui.py │ ├── CoherentDetector_ui.py │ ├── EnvelopeDetector_ui.py │ ├── LowPassFilter_ui.py │ ├── NoiseFigure_ui.py │ ├── Resolution_ui.py │ ├── STC_ui.py │ └── __init__.py ├── Chapter06 ├── __init__.py ├── binary_integration_example.py ├── cfar_example.py ├── coherent_integration_example.py ├── gaussian_noise_pd_example.py ├── non_coherent_integration_example.py ├── optimum_binary_example.py ├── probability_distributions_example.py ├── rayleigh_noise_pd_example.py ├── shnidman_example.py ├── single_pulse_snr_example.py └── ui │ ├── BinaryIntegration_ui.py │ ├── CFAR_ui.py │ ├── CoherentPd_ui.py │ ├── Distributions_ui.py │ ├── GaussianNoisePd_ui.py │ ├── NonCoherentPd_ui.py │ ├── OptimumBinary_ui.py │ ├── RayleighNoisePd_ui.py │ ├── RayleignNoisePd_ui.py │ ├── Shnidman_ui.py │ ├── SinglePulsePd_ui.py │ ├── SinglePulseSNR_ui.py │ └── __init__.py ├── Chapter07 ├── __init__.py ├── fdtd_example.py ├── frustum_example.py ├── infinite_cylinder_example.py ├── infinite_cylinder_oblique_example.py ├── infinite_strip_example.py ├── po_example.py ├── rectangular_plate_example.py ├── right_circular_cone_example.py ├── rounded_nose_cone_example.py ├── stratified_sphere_example.py └── ui │ ├── FDTD_ui.py │ ├── Frustum_ui.py │ ├── InfiniteCylinderOblique_ui.py │ ├── InfiniteCylinder_ui.py │ ├── InfiniteStrip_ui.py │ ├── PO_ui.py │ ├── RectangularPlate_ui.py │ ├── RightCircularCone_ui.py │ ├── RoundedNoseCone_ui.py │ ├── StratifiedSphere_ui.py │ └── __init__.py ├── Chapter08 ├── PRN_ambiguity_example.py ├── __init__.py ├── barker_ambiguity_example.py ├── frank_ambiguity_example.py ├── lfm_pulse_ambiguity_example.py ├── lfm_train_ambiguity_example.py ├── matched_filter_example.py ├── pulse_train_ambiguity_example.py ├── single_pulse_ambiguity_example.py ├── stepped_frequency_example.py ├── stretch_processor_example.py └── ui │ ├── AFSingle_ui.py │ ├── AFTrain_ui.py │ ├── AF_Barker_ui.py │ ├── AF_Frank_ui.py │ ├── AF_LFM_ui.py │ ├── AF_PRN_ui.py │ ├── LFM_Train_ui.py │ ├── MatchedFilter_ui.py │ ├── SteppedFrequency_ui.py │ ├── StretchProcessor_ui.py │ └── __init__.py ├── Chapter09 ├── __init__.py ├── alpha_beta_example.py ├── alpha_beta_gamma_example.py ├── kalman_ca_example.py ├── kalman_cv_example.py ├── kalman_epsilon_example.py ├── kalman_sigma_example.py └── ui │ ├── AlphaBetaGamma_ui.py │ ├── AlphaBeta_ui.py │ ├── KalmanAcceleration_ui.py │ ├── KalmanAdaptiveEpsilon_ui.py │ ├── KalmanAdaptiveSigma_ui.py │ ├── Kalman_ui.py │ └── __init__.py ├── Chapter10 ├── __init__.py ├── back_projection_3d_example.py ├── back_projection_backhoe_example.py ├── back_projection_cv_example.py ├── back_projection_example.py ├── stripmap_cv_example.py ├── stripmap_example.py └── ui │ ├── BackProjection3pt_ui.py │ ├── BackProjectionBH_ui.py │ ├── BackProjectionCV_ui.py │ ├── BackProjection_ui.py │ ├── StripmapCV_ui.py │ ├── Stripmap_ui.py │ └── __init__.py ├── Chapter11 ├── __init__.py ├── burnthrough_range_example.py ├── crossover_range_example.py ├── delay_line_example.py ├── jammer_to_signal_example.py └── ui │ ├── Burnthrough_ui.py │ ├── Crossover_ui.py │ ├── DelayLine_ui.py │ ├── JSR_ui.py │ └── __init__.py ├── Libs ├── __init__.py ├── ambiguity │ ├── __init__.py │ ├── ambiguity_function.py │ ├── frank_code.py │ └── prn_code.py ├── antenna │ ├── __init__.py │ ├── aperture │ │ ├── __init__.py │ │ ├── circular_te11_ground_plane.py │ │ ├── circular_uniform_ground_plane.py │ │ ├── rectangular_te10_ground_plane.py │ │ ├── rectangular_uniform_free_space.py │ │ └── rectangular_uniform_ground_plane.py │ ├── array │ │ ├── __init__.py │ │ ├── circular_uniform.py │ │ ├── linear_array.py │ │ ├── linear_array_un.py │ │ └── planar_uniform.py │ ├── horn │ │ ├── __init__.py │ │ ├── e_plane_sectoral.py │ │ ├── h_plane_sectoral.py │ │ └── pyramidal.py │ ├── linear_wire │ │ ├── __init__.py │ │ ├── finite_length_dipole.py │ │ ├── infinitesimal_dipole.py │ │ └── small_dipole.py │ └── loop │ │ ├── __init__.py │ │ ├── circular_loop.py │ │ └── small_loop.py ├── detection │ ├── __init__.py │ ├── binary_integration.py │ ├── cfar.py │ ├── coherent_integration.py │ ├── non_coherent_integration.py │ ├── shnidman.py │ └── single_pulse.py ├── ecm │ ├── __init__.py │ └── countermeasures.py ├── python_icon.png ├── radar_range │ ├── __init__.py │ ├── bistatic_radar_range.py │ ├── hertzian_dipole.py │ ├── radar_range.py │ └── search_radar_range.py ├── rcs │ ├── __init__.py │ ├── backhoe.facet │ ├── cone.facet │ ├── display_facet_model.py │ ├── double_ogive.facet │ ├── fdtd.cell │ ├── frustum.facet │ ├── frustum.py │ ├── infinite_cylinder.py │ ├── infinite_cylinder_oblique.py │ ├── infinite_strip.py │ ├── ogive.facet │ ├── plate.facet │ ├── rectangular_plate.py │ ├── right_circular_cone.py │ ├── rounded_nose_cone.py │ ├── scattering_matrix.py │ ├── sphere.facet │ └── stratified_sphere.py ├── receivers │ ├── __init__.py │ ├── coherent_detector.py │ ├── envelope_detector.py │ ├── noise_figure.py │ ├── quantization.py │ └── sensitivity_time_control.py ├── resources.qrc ├── resources_rc.py ├── sar │ ├── __init__.py │ └── backprojection.py ├── tracking │ ├── __init__.py │ └── kalman.py ├── utils │ ├── __init__.py │ ├── ecef_to_lla.py │ ├── lla_to_ecef.py │ └── plot_settings.py └── wave_propagation │ ├── __init__.py │ ├── atmosphere.py │ ├── cloud_fog.py │ ├── diffraction.py │ ├── ducting.py │ ├── oxygen_spectral_attenuation.txt │ ├── plane_waves.py │ ├── rain.py │ ├── refraction.py │ ├── vegetation.py │ └── water_vapor_spectral_attenuation.txt └── setup.py /.gitignore: -------------------------------------------------------------------------------- 1 | # Byte-compiled / optimized / DLL files 2 | __pycache__/ 3 | *.py[cod] 4 | *$py.class 5 | 6 | # C extensions 7 | *.so 8 | 9 | # UI 10 | *.ui 11 | 12 | # Distribution / packaging 13 | .Python 14 | env/ 15 | build/ 16 | develop-eggs/ 17 | dist/ 18 | downloads/ 19 | eggs/ 20 | .eggs/ 21 | lib/ 22 | lib64/ 23 | parts/ 24 | sdist/ 25 | var/ 26 | wheels/ 27 | *.egg-info/ 28 | .installed.cfg 29 | *.egg 30 | 31 | # PyInstaller 32 | # Usually these files are written by a python script from a template 33 | # before PyInstaller builds the exe, so as to inject date/other infos into it. 34 | *.manifest 35 | *.spec 36 | 37 | # Installer logs 38 | pip-log.txt 39 | pip-delete-this-directory.txt 40 | 41 | # Unit test / coverage reports 42 | htmlcov/ 43 | .tox/ 44 | .coverage 45 | .coverage.* 46 | .cache 47 | nosetests.xml 48 | coverage.xml 49 | *.cover 50 | .hypothesis/ 51 | 52 | # Translations 53 | *.mo 54 | *.pot 55 | 56 | # Django stuff: 57 | *.log 58 | local_settings.py 59 | 60 | # Flask stuff: 61 | instance/ 62 | .webassets-cache 63 | 64 | # Scrapy stuff: 65 | .scrapy 66 | 67 | # Sphinx documentation 68 | docs/_build/ 69 | 70 | # PyBuilder 71 | target/ 72 | 73 | # Jupyter Notebook 74 | .ipynb_checkpoints 75 | 76 | # pyenv 77 | .python-version 78 | 79 | # celery beat schedule file 80 | celerybeat-schedule 81 | 82 | # SageMath parsed files 83 | *.sage.py 84 | 85 | # dotenv 86 | .env 87 | 88 | # virtualenv 89 | .venv 90 | venv/ 91 | ENV/ 92 | 93 | # Spyder project settings 94 | .spyderproject 95 | .spyproject 96 | 97 | # Rope project settings 98 | .ropeproject 99 | 100 | # mkdocs documentation 101 | /site 102 | 103 | # mypy 104 | .mypy_cache/ 105 | .idea/ 106 | .idea/*.xml -------------------------------------------------------------------------------- /docs/AHLogo.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/RadarBook/software/971a6407379fc0dc9fe8f37b118a6fd1e7d59d2d/docs/AHLogo.png -------------------------------------------------------------------------------- /docs/README.md: -------------------------------------------------------------------------------- 1 | # Ordering Information 2 | 3 | ## Artech House Publisher 4 | ISBN: 9781630815974 5 | 6 | Copyright: 2019 7 | 8 | [Order Now](https://us.artechhouse.com/Introduction-to-Radar-Using-Python-and-MATLAB-P2051.aspx) 9 | 10 | ![Book_logo](book_cover_small.png)       ![AH Logo](AHLogo.png) 11 | 12 | ## Python® 13 | 14 | The Python tools were developed with version 3.6.4 and the GUIs were developed with Qt 5.10.0. The tool suite makes use of packages including SciPy, NumPy and Matplotlib. To install Python and the necessary packages, begin by navigating to [Python](http://python.org) and downloading the installer for the operating system of choice. Launch the Python installer and follow the onscreen instructions. Once the installation iscomplete, ensure the following packages are installed by typing the following commands at the command prompt: 15 | 16 | ```markdown 17 | > pip install numpy 18 | > pip install scipy 19 | > pip install matplotlib 20 | > pip install pyqt5 21 | > pip install -e mypath/pyradar 22 | ``` 23 | Where **mypath** is the path to the folder 'pyradar'. 24 | 25 | ## MATLAB® 26 | 27 | The MATLAB scripts associated with this text were developed with R2018a and do not require any additional toolboxes. The folder structure for the MATLAB and Python scripts is identical. In order to run the MATLAB scripts provided with this text, the library folder and subfolders must be added to the MATLAB path. Once these folders have been added, the MATLAB scripts may be executed from the editor or from the command window by typing the name of the script. For more information on MATLAB visit [MathWorks®](https://www.mathworks.com/). 28 | 29 | ## DATA 30 | Data for experiments are hosted by AFRL's Sendor Data Management System. See [https://www.sdms.afrl.af.mil/index.php](https://www.sdms.afrl.af.mil/index.php) for access. 31 | -------------------------------------------------------------------------------- /docs/_config.yml: -------------------------------------------------------------------------------- 1 | title: Introduction to Radar Using Python and MATLAB 2 | description: by Andy Harrison 3 | theme: jekyll-theme-cayman 4 | -------------------------------------------------------------------------------- /docs/book_cover.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/RadarBook/software/971a6407379fc0dc9fe8f37b118a6fd1e7d59d2d/docs/book_cover.jpg -------------------------------------------------------------------------------- /docs/book_cover_small.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/RadarBook/software/971a6407379fc0dc9fe8f37b118a6fd1e7d59d2d/docs/book_cover_small.png -------------------------------------------------------------------------------- /jupyter/Chapter02/lib_path.py: -------------------------------------------------------------------------------- 1 | import sys 2 | import os 3 | 4 | module_path = os.path.abspath(os.path.join(os.pardir, os.pardir)) 5 | if module_path not in sys.path: 6 | sys.path.append(module_path) 7 | -------------------------------------------------------------------------------- /jupyter/Chapter03/lib_path.py: -------------------------------------------------------------------------------- 1 | import sys 2 | import os 3 | 4 | module_path = os.path.abspath(os.path.join(os.pardir, os.pardir)) 5 | if module_path not in sys.path: 6 | sys.path.append(module_path) -------------------------------------------------------------------------------- /jupyter/Chapter04/lib_path.py: -------------------------------------------------------------------------------- 1 | import sys 2 | import os 3 | 4 | module_path = os.path.abspath(os.path.join(os.pardir, os.pardir)) 5 | if module_path not in sys.path: 6 | sys.path.append(module_path) -------------------------------------------------------------------------------- /jupyter/Chapter05/lib_path.py: -------------------------------------------------------------------------------- 1 | import sys 2 | import os 3 | 4 | module_path = os.path.abspath(os.path.join(os.pardir, os.pardir)) 5 | if module_path not in sys.path: 6 | sys.path.append(module_path) -------------------------------------------------------------------------------- /jupyter/Chapter06/lib_path.py: -------------------------------------------------------------------------------- 1 | import sys 2 | import os 3 | 4 | module_path = os.path.abspath(os.path.join(os.pardir, os.pardir)) 5 | if module_path not in sys.path: 6 | sys.path.append(module_path) -------------------------------------------------------------------------------- /jupyter/Chapter07/lib_path.py: -------------------------------------------------------------------------------- 1 | import sys 2 | import os 3 | 4 | module_path = os.path.abspath(os.path.join(os.pardir, os.pardir)) 5 | if module_path not in sys.path: 6 | sys.path.append(module_path) -------------------------------------------------------------------------------- /jupyter/Chapter08/lib_path.py: -------------------------------------------------------------------------------- 1 | import sys 2 | import os 3 | 4 | module_path = os.path.abspath(os.path.join(os.pardir, os.pardir)) 5 | if module_path not in sys.path: 6 | sys.path.append(module_path) -------------------------------------------------------------------------------- /jupyter/Chapter09/lib_path.py: -------------------------------------------------------------------------------- 1 | import sys 2 | import os 3 | 4 | module_path = os.path.abspath(os.path.join(os.pardir, os.pardir)) 5 | if module_path not in sys.path: 6 | sys.path.append(module_path) -------------------------------------------------------------------------------- /jupyter/Chapter10/lib_path.py: -------------------------------------------------------------------------------- 1 | import sys 2 | import os 3 | 4 | module_path = os.path.abspath(os.path.join(os.pardir, os.pardir)) 5 | if module_path not in sys.path: 6 | sys.path.append(module_path) -------------------------------------------------------------------------------- /jupyter/Chapter11/lib_path.py: -------------------------------------------------------------------------------- 1 | import sys 2 | import os 3 | 4 | module_path = os.path.abspath(os.path.join(os.pardir, os.pardir)) 5 | if module_path not in sys.path: 6 | sys.path.append(module_path) -------------------------------------------------------------------------------- /mlradar/Chapter01/initial_test.m: -------------------------------------------------------------------------------- 1 | %% Initial repo test 2 | % Created by: Lee A. Harrison 3 | % On: 6/18/2018 4 | % 5 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 6 | % This file is part of Introduction to Radar Using Python and MATLAB 7 | % and can not be copied and/or distributed without the express permission of Artech House. 8 | 9 | clear, clc -------------------------------------------------------------------------------- /mlradar/Chapter02/apparent_elevation_example.m: -------------------------------------------------------------------------------- 1 | %% Apparent elevation example 2 | % Created by: Lee A. Harrison 3 | % On: 6/18/2018 4 | % 5 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 6 | % This file is part of Introduction to Radar Using Python and MATLAB 7 | % and can not be copied and/or distributed without the express permission of Artech House. 8 | 9 | clear, clc 10 | 11 | % True elevation angle (degrees) 12 | theta_true = 20; 13 | 14 | % Target height (km) 15 | height = linspace(0, 5, 100); 16 | 17 | % Preallocate the arrays 18 | theta_apparent = zeros(1, numel(height)); 19 | theta_apparent_approximate = zeros(1, numel(height)); 20 | 21 | % Get the apparent elevation angle 22 | for iHeight = 1:numel(height) 23 | theta_apparent(iHeight) = apparent_elevation(theta_true, height(iHeight)); 24 | theta_apparent_approximate(iHeight) = apparent_elevation_approximate(theta_true, height(iHeight)); 25 | end 26 | 27 | % Plot the results from the integration 28 | figure; 29 | plot(height, theta_apparent, 'b'); 30 | title('Apparent Elevation due to Refraction'); 31 | xlabel('Height (km)'); 32 | ylabel('Apparent Elevation Angle (degrees)'); 33 | grid on; plot_settings; 34 | 35 | % Plot the results from the approximate method 36 | figure; 37 | plot(height, theta_apparent_approximate, 'g'); 38 | title('Apparent Elevation due to Refraction (Approximate)'); 39 | xlabel('Height (km)'); 40 | ylabel('Apparent Elevation Angle (degrees)'); 41 | grid on; plot_settings; -------------------------------------------------------------------------------- /mlradar/Chapter02/apparent_range_example.m: -------------------------------------------------------------------------------- 1 | %% Apparent range example 2 | % Created by: Lee A. Harrison 3 | % On: 6/18/2018 4 | % 5 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 6 | % This file is part of Introduction to Radar Using Python and MATLAB 7 | % and can not be copied and/or distributed without the express permission of Artech House. 8 | 9 | clear, clc 10 | 11 | % Radar LLA coordinates 12 | radar_lla = [34.0, 84.0, 120.0]; 13 | 14 | % Target LLA coordinates 15 | target_lla = [34.0, 80.0, 12000.0]; 16 | 17 | % Apparent range 18 | range = apparent_range(radar_lla, target_lla); 19 | 20 | % Display the true and apparent ranges 21 | display(sprintf('True range = %.2f (km) \nApparent range = %.2f (km)', range.true/1e3, range.apparent/1e3)); -------------------------------------------------------------------------------- /mlradar/Chapter02/atmosphere_example.m: -------------------------------------------------------------------------------- 1 | %% Atmospheric attenuation example 2 | % Created by: Lee A. Harrison 3 | % On: 6/18/2018 4 | % 5 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 6 | % This file is part of Introduction to Radar Using Python and MATLAB 7 | % and can not be copied and/or distributed without the express permission of Artech House. 8 | 9 | clear, clc 10 | 11 | % Operating frequency (GHz) 12 | frequency = linspace(0, 1e3, 1024); 13 | 14 | % System temperature (K) 15 | temperature = 290; 16 | 17 | % Dry air pressure (hPa) 18 | dry_air_pressure = 1013.25; 19 | 20 | % Water vapor density (g/m^3) 21 | water_vapor_density = 7.5; 22 | 23 | % Get the atmospheric attenuation 24 | attenuation = atmospheric_attenuation(frequency, temperature, dry_air_pressure, water_vapor_density); 25 | 26 | % Plot the results 27 | figure; 28 | semilogy(frequency, attenuation, 'b'); 29 | title('Atmospheric Attenuation'); 30 | xlabel('Frequency (GHz)'); 31 | ylabel('Specific Attenuation (dB/km)'); 32 | grid on; plot_settings; -------------------------------------------------------------------------------- /mlradar/Chapter02/beam_spreading_example.m: -------------------------------------------------------------------------------- 1 | %% Beam spreading example 2 | % Created by: Lee A. Harrison 3 | % On: 6/18/2018 4 | % 5 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 6 | % This file is part of Introduction to Radar Using Python and MATLAB 7 | % and can not be copied and/or distributed without the express permission of Artech House. 8 | 9 | clear, clc 10 | 11 | % Elevation angle (degrees) 12 | elevation_angle = 5; 13 | 14 | % Target height (km) 15 | height = 5; 16 | 17 | % Set up the elevation and height arrays 18 | [theta, height] = meshgrid(linspace(0.0, elevation_angle, 200), linspace(0.0, height, 200)); 19 | 20 | % Calculate the beam spreading loss 21 | b = 1. - (0.5411 + 0.07446 * theta + (0.06272 + 0.0276 * theta) .* height + 0.008288 .* height .^ 2) ./ ... 22 | (1.728 + 0.5411 .* theta + (0.1815 + 0.06272 .* theta + 0.0138 .* theta .^ 2) .* height + ... 23 | (0.01727 + 0.008288 .* theta) .* height .^ 2) .^ 2; 24 | 25 | beam_spreading_loss = -db(b); 26 | 27 | % Plot the results as a color plot 28 | figure; 29 | pcolor(theta, height, beam_spreading_loss); shading flat; 30 | title('Beam Spreading Loss') 31 | xlabel('Elevation Angle (degrees)') 32 | ylabel('Height (km)'); 33 | colormap('jet'); colorbar; plot_settings; -------------------------------------------------------------------------------- /mlradar/Chapter02/cloud_fog_example.m: -------------------------------------------------------------------------------- 1 | %% Cloud and fog attenuation example 2 | % Created by: Lee A. Harrison 3 | % On: 6/18/2018 4 | % 5 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 6 | % This file is part of Introduction to Radar Using Python and MATLAB 7 | % and can not be copied and/or distributed without the express permission of Artech House. 8 | 9 | clear, clc 10 | 11 | % Operating frequency (GHz) 12 | frequency = linspace(1.0, 200, 256); 13 | 14 | % Cloud/fog temperature (k) 15 | liquid_water_temperature = 290; 16 | 17 | % Cloud/fog density (g/m^3) 18 | liquid_water_density = 0.5; 19 | 20 | % Calculate the attenuation 21 | attenuation = cloud_fog_attenuation(frequency, liquid_water_temperature, liquid_water_density); 22 | 23 | % Plot the results 24 | figure; 25 | loglog(frequency, attenuation); 26 | title('Cloud or Fog Attenuation'); 27 | xlabel('Frequency (GHz)'); 28 | ylabel('Specific Attenuation (dB/km)') 29 | grid on; plot_settings; -------------------------------------------------------------------------------- /mlradar/Chapter02/diffraction_example.m: -------------------------------------------------------------------------------- 1 | %% Diffraction loss example 2 | % Created by: Lee A. Harrison 3 | % On: 6/18/2018 4 | % 5 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 6 | % This file is part of Introduction to Radar Using Python and MATLAB 7 | % and can not be copied and/or distributed without the express permission of Artech House. 8 | 9 | clear, clc 10 | 11 | % Operating frequency (Hz) 12 | frequency = linspace(1e6, 300e6, 500); 13 | 14 | % Relative permittivity 15 | relative_permittivity = 1.3; 16 | 17 | % Conductivity (S/m) 18 | conductivity = 0.01; 19 | 20 | % Radar LLA (deg, deg, m) 21 | radar.lat = 26.5; 22 | radar.lon = 97.0; 23 | radar.alt = 1000.0; 24 | 25 | % Target LLA (deg, deg, m) 26 | target.lat = 31.0; 27 | target.lon = 96.0; 28 | target.alt = 13000.0; 29 | 30 | % Calculate the diffraction loss 31 | diffraction_loss = diffraction_attenuation(radar, target, frequency, relative_permittivity, conductivity); 32 | 33 | % Plot the results 34 | figure; 35 | plot(frequency, diffraction_loss); 36 | title('Diffraction Loss') 37 | xlabel('Frequency (Hz)') 38 | ylabel('Diffraction Loss (dB)') 39 | grid on; plot_settings; -------------------------------------------------------------------------------- /mlradar/Chapter02/ducting_example.m: -------------------------------------------------------------------------------- 1 | %% Ducting example 2 | % Created by: Lee A. Harrison 3 | % On: 6/18/2018 4 | % 5 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 6 | % This file is part of Introduction to Radar Using Python and MATLAB 7 | % and can not be copied and/or distributed without the express permission of Artech House. 8 | 9 | clear, clc 10 | 11 | % Refractivity gradient (N/km) 12 | refractivity_gradient = linspace(-500, -150, 1000); 13 | 14 | % Duct thickness (m) 15 | duct_thickness = [10, 20, 50]; 16 | 17 | % Calculate the critical angle 18 | critical_angle = ducting(refractivity_gradient, duct_thickness); 19 | 20 | % Plot the results 21 | figure; hold on; 22 | legend_text = []; 23 | for iDuct= 1:numel(duct_thickness) 24 | plot(refractivity_gradient, critical_angle(iDuct,:)); 25 | legend_text = [legend_text; sprintf('Thickness %.1f (m)', duct_thickness(iDuct))]; 26 | end 27 | 28 | title('Ducting over a Spherical Earth'); 29 | xlabel('Refractivity Gradient (N/km)'); 30 | ylabel('Critical Angle (mrad)'); 31 | legend(legend_text); 32 | grid on; plot_settings; -------------------------------------------------------------------------------- /mlradar/Chapter02/rain_attenuation_example.m: -------------------------------------------------------------------------------- 1 | %% Rain attenuation example 2 | % Created by: Lee A. Harrison 3 | % On: 6/18/2018 4 | % 5 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 6 | % This file is part of Introduction to Radar Using Python and MATLAB 7 | % and can not be copied and/or distributed without the express permission of Artech House. 8 | 9 | clear, clc 10 | 11 | % Operating frequency (GHz) 12 | frequency = linspace(1.0, 1000); 13 | 14 | % Rain rate (mm/hr) 15 | rain_rate = 5.0; 16 | 17 | % Elevation angle (deg) 18 | elevation_angle = 10.0; 19 | 20 | % Polarization tilt angle (deg) 21 | polarization_tilt_angle = 0; 22 | 23 | % Calculate the rain attenuation 24 | attenuation = rain_attenuation(frequency, rain_rate, elevation_angle, polarization_tilt_angle); 25 | 26 | % Plot the results 27 | figure; 28 | plot(frequency, attenuation); 29 | title('Rain Attenuation'); 30 | xlabel('Frequency (GHz)'); 31 | ylabel('Specific Attenuation (dB/km)'); 32 | grid on; plot_settings; -------------------------------------------------------------------------------- /mlradar/Chapter02/vegetation_attenuation_example.m: -------------------------------------------------------------------------------- 1 | %% Vegetation attenuation example 2 | % Created by: Lee A. Harrison 3 | % On: 6/18/2018 4 | % 5 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 6 | % This file is part of Introduction to Radar Using Python and MATLAB 7 | % and can not be copied and/or distributed without the express permission of Artech House. 8 | 9 | % Specific attenuation (dB/m) 10 | specific_attenuation = 0.39; 11 | 12 | % Maximum attenuation (dB) 13 | maximum_attenuation = 34.10; 14 | 15 | % Distance (m) 16 | distance = linspace(0, 100.0); 17 | 18 | % Calculate the attenuation due to vegetation 19 | attenuation = maximum_attenuation * (1. - exp(-distance * specific_attenuation / maximum_attenuation)); 20 | 21 | % Plot the results 22 | figure; 23 | semilogy(distance, attenuation); 24 | title('Vegetation Attenuation'); 25 | xlabel('Distance (m)'); 26 | ylabel('Attenuation (dB)'); 27 | grid on; plot_settings; -------------------------------------------------------------------------------- /mlradar/Chapter03/circular_array_example.m: -------------------------------------------------------------------------------- 1 | %% Circular array example 2 | % Created by: Lee A. Harrison 3 | % On: 8/3/2018 4 | % 5 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 6 | % This file is part of Introduction to Radar Using Python and MATLAB 7 | % and can not be copied and/or distributed without the express permission of Artech House. 8 | 9 | clear, clc 10 | 11 | % Number of elements in the array 12 | number_of_elements = 21; 13 | 14 | % Radius of the array (m) 15 | radius = 0.5; 16 | 17 | % Operating frequency (Hz) 18 | frequency = 300.0e6; 19 | 20 | % Scan angles (rad) 21 | scan_angle_theta = 0.0; 22 | scan_angle_phi = 0.0; 23 | 24 | % Set the theta and phi grid 25 | n = 360; 26 | m = floor(n/4); 27 | [theta, phi] = meshgrid(linspace(0.0, 0.5 * pi, n), linspace(0.0, 2.0 * pi, n)); 28 | 29 | % New instance of circular_array 30 | ca = circular_array(number_of_elements, radius, frequency, scan_angle_theta, scan_angle_phi, theta, phi); 31 | 32 | % Get the array factor 33 | af = ca.array_factor; 34 | 35 | % U-V coordinates for plotting the antenna pattern 36 | uu = sin(theta) .* cos(phi); 37 | vv = sin(theta) .* sin(phi); 38 | 39 | % Plot the array factor 40 | figure; 41 | pcolor(uu, vv, abs(af)); shading flat 42 | xlabel('U (sines)'); 43 | ylabel('V (sines)'); 44 | title('Circular Array Antenna Pattern'); 45 | axis equal 46 | plot_settings; 47 | 48 | 49 | figure; 50 | plot(theta(1,:)*180/pi, 2*db(abs(af(m,:)))); hold on; 51 | plot(theta(1,:)*180/pi, 2*db(abs(af(1,:)))); 52 | ylim([-60 5]); 53 | title('Circular Array Antenna Pattern'); 54 | xlabel('Theta (deg)'); 55 | ylabel('Normalized |E| (dB)'); 56 | legend('E-plane', 'H-plane'); 57 | grid on; plot_settings; -------------------------------------------------------------------------------- /mlradar/Chapter03/linear_array_example.m: -------------------------------------------------------------------------------- 1 | %% Linear array example 2 | % Created by: Lee A. Harrison 3 | % On: 8/3/2018 4 | % 5 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 6 | % This file is part of Introduction to Radar Using Python and MATLAB 7 | % and can not be copied and/or distributed without the express permission of Artech House. 8 | 9 | clear, clc 10 | 11 | % Number of elements in the array 12 | number_of_elements = 21; 13 | 14 | % Element spacing 15 | element_spacing = 0.5; 16 | 17 | % Operating frequency (Hz) 18 | frequency = 300e6; 19 | 20 | % Scan angles (rad) 21 | scan_angle = 0.5 * pi; 22 | 23 | % Set the theta array 24 | theta = linspace(eps, pi, 1000); 25 | 26 | % Sidelobe level for Tschebyscheff coefficients 27 | side_lobe_level = 30.0; 28 | 29 | % Window type for the array 30 | window_type = 'Uniform'; 31 | % window_type = 'Binomial'; 32 | % window_type = 'Tschebyscheff'; 33 | % window_type = 'Hanning'; 34 | % window_type = 'Hamming'; 35 | 36 | % New instance of linear_array 37 | la = linear_array(number_of_elements, scan_angle, element_spacing,... 38 | frequency, theta, window_type, side_lobe_level); 39 | 40 | % Get the array factor 41 | af = la.array_factor; 42 | 43 | % Plot the array factor 44 | figure; 45 | plot(theta*180/pi, 2*db(abs(af))); 46 | ylim([-60 5]); 47 | title('Linear Array Antenna Pattern'); 48 | xlabel('Theta (deg)'); 49 | ylabel('Normalized |E| (dB)'); 50 | grid on; plot_settings; -------------------------------------------------------------------------------- /mlradar/Chapter03/loop_example.m: -------------------------------------------------------------------------------- 1 | %% Loop example 2 | % Created by: Lee A. Harrison 3 | % On: 8/5/2018 4 | % 5 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 6 | % This file is part of Introduction to Radar Using Python and MATLAB 7 | % and can not be copied and/or distributed without the express permission of Artech House. 8 | 9 | clear, clc 10 | 11 | % The operating frequency (Hz) 12 | frequency = 1.0e9; 13 | 14 | % The current on the loop (A) 15 | current = 1.0; 16 | 17 | % The radius of the loop (m) 18 | radius = 0.1; 19 | 20 | % Angluar span for the pattern (rad) 21 | theta = linspace(0.0, 2.0 * pi, 1000); 22 | 23 | % A new instance of loop antenna 24 | %loop = small_loop(radius, current, frequency, 1e6, theta); 25 | loop = circular_loop(radius, current, frequency, 1e6, theta); 26 | 27 | % Calculate the directivity 28 | d = loop.directivity; 29 | fprintf('Directivity = %.2f\n', d); 30 | 31 | % Calculate the beamwidth 32 | b = loop.beamwidth; 33 | fprintf('Beamwidth = %.2f (deg)\n', b); 34 | 35 | % Calculate the maximum effective aperture 36 | ae = loop.maximum_effective_aperture; 37 | fprintf('Maximum Effective Aperture = %.2e (m^2)\n', ae); 38 | 39 | % Calculate the radiation resistance 40 | rr = loop.radiation_resistance; 41 | fprintf('Radiation Resistance = %.2f (Ohms)\n', rr); 42 | 43 | % Calculate the radiated power 44 | prad = loop.radiated_power; 45 | fprintf('Total Power Radiated = %.2f (W)\n', prad); 46 | 47 | % Calculate the far fields 48 | [e_r, e_theta, e_phi, h_r, h_theta, h_phi] = loop.far_field; 49 | 50 | % Calculate the normalized magnitude of the electric field 51 | e_mag = sqrt(abs(e_phi .* e_phi)); 52 | e_mag = e_mag ./ max(max(e_mag)); 53 | 54 | % Plot the results 55 | figure; 56 | polar(theta, (e_mag)); 57 | % polarplot(theta, (e_mag)); 58 | title('Loop Antenna Pattern'); 59 | grid on; plot_settings; -------------------------------------------------------------------------------- /mlradar/Chapter03/planar_array_example.m: -------------------------------------------------------------------------------- 1 | %% Planar array example 2 | % Created by: Lee A. Harrison 3 | % On: 8/3/2018 4 | % 5 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 6 | % This file is part of Introduction to Radar Using Python and MATLAB 7 | % and can not be copied and/or distributed without the express permission of Artech House. 8 | 9 | clear, clc 10 | 11 | % Number of elements in the array 12 | number_of_elements_x = 21; 13 | number_of_elements_y = 21; 14 | 15 | % Element spacing 16 | element_spacing_x = 0.5; 17 | element_spacing_y = 0.25; 18 | 19 | % Operating frequency (Hz) 20 | frequency = 300.0e6; 21 | 22 | % Scan angles (rad) 23 | scan_angle_theta = 0.0; 24 | scan_angle_phi = 0.0; 25 | 26 | % Set the theta and phi grid 27 | n = 400; 28 | m = floor(n/4); 29 | [theta, phi] = meshgrid(linspace(eps, 0.5 * pi, n), linspace(eps, 2.0 * pi, n)); 30 | 31 | % New instance of planar_array 32 | pa = planar_array(number_of_elements_x, number_of_elements_y, element_spacing_x, element_spacing_y, ... 33 | frequency, scan_angle_theta, scan_angle_phi, theta, phi); 34 | 35 | % Get the array factor 36 | af = pa.array_factor; 37 | 38 | % U-V coordinates for plotting the antenna pattern 39 | uu = sin(theta) .* cos(phi); 40 | vv = sin(theta) .* sin(phi); 41 | 42 | % Plot the array factor 43 | figure; 44 | pcolor(uu, vv, abs(af)); shading flat 45 | xlabel('U (sines)'); 46 | ylabel('V (sines)'); 47 | title('Planar Array Antenna Pattern'); 48 | axis equal 49 | plot_settings; 50 | 51 | 52 | figure; 53 | plot(theta(1,:)*180/pi, 2*db(abs(af(m,:)))); hold on; 54 | plot(theta(1,:)*180/pi, 2*db(abs(af(1,:)))); 55 | ylim([-60 5]); 56 | title('Planar Array Antenna Pattern'); 57 | xlabel('Theta (deg)'); 58 | ylabel('Normalized |E| (dB)'); 59 | legend('E-plane', 'H-plane'); 60 | grid on; plot_settings; -------------------------------------------------------------------------------- /mlradar/Chapter04/loop_gain_example.m: -------------------------------------------------------------------------------- 1 | %% Loop gain example 2 | % Created by: Lee A. Harrison 3 | % On: 7/1/2018 4 | % 5 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 6 | % This file is part of Introduction to Radar Using Python and MATLAB 7 | % and can not be copied and/or distributed without the express permission of Artech House. 8 | 9 | clear, clc 10 | 11 | % Reference range (m) 12 | reference_range = 100e3; 13 | 14 | % Reference radar cross section (dBsm) 15 | reference_rcs = 10; 16 | 17 | % Reference signal to noise ratio (dB) 18 | reference_snr = 20.0; 19 | 20 | % Calculate the loop gain 21 | lg = loop_gain(reference_range, 10^(reference_rcs/10), 10^(reference_snr/10)); 22 | 23 | % Display the result 24 | fprintf('Loop gain = %.2f (dB)\n', db(lg)); -------------------------------------------------------------------------------- /mlradar/Chapter04/maximum_detection_range_example.m: -------------------------------------------------------------------------------- 1 | %% Maximum detection range example 2 | % Created by: Lee A. Harrison 3 | % On: 7/1/2018 4 | % 5 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 6 | % This file is part of Introduction to Radar Using Python and MATLAB 7 | % and can not be copied and/or distributed without the express permission of Artech House. 8 | 9 | clear, clc 10 | 11 | % System temperature (K) 12 | system_temperature = 290; 13 | 14 | % Receiver bandwidth (Hz) 15 | bandwidth = 10e6; 16 | 17 | % Noise figure (dB) 18 | noise_figure = 6; 19 | 20 | % System losses (dB) 21 | losses = 4; 22 | 23 | % Signal to noise ratio (dB) 24 | signal_to_noise = linspace(5, 25, 1000); 25 | 26 | % Peak transmit power (W) 27 | peak_power = 50e3; 28 | 29 | % Antenna gain (dB) 30 | antenna_gain = 20; 31 | 32 | % Operating frequency (Hz) 33 | frequency = 1e9; 34 | 35 | % Target radar cross section (dBsm) 36 | target_rcs = 10; 37 | 38 | % Calculate the maximum detection range (m) 39 | r_max = maximum_range(system_temperature, bandwidth, lin(noise_figure), lin(losses), ... 40 | lin(signal_to_noise), peak_power, lin(antenna_gain), frequency, lin(target_rcs)); 41 | 42 | % Plot the result 43 | figure; 44 | plot(signal_to_noise, r_max/1e3); 45 | title('Maximum Detection Range'); 46 | xlabel('Signal to Noise Ratio (dB)'); 47 | ylabel('Detection Range (km)'); 48 | grid on; 49 | plot_settings; 50 | -------------------------------------------------------------------------------- /mlradar/Chapter04/minimum_detectable_signal_example.m: -------------------------------------------------------------------------------- 1 | %% Minimum detectable signal example 2 | % Created by: Lee A. Harrison 3 | % On: 7/1/2018 4 | % 5 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 6 | % This file is part of Introduction to Radar Using Python and MATLAB 7 | % and can not be copied and/or distributed without the express permission of Artech House. 8 | 9 | clear, clc 10 | 11 | % System temperature (K) 12 | system_temperature = 290; 13 | 14 | % Receiver bandwidth (Hz) 15 | bandwidth = 10e6; 16 | 17 | % Noise figure (dB) 18 | noise_figure = 6; 19 | 20 | % System losses (dB) 21 | losses = 4; 22 | 23 | % Signal to noise ration (dB) 24 | signal_to_noise = 20; 25 | 26 | % Calculate the minimum detectable signal (W) 27 | p_min = minimum_detectable_signal(system_temperature, bandwidth, lin(noise_figure), lin(losses), lin(signal_to_noise)); 28 | 29 | % Display the result 30 | fprintf('Minimum detectable signal = %.2e (W)\n', p_min); -------------------------------------------------------------------------------- /mlradar/Chapter04/ouput_signal_to_noise_bistatic_example.m: -------------------------------------------------------------------------------- 1 | %% Output signal to noise bistatic example 2 | % Created by: Lee A. Harrison 3 | % On: 7/1/2018 4 | % 5 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 6 | % This file is part of Introduction to Radar Using Python and MATLAB 7 | % and can not be copied and/or distributed without the express permission of Artech House. 8 | 9 | clear, clc 10 | 11 | % Peak transmit power 12 | peak_power = 50e3; 13 | 14 | % Transmit antenna gain (dB) 15 | transmit_antenna_gain = 20; 16 | 17 | % Receive antenna gain (dB) 18 | receive_antenna_gain = 10; 19 | 20 | % Transmitter to target range (m) 21 | transmit_target_range = 1.0; 22 | 23 | % Receiver to target range (m) 24 | receive_target_range = linspace(1e3, 100e3, 1e3); 25 | 26 | % Operating frequency (Hz) 27 | frequency = 1.0e9; 28 | 29 | % Bistatic target radar cross section (dBsm) 30 | bistatic_target_rcs = 10; 31 | 32 | % System temperature (K) 33 | system_temperature = 290; 34 | 35 | % Receiver bandwidth (Hz) 36 | bandwidth = 10e6; 37 | 38 | % Noise figure (dB) 39 | noise_figure = 6; 40 | 41 | % Transmit losses (dB) 42 | transmit_losses = 4; 43 | 44 | % Receive losses (dB) 45 | receive_losses = 2; 46 | 47 | % Calculate the output signal to noise ratio 48 | snr = output_snr_bistatic(peak_power, lin(transmit_antenna_gain), lin(receive_antenna_gain), transmit_target_range, receive_target_range,... 49 | frequency, lin(bistatic_target_rcs), system_temperature, bandwidth, lin(noise_figure), lin(transmit_losses), lin(receive_losses)); 50 | 51 | % Plot the result 52 | figure; 53 | plot(transmit_target_range*receive_target_range/1e6, db(snr)); 54 | title('Bistatic Radar Range Equation'); 55 | xlabel('Range Product (km^{2})'); 56 | ylabel('Output Signal to Noise Ratio (dB)'); 57 | grid on; 58 | plot_settings; -------------------------------------------------------------------------------- /mlradar/Chapter04/output_signal_to_noise_example.m: -------------------------------------------------------------------------------- 1 | %% Output signal to noise example 2 | % Created by: Lee A. Harrison 3 | % On: 7/1/2018 4 | % 5 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 6 | % This file is part of Introduction to Radar Using Python and MATLAB 7 | % and can not be copied and/or distributed without the express permission of Artech House. 8 | 9 | clear, clc 10 | 11 | % Peak transmit power (W) 12 | peak_power = 50e3; 13 | 14 | % Antenna gain (dB) 15 | antenna_gain = 20; 16 | 17 | % Target range (m) 18 | target_range = linspace(1e3, 100e3, 1e3); 19 | 20 | % Operating frequency (Hz) 21 | frequency = 1.0e9; 22 | 23 | % Target radar cross section (dBsm) 24 | target_rcs = 10; 25 | 26 | % System temperature (K) 27 | system_temperature = 290; 28 | 29 | % Receiver bandwidth (Hz) 30 | bandwidth = 10e6; 31 | 32 | % Noise figure (dB) 33 | noise_figure = 6; 34 | 35 | % Losses (dB) 36 | losses = 4; 37 | 38 | % Calculate the output signal to noise ratio 39 | snr = output_snr(system_temperature, bandwidth, lin(noise_figure), lin(losses), ... 40 | peak_power, lin(antenna_gain), frequency, lin(target_rcs), target_range); 41 | 42 | % Plot the result 43 | figure; 44 | plot(target_range/1e3, db(snr)); 45 | title('Output Signal to Noise Ratio'); 46 | xlabel('Target Range (km)'); 47 | ylabel('Output Signal to Noise Ratio (dB)'); 48 | grid on; 49 | plot_settings; -------------------------------------------------------------------------------- /mlradar/Chapter04/output_signal_to_noise_search_example.m: -------------------------------------------------------------------------------- 1 | %% Output signal to noise search example 2 | % Created by: Lee A. Harrison 3 | % On: 7/2/2018 4 | % 5 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 6 | % This file is part of Introduction to Radar Using Python and MATLAB 7 | % and can not be copied and/or distributed without the express permission of Artech House. 8 | 9 | clear, clc 10 | 11 | % Power aperture (W m^2) 12 | power_aperture = 50e3; 13 | 14 | % Search volume (steradian) 15 | search_volume = 400; 16 | 17 | % Scan time (s) 18 | scan_time = 2; 19 | 20 | % Antenna gain (dB) 21 | antenna_gain = 20; 22 | 23 | % Target range (m) 24 | target_range = linspace(1e3, 100e3, 1e3); 25 | 26 | % Operating frequency (Hz) 27 | frequency = 1.0e9; 28 | 29 | % Target radar cross section (dBsm) 30 | target_rcs = 10; 31 | 32 | % System temperature (K) 33 | system_temperature = 290; 34 | 35 | % Receiver bandwidth (Hz) 36 | bandwidth = 10e6; 37 | 38 | % Noise figure (dB) 39 | noise_figure = 6; 40 | 41 | % Losses (dB) 42 | losses = 4; 43 | 44 | % Calculate the output signal to noise ratio 45 | snr = output_snr_search(power_aperture, system_temperature, lin(noise_figure), lin(losses),... 46 | target_range, search_volume, scan_time, lin(target_rcs)); 47 | 48 | % Plot the result 49 | figure; 50 | plot(target_range/1e3, db(snr)); 51 | title('Output Signal to Noise for Search'); 52 | xlabel('Target Range (km)'); 53 | ylabel('Output Signal to Noise Ratio (dB)'); 54 | grid on; 55 | plot_settings; -------------------------------------------------------------------------------- /mlradar/Chapter04/power_aperture_example.m: -------------------------------------------------------------------------------- 1 | %% Power aperture example 2 | % Created by: Lee A. Harrison 3 | % On: 7/2/2018 4 | % 5 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 6 | % This file is part of Introduction to Radar Using Python and MATLAB 7 | % and can not be copied and/or distributed without the express permission of Artech House. 8 | 9 | clear, clc 10 | 11 | % Target range (m) 12 | target_range = linspace(1e3, 100e3, 1000); 13 | 14 | % System temperature (K) 15 | system_temperature = 290; 16 | 17 | % Search volume (steradian) 18 | search_volume = 400; 19 | 20 | % Noise figure (dB) 21 | noise_figure = 6; 22 | 23 | % Losses (dB) 24 | losses = 4; 25 | 26 | % Signal to noise ratio (dB) 27 | signal_to_noise = 20; 28 | 29 | % Scan time (s) 30 | scan_time = 2; 31 | 32 | % Target radar cross section (dBsm) 33 | target_rcs = 10; 34 | 35 | % Calculate the power aperture 36 | pa = power_aperture(system_temperature, lin(noise_figure), lin(losses),... 37 | lin(signal_to_noise), target_range, search_volume, scan_time, lin(target_rcs)); 38 | 39 | % Plot the result 40 | figure; 41 | plot(target_range/1e3, db(pa)); 42 | title('Power Aperture Product'); 43 | xlabel('Target Range (km)'); 44 | ylabel('Power Aperture (dB)'); 45 | grid on; 46 | plot_settings; -------------------------------------------------------------------------------- /mlradar/Chapter04/power_at_radar_bistatic_example.m: -------------------------------------------------------------------------------- 1 | %% Power at radar bistatic example 2 | % Created by: Lee A. Harrison 3 | % On: 7/2/2018 4 | % 5 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 6 | % This file is part of Introduction to Radar Using Python and MATLAB 7 | % and can not be copied and/or distributed without the express permission of Artech House. 8 | 9 | clear, clc 10 | 11 | % Peak transmit power (W) 12 | peak_power = 50e3; 13 | 14 | % Transmit antenna gain (dB) 15 | transmit_antenna_gain = 20; 16 | 17 | % Receive antenna gain (dB) 18 | receive_antenna_gain = 10; 19 | 20 | % Transmit/Receive range product (m^2) 21 | range_product = linspace(1e3, 100e3, 1000); 22 | 23 | % Operating frequency (Hz) 24 | frequency = 1.0e9; 25 | 26 | % Bistatic target radar cross section (dBsm) 27 | bistatic_target_rcs = 10; 28 | 29 | % Calculate the power at the receiver (W) 30 | pr = power_at_radar_bistatic(peak_power, lin(transmit_antenna_gain),... 31 | lin(receive_antenna_gain), 1.0, range_product,... 32 | frequency, lin(bistatic_target_rcs)); 33 | 34 | % Plot the result 35 | figure; 36 | plot(range_product/1e6, pr); 37 | title('Bistatic Power at the Receiver'); 38 | xlabel('Range Product (km^{2})'); 39 | ylabel('Power at the Receiver (W)'); 40 | grid on; 41 | plot_settings; -------------------------------------------------------------------------------- /mlradar/Chapter04/power_at_radar_example.m: -------------------------------------------------------------------------------- 1 | %% Power at radar example 2 | % Created by: Lee A. Harrison 3 | % On: 7/2/2018 4 | % 5 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 6 | % This file is part of Introduction to Radar Using Python and MATLAB 7 | % and can not be copied and/or distributed without the express permission of Artech House. 8 | 9 | clear, clc 10 | 11 | % Peak transmit power (W) 12 | peak_power = 50e3; 13 | 14 | % Antenna gain (dB) 15 | antenna_gain = 20; 16 | 17 | % Target range (m) 18 | target_range = linspace(1e3, 5e3, 1000); 19 | 20 | % Operating frequency (Hz) 21 | frequency = 1e9; 22 | 23 | % Target radar cross section (dBsm) 24 | target_rcs = 10; 25 | 26 | % Calculate the power at the radar (W) 27 | pr = power_at_radar(peak_power, lin(antenna_gain), target_range, frequency, lin(target_rcs)); 28 | 29 | % Plot the result 30 | figure; 31 | plot(target_range/1e3, pr); 32 | title('Power at the Radar'); 33 | xlabel('Target Range (km)'); 34 | ylabel('Power at the Radar (W)'); 35 | grid on; 36 | plot_settings; -------------------------------------------------------------------------------- /mlradar/Chapter04/power_density_example.m: -------------------------------------------------------------------------------- 1 | %% Power density example 2 | % Created by: Lee A. Harrison 3 | % On: 7/2/2018 4 | % 5 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 6 | % This file is part of Introduction to Radar Using Python and MATLAB 7 | % and can not be copied and/or distributed without the express permission of Artech House. 8 | 9 | clear, clc 10 | 11 | % Peak transmit power (W) 12 | peak_power = 50e3; 13 | 14 | % Antenna gain (dB) 15 | antenna_gain = 20; 16 | 17 | % Target range (m) 18 | target_range = linspace(1e3, 5e3, 1000); 19 | 20 | % Calculate the power density (W/m^2) 21 | pd = power_density_radar(peak_power, lin(antenna_gain), target_range); 22 | 23 | % Plot the result 24 | figure; 25 | plot(target_range/1e3, pd); 26 | title('Incident Power Density'); 27 | xlabel('Target Range (km)'); 28 | ylabel('Power Density (W/m^{2})'); 29 | grid on; 30 | plot_settings; 31 | 32 | -------------------------------------------------------------------------------- /mlradar/Chapter05/adc_example.m: -------------------------------------------------------------------------------- 1 | %% ADC example 2 | % Created by: Lee A. Harrison 3 | % On: 9/19/2018 4 | % 5 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 6 | % This file is part of Introduction to Radar Using Python and MATLAB 7 | % and can not be copied and/or distributed without the express permission of Artech House. 8 | 9 | clear, clc 10 | 11 | % Set the parameters 12 | number_of_bits = 3; 13 | sampling_frequency = 100; 14 | start_frequency = 1.0; 15 | end_frequency = 4.0; 16 | am_amplitude = 0.1; 17 | am_frequency = 4.0; 18 | 19 | % Analog signal for plotting 20 | t = linspace(0.0, 1.0, 4196); 21 | a_signal = chirp(t, start_frequency, t(end), end_frequency); 22 | a_signal = a_signal .* (1.0 + am_amplitude * sin(2.0 * pi * am_frequency * t)); 23 | 24 | % Set up the waveform 25 | time = (0:sampling_frequency) / sampling_frequency; 26 | if_signal = chirp(time, start_frequency, time(end), end_frequency); 27 | if_signal = if_signal .* (1.0 + am_amplitude * sin(2.0 * pi * am_frequency * time)); 28 | 29 | % Calculate the envelope 30 | [quantized_signal, error_signal] = quantization(if_signal, number_of_bits); 31 | 32 | % Plot the results 33 | figure; 34 | subplot(2,1,1) 35 | plot(t, a_signal); hold on; 36 | plot(time, quantized_signal, 'r--'); 37 | ylabel('Amplitude (V)'); 38 | title('Analog to Digital Conversion'); 39 | grid on; 40 | legend('Analog Signal', 'Digital Signal') 41 | 42 | subplot(2,1,2) 43 | plot(time, error_signal); 44 | xlabel('Time (s)'); 45 | ylabel('Error (V)'); 46 | grid on; 47 | 48 | plot_settings; -------------------------------------------------------------------------------- /mlradar/Chapter05/coherent_detector_example.m: -------------------------------------------------------------------------------- 1 | %% Coherent detector example 2 | % Created by: Lee A. Harrison 3 | % On: 9/19/2018 4 | % 5 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 6 | % This file is part of Introduction to Radar Using Python and MATLAB 7 | % and can not be copied and/or distributed without the express permission of Artech House. 8 | 9 | clear, clc 10 | 11 | % Set the parameters 12 | sampling_frequency = 400; 13 | start_frequency = 20; 14 | end_frequency = 80; 15 | am_amplitude = 0.1; 16 | am_frequency = 4; 17 | 18 | % Calculate the bandwidth and center frequency 19 | bandwidth = end_frequency - start_frequency; 20 | center_frequency = 0.5 * bandwidth + start_frequency; 21 | 22 | % Set up the waveform 23 | time = (0:sampling_frequency-1) / sampling_frequency; 24 | if_signal = chirp(time, start_frequency, time(end), end_frequency); 25 | if_signal = if_signal .* (1.0 + am_amplitude * sin(2.0 * pi * am_frequency * time)); 26 | 27 | 28 | % Calculate the baseband I and Q 29 | [i_signal, q_signal] = coherent_detector(if_signal, center_frequency, bandwidth, sampling_frequency, time); 30 | 31 | % Plot the results 32 | figure; 33 | plot(time, i_signal); hold on; 34 | plot(time, q_signal, 'r--'); 35 | title('Coherent Detector'); 36 | xlabel('Time (s)'); 37 | ylabel('Amplitude (V)'); 38 | grid on; 39 | legend('In Phase', 'Quadrature'); 40 | 41 | plot_settings; -------------------------------------------------------------------------------- /mlradar/Chapter05/envelope_detector_example.m: -------------------------------------------------------------------------------- 1 | %% Envelope detector example 2 | % Created by: Lee A. Harrison 3 | % On: 9/19/2018 4 | % 5 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 6 | % This file is part of Introduction to Radar Using Python and MATLAB 7 | % and can not be copied and/or distributed without the express permission of Artech House. 8 | 9 | clear, clc 10 | 11 | % Set the parameters 12 | 13 | sampling_frequency = 400; 14 | start_frequency = 20; 15 | end_frequency = 80; 16 | am_amplitude = 0.1; 17 | am_frequency = 4; 18 | 19 | % Set up the waveform 20 | time = (0:sampling_frequency - 1) / sampling_frequency; 21 | if_signal = chirp(time, start_frequency, time(end), end_frequency); 22 | if_signal = if_signal .* (1.0 + am_amplitude * sin(2.0 * pi * am_frequency * time)); 23 | 24 | % Calculate the envelope 25 | envelope = envelope_detector(if_signal); 26 | 27 | % Plot the results 28 | figure; 29 | plot(time, if_signal); hold on; 30 | plot(time, envelope, 'r--'); 31 | 32 | title('Envelope Detector'); 33 | xlabel('Time (s)'); 34 | ylabel('Amplitude (V)'); 35 | 36 | grid on; 37 | 38 | legend('IF Signal', 'Envelope') 39 | 40 | plot_settings; -------------------------------------------------------------------------------- /mlradar/Chapter05/low_pass_filter_example.m: -------------------------------------------------------------------------------- 1 | %% Low pass filter example 2 | % Created by: Lee A. Harrison 3 | % On: 9/19/2018 4 | % 5 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 6 | % This file is part of Introduction to Radar Using Python and MATLAB 7 | % and can not be copied and/or distributed without the express permission of Artech House. 8 | 9 | clear, clc 10 | 11 | % Set the parameters 12 | filter_order = 4; 13 | critical_frequency = 100; 14 | maximum_ripple = 5.0; 15 | minimum_attenuation = 40.0; 16 | 17 | % Butterworth 18 | [zb, pb, kb] = butter(filter_order, 2.0 * pi * critical_frequency, 's'); 19 | [bb, ab] = zp2tf(zb, pb, kb); 20 | [hb, wb] = freqs(bb, ab, 4096); 21 | 22 | % Chebyshev Type I 23 | [z1, p1, k1] = cheby1(filter_order, maximum_ripple, 2.0 * pi * critical_frequency, 's'); 24 | [b1, a1] = zp2tf(z1, p1, k1); 25 | [h1, w1] = freqs(b1, a1, 4096); 26 | 27 | % Chebyshev Type II 28 | [z2, p2, k2] = cheby2(filter_order, minimum_attenuation, 2.0 * pi * critical_frequency, 's'); 29 | [b2, a2] = zp2tf(z2, p2, k2); 30 | [h2, w2] = freqs(b2, a2, 4096); 31 | 32 | % Elliptic filter 33 | [ze, pe, ke] = ellip(filter_order, maximum_ripple, minimum_attenuation, 2.0 * pi * critical_frequency, 's'); 34 | [be, ae] = zp2tf(ze, pe, ke); 35 | [he, we] = freqs(be, ae, 4096); 36 | 37 | % Plot the results 38 | plot(wb / (critical_frequency * pi), 20 * log10(abs(hb))); hold on 39 | plot(w1 / (critical_frequency * pi), 20 * log10(abs(h1))); 40 | plot(w2 / (critical_frequency * pi), 20 * log10(abs(h2))); 41 | plot(we / (critical_frequency * pi), 20 * log10(abs(he))); 42 | grid on; 43 | xlabel('Frequency (Hz)') 44 | ylabel('Attenuation (dB)') 45 | legend('Butterworth','Chebyshev I','Chebyshev II','Elliptic') -------------------------------------------------------------------------------- /mlradar/Chapter05/noise_figure_example.m: -------------------------------------------------------------------------------- 1 | %% Noise figure example 2 | % Created by: Lee A. Harrison 3 | % On: 9/19/2018 4 | % 5 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 6 | % This file is part of Introduction to Radar Using Python and MATLAB 7 | % and can not be copied and/or distributed without the express permission of Artech House. 8 | 9 | clear, clc 10 | 11 | % Set the parameters 12 | gain = [20, -0.5, -6, -1, 30]; 13 | noise_figure = [3.0, 0.5, 6, 1, 5]; 14 | 15 | % Calculate the total noise figure 16 | total_noise_figure = cascade_noise_figure(gain, noise_figure); 17 | 18 | % Display 19 | fprintf('Total noise figure = %.2f\n', total_noise_figure); -------------------------------------------------------------------------------- /mlradar/Chapter05/resolution_example.m: -------------------------------------------------------------------------------- 1 | %% Resolution example 2 | % Created by: Lee A. Harrison 3 | % On: 9/19/2018 4 | % 5 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 6 | % This file is part of Introduction to Radar Using Python and MATLAB 7 | % and can not be copied and/or distributed without the express permission of Artech House. 8 | 9 | clear, clc 10 | 11 | % Set the parameters 12 | number_of_bits = 12; 13 | signal_to_noise = 68.0; 14 | 15 | % Calculate the ideal signal to noise 16 | fprintf('Ideal SNR = %.2f (dB)\n', 6.02 * number_of_bits + 1.76); 17 | 18 | % Calculate the effective number of bits 19 | fprintf('Effective Number of Bits %d\n', round((signal_to_noise - 1.76) / 6.02)); 20 | -------------------------------------------------------------------------------- /mlradar/Chapter05/sensitivity_time_control_example.m: -------------------------------------------------------------------------------- 1 | %% Sensitivity time control example 2 | % Created by: Lee A. Harrison 3 | % On: 9/19/2018 4 | % 5 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 6 | % This file is part of Introduction to Radar Using Python and MATLAB 7 | % and can not be copied and/or distributed without the express permission of Artech House. 8 | 9 | clear, clc 10 | 11 | % Set the parameters 12 | pulse_repetition_frequency = 30e3; 13 | pulsewidth = 1.0e-6; 14 | 15 | % Calculate the attenuation and receive range 16 | [receive_range, atten] = sensitivity_time_control(pulse_repetition_frequency, pulsewidth); 17 | 18 | % Plot the results 19 | figure; 20 | plot(receive_range, 10.0 * log10(atten ./ max(atten))); 21 | title('Sensitivity Time Control'); 22 | xlabel('Range (m)'); 23 | ylabel('Normalized Attenuation (dB)'); 24 | grid on; 25 | plot_settings; -------------------------------------------------------------------------------- /mlradar/Chapter06/binary_integration_example.m: -------------------------------------------------------------------------------- 1 | %% Binary integration example 2 | % Created by: Lee A. Harrison 3 | % On: 10/11/2018 4 | % 5 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 6 | % This file is part of Introduction to Radar Using Python and MATLAB 7 | % and can not be copied and/or distributed without the express permission of Artech House. 8 | 9 | clear, clc 10 | 11 | % Set the parameters 12 | snr_db = linspace(0, 20); 13 | snr = 10.^(snr_db / 10); 14 | pfa = 1.0e-6; 15 | m = 3; 16 | n = 5; 17 | 18 | % Calculate the probability of detection 19 | for i = 1:length(snr) 20 | pd(i) = binary_integration(m, n, pd_rayleigh(snr(i), pfa), pfa); 21 | end 22 | 23 | % Plot the results 24 | figure; 25 | plot(snr_db, pd); 26 | title('Binary Integration M of N'); 27 | xlabel('Signal to Noise (dB)'); 28 | ylabel('Probability of Detection'); 29 | grid on; 30 | plot_settings; -------------------------------------------------------------------------------- /mlradar/Chapter06/cfar_example.m: -------------------------------------------------------------------------------- 1 | %% CFAR example 2 | % Created by: Lee A. Harrison 3 | % On: 10/11/2018 4 | % 5 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 6 | % This file is part of Introduction to Radar Using Python and MATLAB 7 | % and can not be copied and/or distributed without the express permission of Artech House. 8 | 9 | clear, clc 10 | 11 | % Set the parameters 12 | cfar_type = 'Cell Averaging'; 13 | %cfar_type = 'Cell Averaging Greatest Of'; 14 | %cfar_type = 'Cell Averaging Smallest Of'; 15 | %cfar_type = 'Ordered Statistic'; 16 | 17 | guard_cells = 2; 18 | reference_cells = 10; 19 | bias = 3.0; 20 | 21 | % Generate a sample signal to be used (later used matched filter output) 22 | number_of_samples = 1000; 23 | i_noise = 0.05 * randn(1, number_of_samples); 24 | q_noise = 0.05 * randn(1, number_of_samples); 25 | 26 | noise_signal = sqrt(i_noise .^ 2 + q_noise .^ 2); 27 | 28 | t = linspace(0.0, 1.0, number_of_samples); 29 | 30 | s1 = 0.4 * cos(2 * pi * 600 * t) + 1j * 0.4 * sin(2 * pi * 600 * t); 31 | s2 = 0.1 * cos(2 * pi * 150 * t) + 1j * 0.1 * sin(2 * pi * 150 * t); 32 | s3 = 0.2 * cos(2 * pi * 100 * t) + 1j * 0.2 * sin(2 * pi * 100 * t); 33 | 34 | % Sum for the example signal 35 | signal = abs(fft(s1 + s2 + s3 + noise_signal)); 36 | signal(1) = 0; 37 | 38 | % Calculate the CFAR threshold 39 | cfar_threshold = cfar(signal, guard_cells, reference_cells, bias, cfar_type); 40 | 41 | % Plot the results 42 | figure; 43 | plot(t, 10 * log10(signal)); hold on; 44 | plot(t, cfar_threshold); 45 | title('Constant False Alarm Rate'); 46 | xlabel('Range (m)'); 47 | ylabel('Signal Strength (dB)'); 48 | legend('Signal', 'CFAR Threshold'); 49 | grid on; 50 | plot_settings; -------------------------------------------------------------------------------- /mlradar/Chapter06/coherent_integration_example.m: -------------------------------------------------------------------------------- 1 | %% Coherent integration example 2 | % Created by: Lee A. Harrison 3 | % On: 10/11/2018 4 | % 5 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 6 | % This file is part of Introduction to Radar Using Python and MATLAB 7 | % and can not be copied and/or distributed without the express permission of Artech House. 8 | 9 | clear, clc 10 | 11 | % Set the parameters 12 | snr_db = linspace(-4.0, 18.0); 13 | snr = 10.^(snr_db/10); 14 | pfa = 1.0e-9; 15 | number_of_pulses = 10; 16 | target_type = 'Swerling 0'; 17 | 18 | % Calculate the probability of detection 19 | pd = coherent_integration(snr, number_of_pulses, pfa, target_type); 20 | 21 | % Plot the results 22 | figure; 23 | plot(snr_db, pd); 24 | title('Coherent Integration'); 25 | xlabel('Signal to Noise (dB)'); 26 | ylabel('Probability of Detection'); 27 | grid on; 28 | plot_settings; -------------------------------------------------------------------------------- /mlradar/Chapter06/gaussian_noise_pd_example.m: -------------------------------------------------------------------------------- 1 | %% Gaussian noise pd example 2 | % Created by: Lee A. Harrison 3 | % On: 10/11/2018 4 | % 5 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 6 | % This file is part of Introduction to Radar Using Python and MATLAB 7 | % and can not be copied and/or distributed without the express permission of Artech House. 8 | 9 | clear, clc 10 | 11 | % Set the parameters 12 | snr_db = linspace(3.0, 18.0); 13 | snr = 10.^(snr_db/10); 14 | pfa = 1.0e-6; 15 | 16 | % Calculate the probability of detection 17 | pd = pd_gaussian(snr, pfa); 18 | 19 | % Plot the results 20 | figure; 21 | plot(snr_db, pd); 22 | title('Pd - Gaussian Noise'); 23 | xlabel('Signal to Noise (dB)'); 24 | ylabel('Probability of Detection'); 25 | grid on; 26 | plot_settings; -------------------------------------------------------------------------------- /mlradar/Chapter06/non_coherent_integration_example.m: -------------------------------------------------------------------------------- 1 | %% Non-Coherent integration example 2 | % Created by: Lee A. Harrison 3 | % On: 10/11/2018 4 | % 5 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 6 | % This file is part of Introduction to Radar Using Python and MATLAB 7 | % and can not be copied and/or distributed without the express permission of Artech House. 8 | 9 | clear, clc 10 | 11 | % Set the parameters 12 | snr_db = linspace(-4.0, 18.0); 13 | snr = 10.^(snr_db/10); 14 | pfa = 1.0e-9; 15 | number_of_pulses = 10; 16 | target_type = 'Swerling 0'; 17 | 18 | % Calculate the probability of detection 19 | pd = non_coherent_integration(snr, pfa, number_of_pulses, target_type); 20 | 21 | % Plot the results 22 | figure; 23 | plot(snr_db, pd); 24 | title('Noncoherent Integration'); 25 | xlabel('Signal to Noise (dB)'); 26 | ylabel('Probability of Detection'); 27 | grid on; 28 | plot_settings; -------------------------------------------------------------------------------- /mlradar/Chapter06/optimum_binary_example.m: -------------------------------------------------------------------------------- 1 | %% Optimum binary example 2 | % Created by: Lee A. Harrison 3 | % On: 10/11/2018 4 | % 5 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 6 | % This file is part of Introduction to Radar Using Python and MATLAB 7 | % and can not be copied and/or distributed without the express permission of Artech House. 8 | 9 | clear, clc 10 | 11 | % Set the parameters 12 | number_of_pulses = 10; 13 | target_type = 'Swerling 0'; 14 | 15 | if strcmp(target_type, 'Swerling 0') 16 | alpha = 0.8; 17 | beta = -0.02; 18 | elseif strcmp(target_type, 'Swerling 1') 19 | alpha = 0.8; 20 | beta = -0.02; 21 | elseif strcmp(target_type, 'Swerling 2') 22 | alpha = 0.91; 23 | beta = -0.38; 24 | elseif strcmp(target_type, 'Swerling 3') 25 | alpha = 0.8; 26 | beta = -0.02; 27 | elseif strcmp(target_type, 'Swerling 4') 28 | alpha = 0.873; 29 | beta = -0.27; 30 | end 31 | 32 | % Calculate the optimum choice for M 33 | n = 1:number_of_pulses + 1; 34 | m_optimum = ceil(10.0 ^ beta * n .^ alpha); 35 | 36 | % Plot the results 37 | figure; 38 | plot(n, m_optimum); 39 | title('Optimum M for Binary Integration'); 40 | xlabel('Number of Pulses'); 41 | ylabel('M'); 42 | grid on; 43 | plot_settings; -------------------------------------------------------------------------------- /mlradar/Chapter06/probability_distributions_example.m: -------------------------------------------------------------------------------- 1 | %% Optimum binary example 2 | % Created by: Lee A. Harrison 3 | % On: 10/11/2018 4 | % 5 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 6 | % This file is part of Introduction to Radar Using Python and MATLAB 7 | % and can not be copied and/or distributed without the express permission of Artech House. 8 | 9 | clear, clc 10 | 11 | % Gaussian pdf 12 | x = -3:0.01:3; 13 | y = pdf('Normal', x, 1.0, 2.0); 14 | 15 | % Weibull 16 | pd = makedist('Weibull','a',5,'b',2); 17 | x = 0:0.01:15; 18 | y = pdf(pd, x); 19 | 20 | % Rayleigh 21 | x = 0:0.01:2; 22 | y = raylpdf(x, 0.5); 23 | 24 | % Rician 25 | x = 0:0.01:10; 26 | pd = makedist('Rician','s',0,'sigma',2); 27 | y = pdf(pd, x); 28 | 29 | % Chi-Squared 30 | x = 0:0.01:15; 31 | y = chi2pdf(x, 4); 32 | 33 | % Plot the results 34 | figure; 35 | plot(x, y); 36 | title('Probability Density Function'); 37 | xlabel('x'); 38 | ylabel('Probability p(x)'); 39 | grid on; 40 | plot_settings; -------------------------------------------------------------------------------- /mlradar/Chapter06/rayleigh_noise_pd_example.m: -------------------------------------------------------------------------------- 1 | %% Rayleigh noise pd example 2 | % Created by: Lee A. Harrison 3 | % On: 10/11/2018 4 | % 5 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 6 | % This file is part of Introduction to Radar Using Python and MATLAB 7 | % and can not be copied and/or distributed without the express permission of Artech House. 8 | 9 | clear, clc 10 | 11 | % Set the parameters 12 | snr_db = linspace(3.0, 18.0); 13 | snr = 10.^(snr_db/10); 14 | pfa = 1.0e-6; 15 | 16 | % Calculate the probability of detection 17 | pd = pd_rayleigh(snr, pfa); 18 | 19 | % Plot the results 20 | figure; 21 | plot(snr_db, pd); 22 | title('Pd - Rayleigh Noise'); 23 | xlabel('Signal to Noise (dB)'); 24 | ylabel('Probability of Detection'); 25 | grid on; 26 | plot_settings; -------------------------------------------------------------------------------- /mlradar/Chapter06/shnidman_example.m: -------------------------------------------------------------------------------- 1 | %% Shnidman example 2 | % Created by: Lee A. Harrison 3 | % On: 10/11/2018 4 | % 5 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 6 | % This file is part of Introduction to Radar Using Python and MATLAB 7 | % and can not be copied and/or distributed without the express permission of Artech House. 8 | 9 | clear, clc 10 | 11 | % Set the parameters 12 | pd = linspace(0.1, 0.99, 200); 13 | pfa = 1.0e-6; 14 | number_of_pulses = 10; 15 | target_type = 'Swerling 4'; 16 | 17 | % Calculate the error in the Shnidman approximation of signal to noise 18 | error = zeros(1, length(pd)); 19 | for i = 1:length(pd) 20 | error(i) = 10 * log10(single_pulse_snr_swerling(pd(i), pfa, number_of_pulses, target_type)) - ... 21 | shnidman(pd(i), pfa, number_of_pulses, target_type); 22 | end 23 | 24 | % Plot the results 25 | figure; 26 | plot(pd, error); 27 | ylim([-1, 1]) 28 | title('Shnidman''s Approximation'); 29 | xlabel('Probability of Detection'); 30 | ylabel('Signal to Noise Error (dB)'); 31 | grid on; 32 | plot_settings; -------------------------------------------------------------------------------- /mlradar/Chapter06/single_pulse_snr_example.m: -------------------------------------------------------------------------------- 1 | %% Single pulse example example 2 | % Created by: Lee A. Harrison 3 | % On: 10/11/2018 4 | % 5 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 6 | % This file is part of Introduction to Radar Using Python and MATLAB 7 | % and can not be copied and/or distributed without the express permission of Artech House. 8 | 9 | clear, clc 10 | 11 | % Set the parameters 12 | pfa = 1.0e-6; 13 | pd = 0.99; 14 | number_of_pulses = 10; 15 | 16 | np = 1:number_of_pulses; 17 | 18 | % Find the required signal to noise for the pd & pfa 19 | required_snr = single_pulse_snr(pd, pfa); 20 | 21 | % Calculate the single pulse signal to noise (Curry) 22 | signal_to_noise_reduction = snr_reduction(np, required_snr); 23 | 24 | % Calculate the single pulse signal to noise (Peebles) 25 | signal_to_noise_gain = snr_gain(pd, pfa, np, required_snr); 26 | 27 | % Calculate the single pulse signal to noise for coherent integration 28 | signal_to_noise_coherent = 10.0 * log10(required_snr ./ np); 29 | 30 | % Plot the results 31 | figure; 32 | plot(np, signal_to_noise_coherent); hold on; 33 | plot(np, signal_to_noise_gain); 34 | plot(np, signal_to_noise_reduction); 35 | title('Single Pulse Signal to Noise'); 36 | xlabel('Number of Pulses'); 37 | ylabel('Signal to Noise (dB)'); 38 | grid on; 39 | legend('Coherent Integration', 'Noncoherent Integration (6.22)', 'Noncoherent Integration (6.21)') 40 | plot_settings; -------------------------------------------------------------------------------- /mlradar/Chapter07/fdtd_example.m: -------------------------------------------------------------------------------- 1 | %% FDTD example 2 | % Created by: Lee A. Harrison 3 | % On: 1/15/2019 4 | % 5 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 6 | % This file is part of Introduction to Radar Using Python and MATLAB 7 | % and can not be copied and/or distributed without the express permission of Artech House. 8 | 9 | clear, clc 10 | 11 | % Set the parameters 12 | data.mode = 'TM'; 13 | data.incident_angle = 90.0; % Degrees 14 | data.number_of_time_steps = 400; 15 | data.geometry_file = 'fdtd.cell'; 16 | data.gaussian_pulse_width = 10; % Steps 17 | data.gaussian_pulse_amplitude = 1.0; 18 | data.number_of_pml = 20; 19 | 20 | % Run the finite difference time domain method 21 | fdtd(data); -------------------------------------------------------------------------------- /mlradar/Chapter07/frustum_example.m: -------------------------------------------------------------------------------- 1 | %% Frustum example 2 | % Created by: Lee A. Harrison 3 | % On: 1/15/2019 4 | % 5 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 6 | % This file is part of Introduction to Radar Using Python and MATLAB 7 | % and can not be copied and/or distributed without the express permission of Artech House. 8 | 9 | clear, clc 10 | 11 | % Set the parameters 12 | frequency = 1.0e9; % Hz 13 | nose_radius = 0.1; % meters 14 | base_radius = 0.2; % meters 15 | length = 0.8; % meters 16 | 17 | % Set the incident angles 18 | incident_angle = linspace(0, pi, 1801); 19 | 20 | % Calculate the radar cross section 21 | for i = 1:numel(incident_angle) 22 | rcs(i) = rcs_frustum(frequency, nose_radius, base_radius, length, incident_angle(i)); 23 | end 24 | 25 | % Display the results 26 | figure; 27 | plot(incident_angle * 180 / pi, 10 * log10(rcs)) 28 | title('RCS vs Incident Angle') 29 | ylabel('RCS (dBsm)') 30 | xlabel('Incident Angle (deg)') 31 | 32 | % Turn on the grid 33 | grid on 34 | 35 | % Plot settings 36 | plot_settings; -------------------------------------------------------------------------------- /mlradar/Chapter07/infinite_cylinder_example.m: -------------------------------------------------------------------------------- 1 | %% Infinite cylinder example 2 | % Created by: Lee A. Harrison 3 | % On: 1/15/2019 4 | % 5 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 6 | % This file is part of Introduction to Radar Using Python and MATLAB 7 | % and can not be copied and/or distributed without the express permission of Artech House. 8 | 9 | clear, clc 10 | 11 | % Set the parameters 12 | frequency = 300e6; % Hz 13 | radius = 3; % meters 14 | length = 20; % meters 15 | number_of_modes = 60; 16 | 17 | % 2D or 3D RCS 18 | mode = '2D'; 19 | 20 | % Set the observation angles 21 | observation_angle = linspace(-90, 90, 1801); 22 | 23 | if strcmp(mode, '2D') 24 | for i = 1:numel(observation_angle) 25 | [rcs_te(i), rcs_tm(i)] = cylinder_rcs_2d(frequency, radius, observation_angle(i), number_of_modes); 26 | end 27 | else 28 | for i = 1:numel(observation_angle) 29 | [rcs_te(i), rcs_tm(i)] = cylinder_rcs_3d(frequency, radius, observation_angle(i), number_of_modes, length); 30 | end 31 | end 32 | 33 | % Display the results 34 | figure; 35 | plot(observation_angle, 10.0 * log10(rcs_te)); hold on; 36 | plot(observation_angle, 10.0 * log10(rcs_tm), '--') 37 | 38 | % Set the plot title and labels 39 | title('RCS vs Bistatic Angle') 40 | ylabel('RCS (dBsm)') 41 | xlabel('Observation Angle (deg)') 42 | ylim([min(10.0 * log10(rcs_te)) - 3, max(10.0 * log10(rcs_te)) + 3]) 43 | 44 | % Set the legend 45 | legend({'TE^{z}', 'TM^{z}'}) 46 | 47 | % Turn on the grid 48 | grid on 49 | 50 | % Plot settings 51 | plot_settings; 52 | -------------------------------------------------------------------------------- /mlradar/Chapter07/infinite_cylinder_oblique_example.m: -------------------------------------------------------------------------------- 1 | %% Infinite cylinder oblique example 2 | % Created by: Lee A. Harrison 3 | % On: 1/15/2019 4 | % 5 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 6 | % This file is part of Introduction to Radar Using Python and MATLAB 7 | % and can not be copied and/or distributed without the express permission of Artech House. 8 | 9 | clear, clc 10 | 11 | % Set the parameters 12 | frequency = 300e6; % Hz 13 | radius = 3; % meters 14 | length = 20; % meters 15 | incident_angle = 50; % degrees 16 | number_of_modes = 60; 17 | 18 | % 2D or 3D RCS 19 | mode = '3D'; 20 | 21 | % Set the observation angles 22 | observation_angle = linspace(-90, 90, 1801); 23 | 24 | if strcmp(mode, '2D') 25 | for i = 1:numel(observation_angle) 26 | [rcs_te(i), rcs_tm(i)] = cylinder_oblique_rcs_2d(frequency, radius, incident_angle, observation_angle(i), number_of_modes); 27 | end 28 | else 29 | for i = 1:numel(observation_angle) 30 | [rcs_te(i), rcs_tm(i)] = cylinder_oblique_rcs_3d(frequency, radius, incident_angle, observation_angle(i), number_of_modes, length); 31 | end 32 | end 33 | 34 | % Display the results 35 | figure; 36 | plot(observation_angle, 10.0 * log10(rcs_te + 1e-10)); hold on; 37 | plot(observation_angle, 10.0 * log10(rcs_tm + 1e-10), '--') 38 | 39 | % Set the plot title and labels 40 | title('RCS vs Bistatic Angle') 41 | ylabel('RCS (dBsm)') 42 | xlabel('Observation Angle (deg)') 43 | ylim([min(10.0 * log10(rcs_te + 1e-10)) - 3, max(10.0 * log10(rcs_te + 1e-10)) + 3]) 44 | 45 | % Set the legend 46 | legend({'TE^{z}', 'TM^{z}'}) 47 | 48 | % Turn on the grid 49 | grid on 50 | 51 | % Plot settings 52 | plot_settings; 53 | -------------------------------------------------------------------------------- /mlradar/Chapter07/infinite_strip_example.m: -------------------------------------------------------------------------------- 1 | %% Infinite strip example 2 | % Created by: Lee A. Harrison 3 | % On: 1/15/2019 4 | % 5 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 6 | % This file is part of Introduction to Radar Using Python and MATLAB 7 | % and can not be copied and/or distributed without the express permission of Artech House. 8 | 9 | clear, clc 10 | 11 | % Set the parameters 12 | incident_angle = 60; % degrees 13 | frequency = 300e6; % Hz 14 | width = 3; % meters 15 | 16 | % Set the observation angles 17 | observation_angle = linspace(0, 180, 1801); 18 | 19 | for i = 1:numel(observation_angle) 20 | [rcs_te(i), rcs_tm(i)] = strip_rcs(frequency, width, incident_angle, observation_angle(i)); 21 | end 22 | 23 | % Display the results 24 | figure; 25 | plot(observation_angle, 10 * log10(rcs_te + 1e-10)); hold on 26 | plot(observation_angle, 10 * log10(rcs_tm + 1e-10), '--') 27 | 28 | % Set the plot title and labels 29 | title('RCS vs Bistatic Angle') 30 | ylabel('RCS (dBsm)') 31 | xlabel('Observation Angle (deg)') 32 | ylim([min(10 * log10(rcs_te + 1e-4)) - 3, max(10 * log10(rcs_te + 1e-4)) + 3]) 33 | 34 | % Set the legend 35 | legend({'TE^{z}', 'TM^{z}'}) 36 | 37 | % Turn on the grid 38 | grid on 39 | 40 | % Plot settings 41 | plot_settings; 42 | -------------------------------------------------------------------------------- /mlradar/Chapter07/rectangular_plate_example.m: -------------------------------------------------------------------------------- 1 | %% Rectangular plate example 2 | % Created by: Lee A. Harrison 3 | % On: 1/17/2019 4 | % 5 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 6 | % This file is part of Introduction to Radar Using Python and MATLAB 7 | % and can not be copied and/or distributed without the express permission of Artech House. 8 | 9 | clear, clc 10 | 11 | % Set the parameters 12 | frequency = 300e6; % Hz 13 | width = 3; % meters 14 | length = 5; % meters 15 | incident_theta = 15.0; % degrees 16 | 17 | % Set the observation angles 18 | observation_phi = 90.0; % degrees 19 | observation_theta = linspace(-90, 90, 1801); % degrees 20 | 21 | % Calculate the radar cross section 22 | for i = 1:numel(observation_theta) 23 | [rcs_tm(i), rcs_te(i)] = rectangular_plate(frequency, width, length, incident_theta, observation_theta(i), observation_phi); 24 | end 25 | 26 | % Display the results 27 | figure; 28 | plot(observation_theta, 10 * log10(rcs_te)); hold on; 29 | plot(observation_theta, 10 * log10(rcs_tm), '--') 30 | title('RCS vs Observation Angle') 31 | ylabel('RCS (dBsm)') 32 | xlabel('Observation Angle (deg)') 33 | 34 | ylim([min(10 * log10(rcs_te + 1e-4)) - 3, max(10 * log10(rcs_te + 1e-4)) + 3]) 35 | 36 | % Legend 37 | legend({'TE^{x}', 'TM^{x}'}) 38 | 39 | % Turn on the grid 40 | grid on 41 | 42 | % Plot settings 43 | plot_settings; -------------------------------------------------------------------------------- /mlradar/Chapter07/right_circular_cone_example.m: -------------------------------------------------------------------------------- 1 | %% Right circular cone example 2 | % Created by: Lee A. Harrison 3 | % On: 1/17/2019 4 | % 5 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 6 | % This file is part of Introduction to Radar Using Python and MATLAB 7 | % and can not be copied and/or distributed without the express permission of Artech House. 8 | 9 | clear, clc 10 | 11 | % Set the parameters 12 | frequency = 1e9; % Hz 13 | cone_half_angle = 15; % degrees 14 | base_radius = 1.4; % meters 15 | 16 | % Set the incident angles 17 | incident_angle = linspace(0, pi, 1801); 18 | 19 | % Calculate the radar cross section 20 | for i = 1:numel(incident_angle) 21 | [rcs_vv(i), rcs_hh(i)] = right_circular_cone(frequency, cone_half_angle * pi / 180, base_radius, incident_angle(i)); 22 | end 23 | 24 | % Display the results 25 | figure; 26 | plot(incident_angle, 10 * log10(rcs_vv)); hold on; 27 | plot(incident_angle, 10 * log10(rcs_hh), '--') 28 | title('RCS vs Incident Angle') 29 | ylabel('RCS (dBsm)') 30 | xlabel('Incident Angle (deg)') 31 | 32 | ylim([min(10 * log10(rcs_vv + 1e-4)) - 3, max(10 * log10(rcs_vv + 1e-4)) + 3]) 33 | 34 | % Legend 35 | legend({'VV', 'HH'}) 36 | 37 | % Turn on the grid 38 | grid on 39 | 40 | % Plot settings 41 | plot_settings; -------------------------------------------------------------------------------- /mlradar/Chapter07/rounded_nose_cone_example.m: -------------------------------------------------------------------------------- 1 | %% Rounded nose cone example 2 | % Created by: Lee A. Harrison 3 | % On: 1/18/2019 4 | % 5 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 6 | % This file is part of Introduction to Radar Using Python and MATLAB 7 | % and can not be copied and/or distributed without the express permission of Artech House. 8 | 9 | clear, clc 10 | 11 | % Set the parameters 12 | frequency = 1e9; % Hz 13 | cone_half_angle = 20; % degrees 14 | nose_radius = 1.4; % meters 15 | 16 | % Set the incident angles 17 | incident_angle = linspace(0, cone_half_angle * pi / 180, 1801); 18 | 19 | % Calculate the radar cross section 20 | for i = 1:numel(incident_angle) 21 | rcs(i) = abs(rounded_nose_cone(frequency, cone_half_angle * pi / 180, nose_radius, incident_angle(i))); 22 | end 23 | 24 | % Display the results 25 | figure; 26 | plot(incident_angle, 10 * log10(rcs)); 27 | title('RCS vs Incident Angle') 28 | ylabel('RCS (dBsm)') 29 | xlabel('Incident Angle (deg)') 30 | 31 | ylim([min(10 * log10(rcs + 1e-4)) - 3, max(10 * log10(rcs + 1e-4)) + 3]) 32 | 33 | % Turn on the grid 34 | grid on 35 | 36 | % Plot settings 37 | plot_settings; -------------------------------------------------------------------------------- /mlradar/Chapter07/stratified_sphere_example.m: -------------------------------------------------------------------------------- 1 | %% Stratified sphere example 2 | % Created by: Lee A. Harrison 3 | % On: 1/18/2019 4 | % 5 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 6 | % This file is part of Introduction to Radar Using Python and MATLAB 7 | % and can not be copied and/or distributed without the express permission of Artech House. 8 | 9 | clear, clc 10 | 11 | % Set the parameters 12 | frequency = 1e9; % Hz 13 | radius = [1.0, 1.25]; % meters 14 | mu_r = [1.0, 1.0]; 15 | eps_r = [1.0, 4.0]; 16 | number_of_modes = 60; 17 | 18 | pec_core = true; 19 | 20 | % To put the parameters in order 21 | nr = numel(radius); 22 | 23 | mu = ones(nr + 1, 1); 24 | eps = ones(nr + 1, 1); 25 | ra = ones(nr, 1); 26 | 27 | % Set up the parameters in the correct order 28 | 29 | for ir = 1:nr 30 | ra(nr + 1 - ir) = radius(ir); 31 | end 32 | 33 | for ie = 1:numel(eps_r) 34 | mu(nr + 2 - ie) = mu_r(ie); 35 | eps(nr + 2 - ie) = eps_r(ie); 36 | end 37 | 38 | % Set the observation angles 39 | observation_angle = linspace(0, pi, 721); 40 | 41 | [An, Bn] = sphere_coefficients(frequency, eps, mu, ra, number_of_modes, pec_core); 42 | 43 | for i = 1:numel(observation_angle) 44 | [et(i), ~] = stratified_sphere(frequency, observation_angle(i), 0, An, Bn); 45 | [~, ep(i)] = stratified_sphere(frequency, observation_angle(i), 0.5 * pi, An, Bn); 46 | end 47 | 48 | % Display the results 49 | figure; 50 | plot(observation_angle * 180 / pi, 20 * log10(abs(ep))); hold on 51 | plot(observation_angle * 180 / pi, 20 * log10(abs(et))) 52 | title('RCS vs Bistatic Angle') 53 | ylabel('RCS (dBsm)') 54 | xlabel('Observation Angle (deg)') 55 | 56 | ylim([min(20.0 * log10(abs(et))) - 3, max(20.0 * log10(abs(et))) + 3]) 57 | 58 | % Legend 59 | legend({'TE', 'TM'}) 60 | 61 | % Turn on the grid 62 | grid on 63 | 64 | % Plot settings 65 | plot_settings; -------------------------------------------------------------------------------- /mlradar/Chapter08/frank_ambiguity_example.m: -------------------------------------------------------------------------------- 1 | %% Frank ambiguity example 2 | % Created by: Lee A. Harrison 3 | % On: 4/26/2019 4 | % 5 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 6 | % This file is part of Introduction to Radar Using Python and MATLAB 7 | % and can not be copied and/or distributed without the express permission of Artech House. 8 | 9 | clear, clc 10 | 11 | % Set the parameters 12 | n_phase = 3; % N-phase Frank code 13 | chip_width = 0.1; % seconds 14 | 15 | % Get the N-phase Frank code 16 | code = n_phase_code(n_phase); 17 | 18 | % Calculate the ambiguity function 19 | [ambiguity, time_delay, doppler_frequency] = phase_coded_waveform(code, chip_width); 20 | 21 | % Zero Doppler cut 22 | figure; 23 | plot(time_delay, ambiguity(round(length(doppler_frequency) / 2), :)); 24 | xlabel('Time (s)'); 25 | ylabel('Relative Amplitude'); 26 | title('Frank Code Ambiguity Function'); 27 | xlim([-length(code) * chip_width, length(code) * chip_width]) 28 | grid on; 29 | plot_settings; 30 | 31 | % Zero range cut 32 | figure; 33 | plot(doppler_frequency, ambiguity(:, round(length(time_delay) / 2))); 34 | xlabel('Doppler (Hz)'); 35 | ylabel('Relative Amplitude'); 36 | title('Frank Code Ambiguity Function'); 37 | grid on; 38 | plot_settings; 39 | 40 | % 2D contour 41 | [t, f] = meshgrid(time_delay, doppler_frequency); 42 | figure; 43 | contour(t, f, ambiguity, 30); 44 | xlabel('Time (s)'); 45 | ylabel('Doppler (Hz)'); 46 | title('Frank Code Ambiguity Function'); 47 | xlim([-length(code) * chip_width, length(code) * chip_width]) 48 | grid on; 49 | plot_settings; -------------------------------------------------------------------------------- /mlradar/Chapter08/lfm_pulse_ambiguity_example.m: -------------------------------------------------------------------------------- 1 | %% LFM pulse ambiguity example 2 | % Created by: Lee A. Harrison 3 | % On: 4/26/2019 4 | % 5 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 6 | % This file is part of Introduction to Radar Using Python and MATLAB 7 | % and can not be copied and/or distributed without the express permission of Artech House. 8 | 9 | clear, clc 10 | 11 | % Set the parameters 12 | bandwidth = 2e3; % Hz 13 | pulsewidth = 1e-3; % seconds 14 | 15 | %% Zero Doppler cut 16 | 17 | % Set the time delay 18 | time_delay = linspace(-pulsewidth, pulsewidth, 5000); 19 | 20 | % Calculate the ambiguity function 21 | ambiguity = lfm_pulse(time_delay, eps, pulsewidth, bandwidth); 22 | 23 | figure; 24 | plot(time_delay, ambiguity); 25 | xlabel('Time (s)'); 26 | ylabel('Relative Amplitude'); 27 | title('LFM Pulse Ambiguity Function'); 28 | grid on; 29 | plot_settings; 30 | 31 | %% Zero range cut 32 | 33 | % Set the Doppler mismatch 34 | doppler_frequency = linspace(-bandwidth, bandwidth, 5000); 35 | 36 | % Calculate the ambiguity function 37 | ambiguity = lfm_pulse(eps, doppler_frequency, pulsewidth, bandwidth); 38 | 39 | figure; 40 | plot(doppler_frequency, ambiguity); 41 | xlabel('Doppler (Hz)'); 42 | ylabel('Relative Amplitude'); 43 | title('LFM Pulse Ambiguity Function'); 44 | grid on; 45 | plot_settings; 46 | 47 | %% 2D contour 48 | 49 | % Set the time delay 50 | time_delay = linspace(-pulsewidth, pulsewidth, 500); 51 | 52 | % Set the Doppler mismatch 53 | doppler_frequency = linspace(-bandwidth, bandwidth, 500); 54 | 55 | % Create the grid 56 | [t, f] = meshgrid(time_delay, doppler_frequency); 57 | 58 | % Calculate the ambiguity function 59 | ambiguity = lfm_pulse(t, f, pulsewidth, bandwidth); 60 | 61 | figure; 62 | contour(t, f, ambiguity, 30); 63 | xlabel('Time (s)'); 64 | ylabel('Doppler (Hz)'); 65 | title('LFM Pulse Ambiguity Function'); 66 | grid on; 67 | plot_settings; -------------------------------------------------------------------------------- /mlradar/Chapter08/single_pulse_ambiguity_example.m: -------------------------------------------------------------------------------- 1 | %% Single pulse ambiguity example 2 | % Created by: Lee A. Harrison 3 | % On: 4/27/2019 4 | % 5 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 6 | % This file is part of Introduction to Radar Using Python and MATLAB 7 | % and can not be copied and/or distributed without the express permission of Artech House. 8 | 9 | clear, clc 10 | 11 | % Set the parameters 12 | pulsewidth = 1e-3; % seconds 13 | 14 | %% Zero Doppler cut 15 | 16 | % Set the time delay 17 | time_delay = linspace(-pulsewidth, pulsewidth, 5000); 18 | 19 | % Calculate the ambiguity function 20 | ambiguity = single_pulse(time_delay, eps, pulsewidth); 21 | 22 | figure; 23 | plot(time_delay, ambiguity); 24 | xlabel('Time (s)'); 25 | ylabel('Relative Amplitude'); 26 | title('Unmodulated Pulse Ambiguity Function'); 27 | grid on; 28 | plot_settings; 29 | 30 | %% Zero range cut 31 | 32 | % Set the Doppler mismatch 33 | doppler_frequency = linspace(-2.0 / pulsewidth, 2.0 / pulsewidth, 5000); 34 | 35 | % Calculate the ambiguity function 36 | ambiguity = single_pulse(eps, doppler_frequency, pulsewidth); 37 | 38 | figure; 39 | plot(doppler_frequency, ambiguity); 40 | xlabel('Doppler (Hz)'); 41 | ylabel('Relative Amplitude'); 42 | title('Unmodulated Pulse Ambiguity Function'); 43 | grid on; 44 | plot_settings; 45 | 46 | %% 2D contour 47 | 48 | % Set the time delay 49 | time_delay = linspace(-pulsewidth, pulsewidth, 500); 50 | 51 | % Set the Doppler mismatch 52 | doppler_frequency = linspace(-2.0 / pulsewidth, 2.0 / pulsewidth, 500); 53 | 54 | % Create the grid 55 | [t, f] = meshgrid(time_delay, doppler_frequency); 56 | 57 | % Calculate the ambiguity function 58 | ambiguity = single_pulse(t, f, pulsewidth); 59 | 60 | figure; 61 | contour(t, f, ambiguity, 30); 62 | xlabel('Time (s)'); 63 | ylabel('Doppler (Hz)'); 64 | title('Unmodulated Pulse Ambiguity Function'); 65 | grid on; 66 | plot_settings; -------------------------------------------------------------------------------- /mlradar/Chapter08/stepped_frequency_example.m: -------------------------------------------------------------------------------- 1 | %% Stepped frequency example 2 | % Created by: Lee A. Harrison 3 | % On: 4/27/2019 4 | % 5 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 6 | % This file is part of Introduction to Radar Using Python and MATLAB 7 | % and can not be copied and/or distributed without the express permission of Artech House. 8 | 9 | clear, clc 10 | 11 | % Speed of light 12 | c = 299792458; 13 | 14 | % Set the parameters 15 | number_of_steps = 64; 16 | frequency_step = 50e3; 17 | prf = 100; 18 | target_range = [0.5e3, 1.5e3, 2.0e3]; 19 | target_rcs = [1, 10, 100]; 20 | target_velocity = [0, 0, 10]; 21 | window = 'None'; 22 | 23 | switch window 24 | case 'Hanning' 25 | coefficients = hanning(number_of_steps); 26 | case 'Hamming' 27 | coefficients = hamming(number_of_steps); 28 | case 'Kaiser' 29 | coefficients = kaiser(number_of_steps, 6); 30 | case 'None' 31 | coefficients = ones(1, number_of_steps); 32 | end 33 | 34 | % Calculate the base band return signal 35 | s = 0; 36 | 37 | for m = 1:length(target_range) 38 | s0 = zeros(number_of_steps, 1); 39 | for i = 1:number_of_steps 40 | s0(i) = sqrt(target_rcs(m)) * exp(-1j * 4.0 * pi / c * (i * frequency_step) ... 41 | * (target_range(m) - target_velocity(m) * (i / prf))); 42 | end 43 | s = s + s0; 44 | end 45 | 46 | n = 2^nextpow2(10 * number_of_steps); 47 | sf = ifft(s .* coefficients', n) * n / number_of_steps; 48 | 49 | % range_resolution = c / (2.0 * number_of_steps * frequency_step) 50 | range_unambiguous = c / (2.0 * frequency_step); 51 | 52 | range_window = linspace(0, range_unambiguous, n); 53 | 54 | % Plot the results 55 | figure 56 | plot(range_window, 20.0 * log10(abs(sf) / n + eps)) 57 | xlabel('Range (m)') 58 | ylabel('Amplitude (dBsm)') 59 | title('Stepped Frequency Range Profile') 60 | grid on 61 | plot_settings; -------------------------------------------------------------------------------- /mlradar/Chapter08/stretch_processor_example.m: -------------------------------------------------------------------------------- 1 | %% Stretch processor example 2 | % Created by: Lee A. Harrison 3 | % On: 4/27/2019 4 | % 5 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 6 | % This file is part of Introduction to Radar Using Python and MATLAB 7 | % and can not be copied and/or distributed without the express permission of Artech House. 8 | 9 | clear, clc 10 | 11 | % Speed of light 12 | c = 299792458; 13 | 14 | % Set the parameters 15 | bandwidth = 1e9; % Hz 16 | pulsewidth = 10e-4; % seconds 17 | range_window_length = 50.0; % meters 18 | target_range = [5, 15]; % meters 19 | target_rcs = [20, 10]; % square meters 20 | window = 'None'; 21 | 22 | % Number of samples 23 | n = ceil(4 * bandwidth * range_window_length / c); 24 | 25 | switch window 26 | case 'Hanning' 27 | coefficients = hanning(n); 28 | case 'Hamming' 29 | coefficients = hamming(n); 30 | case 'Kaiser' 31 | coefficients = kaiser(n, 6); 32 | case 'None' 33 | coefficients = ones(1, n); 34 | end 35 | 36 | % Set up the time vector 37 | t = linspace(-0.5 * pulsewidth, 0.5 * pulsewidth, n); 38 | 39 | % Sampled signal after mixing 40 | so = 0; 41 | 42 | for i = 1:length(target_range) 43 | so = so + sqrt(target_rcs(i)) * exp(1j * 2.0 * pi * bandwidth / pulsewidth * (2 * target_range(i) / c) * t); 44 | end 45 | 46 | % Fourier transform 47 | so = fftshift(fft(so .* coefficients, 4 * n)); 48 | 49 | % FFT frequencies 50 | frequencies = fftshift(fftfreq(4 * n, t(2) - t(1))); 51 | 52 | % Range window 53 | range_window = 0.5 * frequencies * c * pulsewidth / bandwidth; 54 | 55 | % Plot the results 56 | figure 57 | plot(range_window, 20.0 * log10(abs(so) / n + eps)) 58 | xlim([min(target_range) - 5, max(target_range) + 5]); 59 | ylim([-60, max(20.0 * log10(abs(so) / n)) + 10]); 60 | xlabel('Range (m)') 61 | ylabel('Amplitude (dBsm)') 62 | title('Stretch Processor Range Profile') 63 | grid on 64 | plot_settings; -------------------------------------------------------------------------------- /mlradar/Chapter11/burn_through_range_example.m: -------------------------------------------------------------------------------- 1 | %% Burn through range example 2 | % Created by: Lee A. Harrison 3 | % On: 5/28/2019 4 | % 5 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 6 | % This file is part of Introduction to Radar Using Python and MATLAB 7 | % and can not be copied and/or distributed without the express permission of Artech House. 8 | 9 | clear, clc 10 | 11 | % Set the parameters 12 | 13 | % Jammer type 14 | jammer_type = 'Self Screening'; 15 | % jammer_type = 'Escort'; 16 | 17 | % Transmit power (W) 18 | peak_power = 100e3; 19 | 20 | % Antenna gain (dB) 21 | radar_antenna_gain = 20; 22 | 23 | % Antenna sidelobe level (dB) 24 | radar_antenna_sidelobe = -20; 25 | 26 | % Radar bandwidth (Hz) 27 | radar_bandwidth = 100e6; 28 | 29 | % Radar Losses (dB) 30 | radar_losses = 3; 31 | 32 | % Target RCS (dBsm) 33 | target_rcs = 3; 34 | 35 | % Jammer ERP (dBW) 36 | jammer_erp = linspace(0, 15, 1000); 37 | 38 | % Jammer bandwidth (Hz) 39 | jammer_bandwidth = 10e6; 40 | 41 | % Jammer range (escort) (m) 42 | jammer_range = 100e3; 43 | 44 | % J/S required (dB) 45 | jsr = -20; 46 | 47 | % Calculate the burn through range 48 | if strcmp(jammer_type, 'Self Screening') 49 | br = burn_through_range_selfscreen(peak_power, lin(radar_antenna_gain), lin(target_rcs),... 50 | radar_bandwidth, lin(radar_losses), lin(jsr), lin(jammer_erp), jammer_bandwidth); 51 | else 52 | br = burn_through_range_escort(peak_power, lin(radar_antenna_gain), lin(target_rcs),... 53 | radar_bandwidth, lin(radar_losses), jammer_range, lin(jsr), lin(jammer_erp), ... 54 | jammer_bandwidth, lin(radar_antenna_sidelobe)); 55 | end 56 | 57 | % Display the results 58 | plot(jammer_erp, br) 59 | 60 | % Set the plot title and labels 61 | title('Burn Through Range') 62 | xlabel('Jammer ERP (dBW)') 63 | ylabel('Burn Through Range (m)') 64 | 65 | % Turn on the grid 66 | grid 67 | 68 | % Plot settings 69 | plot_settings -------------------------------------------------------------------------------- /mlradar/Chapter11/crossover_range_example.m: -------------------------------------------------------------------------------- 1 | %% Crossover range example 2 | % Created by: Lee A. Harrison 3 | % On: 5/28/2019 4 | % 5 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 6 | % This file is part of Introduction to Radar Using Python and MATLAB 7 | % and can not be copied and/or distributed without the express permission of Artech House. 8 | 9 | clear, clc 10 | 11 | % Set the parameters 12 | 13 | % Jammer type 14 | jammer_type = 'Self Screening'; 15 | % jammer_type = 'Escort'; 16 | 17 | % Transmit power (W) 18 | peak_power = 100e3; 19 | 20 | % Antenna gain (dB) 21 | radar_antenna_gain = 20; 22 | 23 | % Antenna sidelobe level (dB) 24 | radar_antenna_sidelobe = -20; 25 | 26 | % Radar bandwidth (Hz) 27 | radar_bandwidth = 100e6; 28 | 29 | % Radar Losses (dB) 30 | radar_losses = 3; 31 | 32 | % Target RCS (dBsm) 33 | target_rcs = 3; 34 | 35 | % Jammer ERP (dBW) 36 | jammer_erp = linspace(0, 15, 1000); 37 | 38 | % Jammer bandwidth (Hz) 39 | jammer_bandwidth = 10e6; 40 | 41 | % Jammer range (escort) (m) 42 | jammer_range = 100e3; 43 | 44 | % Calculate the crossover range 45 | if strcmp(jammer_type, 'Self Screening') 46 | cr = crossover_range_selfscreen(peak_power, lin(radar_antenna_gain), lin(target_rcs), ... 47 | jammer_bandwidth, lin(jammer_erp), radar_bandwidth, lin(radar_losses)); 48 | else 49 | cr = crossover_range_escort(peak_power, lin(radar_antenna_gain), lin(target_rcs), ... 50 | jammer_range, jammer_bandwidth, lin(jammer_erp), radar_bandwidth, ... 51 | lin(radar_losses), lin(radar_antenna_sidelobe)); 52 | end 53 | 54 | % Display the results 55 | plot(jammer_erp, cr) 56 | 57 | % Set the plot title and labels 58 | title('Crossover Range') 59 | xlabel('Jammer ERP (dBW)') 60 | ylabel('Crossover Range (m)') 61 | 62 | % Turn on the grid 63 | grid 64 | 65 | % Plot settings 66 | plot_settings -------------------------------------------------------------------------------- /mlradar/Chapter11/delay_line_example.m: -------------------------------------------------------------------------------- 1 | %% Delay line example 2 | % Created by: Lee A. Harrison 3 | % On: 5/28/2019 4 | % 5 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 6 | % This file is part of Introduction to Radar Using Python and MATLAB 7 | % and can not be copied and/or distributed without the express permission of Artech House. 8 | 9 | clear, clc 10 | 11 | % Set the parameters 12 | type = 'Single'; 13 | type = 'Stagger'; 14 | 15 | % PRF stagger 16 | prf_stagger = 1.25; 17 | 18 | % Normalized frequency 19 | frequency = linspace(0, 4, 1000); 20 | 21 | % Calculate the response based on the type 22 | if strcmp(type, 'Single') 23 | gain = sin(pi * frequency) .^ 2; 24 | 25 | % Display the results 26 | plot(frequency, db(gain + eps)); 27 | else 28 | gain_prf1 = sin(pi * frequency) .^ 2; 29 | gain_prf2 = sin(pi * frequency * prf_stagger) .^ 2; 30 | gain_total = 0.5 * (gain_prf1 + gain_prf2); 31 | 32 | % Display the results 33 | plot(frequency, db(gain_prf1 + eps)); hold on; 34 | plot(frequency, db(gain_prf2 + eps), 'r--'); 35 | plot(frequency, db(gain_total + eps), 'g-.'); 36 | legend('PRF1', 'PRF2', 'PRF Staggered'); 37 | end 38 | 39 | % Title and labels 40 | title('Delay Line Response'); 41 | xlabel('Normalized Frequency (f / PRF)'); 42 | ylabel('Power Gain (dB)'); 43 | 44 | % Set the y-axis limits 45 | ylim([-30 0.0]); 46 | 47 | % Turn on the grid 48 | grid on; 49 | 50 | % Plot settings 51 | plot_settings; -------------------------------------------------------------------------------- /mlradar/Chapter11/jammer_to_signal_example.m: -------------------------------------------------------------------------------- 1 | %% Jammer to signal example 2 | % Created by: Lee A. Harrison 3 | % On: 5/28/2019 4 | % 5 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 6 | % This file is part of Introduction to Radar Using Python and MATLAB 7 | % and can not be copied and/or distributed without the express permission of Artech House. 8 | 9 | clear, clc 10 | 11 | % Set the parameters 12 | 13 | % Jammer type 14 | jammer_type = 'Self Screening'; 15 | % jammer_type = 'Escort'; 16 | 17 | % Transmit power (W) 18 | peak_power = 100e3; 19 | 20 | % Antenna gain (dB) 21 | radar_antenna_gain = 20; 22 | 23 | % Antenna sidelobe level (dB) 24 | radar_antenna_sidelobe = -20; 25 | 26 | % Radar bandwidth (Hz) 27 | radar_bandwidth = 100e6; 28 | 29 | % Radar Losses (dB) 30 | radar_losses = 3; 31 | 32 | % Target range (m) 33 | target_range = linspace(1e3, 50e3, 1000); 34 | 35 | % Target RCS (dBsm) 36 | target_rcs = 3; 37 | 38 | % Jammer ERP (dBW) 39 | jammer_erp = 15; 40 | 41 | % Jammer bandwidth (Hz) 42 | jammer_bandwidth = 10e6; 43 | 44 | % Jammer range (escort) (m) 45 | jammer_range = 100e3; 46 | 47 | % Set up the input args based on jammer type 48 | if strcmp(jammer_type, 'Self Screening') 49 | jammer_range = target_range; 50 | radar_antenna_sidelobe = radar_antenna_gain; 51 | end 52 | 53 | % Calculate the jammer to signal ratio 54 | jsr = jammer_to_signal(peak_power, lin(radar_antenna_gain), lin(target_rcs), ... 55 | jammer_range, jammer_bandwidth, lin(jammer_erp), target_range, ... 56 | radar_bandwidth, lin(radar_losses), lin(radar_antenna_sidelobe)); 57 | 58 | % Display the results 59 | plot(target_range / 1e3, db(jsr)) 60 | 61 | % Set the plot title and labels 62 | title('Jammer to Signal Ratio') 63 | xlabel('Target Range (km)') 64 | ylabel('Jammer to Signal Ratio (dB)') 65 | 66 | % Turn on the grid 67 | grid 68 | 69 | % Plot settings 70 | plot_settings -------------------------------------------------------------------------------- /mlradar/libs/ambiguity/hamming.m: -------------------------------------------------------------------------------- 1 | function [coefficients] = hamming(n) 2 | %% Calculate the coefficients for a Hamming window 3 | % :param n: number of points in the window. 4 | % :return: The Hamming window coefficients. 5 | % 6 | % Created by: Lee A. Harrison 7 | % On: 4/26/2019 8 | % 9 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 10 | % This file is part of Introduction to Radar Using Python and MATLAB 11 | % and can not be copied and/or distributed without the express permission of Artech House. 12 | 13 | i = 0:(n - 1); 14 | coefficients = 0.54 - 0.46 * cos((2.0 * pi * i) / (n - 1)); -------------------------------------------------------------------------------- /mlradar/libs/ambiguity/hanning.m: -------------------------------------------------------------------------------- 1 | function [coefficients] = hanning(n) 2 | %% Calculate the coefficients for a Hanning window 3 | % :param n: number of points in the window. 4 | % :return: The Hanning window coefficients. 5 | % 6 | % Created by: Lee A. Harrison 7 | % On: 4/26/2019 8 | % 9 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 10 | % This file is part of Introduction to Radar Using Python and MATLAB 11 | % and can not be copied and/or distributed without the express permission of Artech House. 12 | 13 | i = 0:(n - 1); 14 | coefficients = 0.5 - 0.5 * cos((2.0 * pi * i) / (n - 1)); -------------------------------------------------------------------------------- /mlradar/libs/ambiguity/kaiser.m: -------------------------------------------------------------------------------- 1 | function [coefficients] = kaiser(n, alpha) 2 | %% Calculate the coefficients for a Kaiser window 3 | % :param n: number of points in the window. 4 | % :param alpha: sidelobe parameter. 5 | % :return: The Hamming window coefficients. 6 | % 7 | % Created by: Lee A. Harrison 8 | % On: 4/26/2019 9 | % 10 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 11 | % This file is part of Introduction to Radar Using Python and MATLAB 12 | % and can not be copied and/or distributed without the express permission of Artech House. 13 | 14 | i = 0:(n - 1); 15 | 16 | z1 = pi * alpha * sqrt(1.0 - (2.0 * i / (n - 1) - 1).^2); 17 | 18 | z2 = pi * alpha; 19 | 20 | coefficients = besseli(0,z1) ./ besseli(0,z2); -------------------------------------------------------------------------------- /mlradar/libs/ambiguity/lfm_pulse.m: -------------------------------------------------------------------------------- 1 | function [ ambiguity ] = lfm_pulse(time_delay, doppler_frequency, pulse_width, bandwidth) 2 | %% Calculate the ambiguity function for a linear frequency modulated single pulse. 3 | % :param time_delay: The time delay for the ambiguity function (seconds) 4 | % :param doppler_frequency: The Doppler frequency for the ambiguity function (Hz) 5 | % :param pulse_width: The waveform pulse width (seconds) 6 | % :param bandwidth: The waveform band width (Hz) 7 | % :return: The ambiguity function for an LFM pulse (unitless) 8 | % 9 | % Created by: Lee A. Harrison 10 | % On: 4/26/2019 11 | % 12 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 13 | % This file is part of Introduction to Radar Using Python and MATLAB 14 | % and can not be copied and/or distributed without the express permission of Artech House. 15 | 16 | ambiguity = abs((1.0 - abs(time_delay) / pulse_width) .* sinc(pulse_width .*... 17 | (bandwidth / pulse_width * time_delay + doppler_frequency) .* (1.0 - abs(time_delay) / pulse_width))).^2; 18 | 19 | if length(time_delay) == 1 && abs(time_delay) > pulse_width 20 | ambiguity(:) = 0; 21 | else 22 | ambiguity(abs(time_delay) > pulse_width) = 0; 23 | end 24 | -------------------------------------------------------------------------------- /mlradar/libs/ambiguity/lfm_train.m: -------------------------------------------------------------------------------- 1 | function [ ambiguity ] = lfm_train( time_delay, doppler_frequency, pulse_width, bandwidth, pulse_repetition_interval, number_of_pulses ) 2 | %% Calculate the ambiguity function for an LFM pulse train. 3 | % :param time_delay: The time delay for the ambiguity function (seconds) 4 | % :param doppler_frequency: The Doppler frequency for the ambiguity function (Hz) 5 | % :param pulse_width: The waveform pulse width (seconds) 6 | % :param bandwidth: The waveform band width (Hz) 7 | % :param pulse_repetition_interval: The time between successive pulses (seconds) 8 | % :param number_of_pulses: The total number of pulses (unitless) 9 | % :return: The ambiguity function for an LFM pulse train (unitless) 10 | % 11 | % Created by: Lee A. Harrison 12 | % On: 4/26/2019 13 | % 14 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 15 | % This file is part of Introduction to Radar Using Python and MATLAB 16 | % and can not be copied and/or distributed without the express permission of Artech House. 17 | 18 | ambiguity = 0; 19 | 20 | for q = -(number_of_pulses - 1):(number_of_pulses - 1) 21 | a1 = sqrt(lfm_pulse(time_delay - q * pulse_repetition_interval, doppler_frequency, pulse_width, bandwidth)); 22 | ambiguity = ambiguity + a1 .* abs(sin(pi * doppler_frequency * (number_of_pulses - abs(q)) * pulse_repetition_interval) ... 23 | ./ sin(pi * doppler_frequency * pulse_repetition_interval)); 24 | end 25 | 26 | ambiguity = abs(ambiguity / number_of_pulses) .^ 2; -------------------------------------------------------------------------------- /mlradar/libs/ambiguity/mls.m: -------------------------------------------------------------------------------- 1 | function [ code ] = mls( register_length, feedback_taps ) 2 | %% Generate a maximum length sequence based on the register length and feedback taps. 3 | % :param register_length: The length of the linear feedback shift register. 4 | % :param feedback_taps: The bits to use as feedback. 5 | % :return: The maximum length sequence. 6 | % 7 | % Created by: Lee A. Harrison 8 | % On: 4/27/2019 9 | % 10 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 11 | % This file is part of Introduction to Radar Using Python and MATLAB 12 | % and can not be copied and/or distributed without the express permission of Artech House. 13 | 14 | % Initialize the linear feedback shift register 15 | i = 1:register_length; 16 | register = mod(i, 2); 17 | 18 | % For the output sequence 19 | sequence_length = 2 ^ register_length - 1; 20 | sequence = zeros(sequence_length, 1); 21 | 22 | % Generate the output PRN based on the register length 23 | for i = 1:sequence_length 24 | 25 | % Calculate the feedback based on the taps and modulo 2 addition 26 | s = mod(sum(register(feedback_taps)), 2); 27 | 28 | % Shift bits to the rights 29 | for k = register_length:-1:2 30 | register(k) = register(k-1); 31 | end 32 | 33 | % Stored feedback into bit 0 34 | register(1) = s; 35 | 36 | % Append the output sequence 37 | sequence(i) = register(end); 38 | end 39 | 40 | code = sequence - (sequence == 0); -------------------------------------------------------------------------------- /mlradar/libs/ambiguity/n_phase_code.m: -------------------------------------------------------------------------------- 1 | function [ code ] = n_phase_code( n ) 2 | %% Generate an N-phase Frank code sequence. 3 | % :param n: The sequence groups. 4 | % :return: The Frank code sequence (length N^2). 5 | % 6 | % Created by: Lee A. Harrison 7 | % On: 4/26/2019 8 | % 9 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 10 | % This file is part of Introduction to Radar Using Python and MATLAB 11 | % and can not be copied and/or distributed without the express permission of Artech House. 12 | 13 | phi = zeros(n ^ 2, 1); 14 | 15 | for i = 1:n 16 | for j = 1:n 17 | phi((i - 1) * n + j) = 2.0 * pi / n * (i - 1) * (j - 1); 18 | end 19 | end 20 | 21 | code = exp(1j * phi); -------------------------------------------------------------------------------- /mlradar/libs/ambiguity/pulse_train.m: -------------------------------------------------------------------------------- 1 | function [ ambiguity ] = pulse_train( time_delay, doppler_frequency, pulse_width, pulse_repetition_interval, number_of_pulses ) 2 | %% Calculate the ambiguity function for a coherent pulse train. 3 | % :param time_delay: The time delay for the ambiguity function (seconds) 4 | % :param doppler_frequency: The Doppler frequency for the ambiguity function (Hz) 5 | % :param pulse_width: The pulse width (seconds) 6 | % :param pulse_repetition_interval: The time between successive pulses (seconds) 7 | % :param number_of_pulses: The total number of pulses (unitless) 8 | % :return: The ambiguity function for a coherent pulse train (unitless) 9 | % 10 | % Created by: Lee A. Harrison 11 | % On: 4/27/2019 12 | % 13 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 14 | % This file is part of Introduction to Radar Using Python and MATLAB 15 | % and can not be copied and/or distributed without the express permission of Artech House. 16 | 17 | ambiguity = 0; 18 | 19 | for q = -(number_of_pulses - 1):(number_of_pulses - 1) 20 | 21 | a1 = sqrt(single_pulse(time_delay - q * pulse_repetition_interval, doppler_frequency, pulse_width)); 22 | 23 | ambiguity = ambiguity + a1 .* abs(sin(pi * doppler_frequency * (number_of_pulses - abs(q)) * pulse_repetition_interval) ... 24 | ./ sin(pi * doppler_frequency * pulse_repetition_interval)); 25 | 26 | end 27 | 28 | ambiguity = abs(ambiguity./number_of_pulses).^2; -------------------------------------------------------------------------------- /mlradar/libs/ambiguity/single_pulse.m: -------------------------------------------------------------------------------- 1 | function [ ambiguity ] = single_pulse(time_delay, doppler_frequency, pulse_width) 2 | %% Calculate the ambiguity function for a continuous wave single pulse. 3 | % :param time_delay: The time delay for the ambiguity function (seconds) 4 | % :param doppler_frequency: The Doppler frequency for the ambiguity function (Hz) 5 | % :param pulse_width: The pulse width (seconds) 6 | % :return: The ambiguity function for a CW pulse (unitless) 7 | % 8 | % Created by: Lee A. Harrison 9 | % On: 4/27/2019 10 | % 11 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 12 | % This file is part of Introduction to Radar Using Python and MATLAB 13 | % and can not be copied and/or distributed without the express permission of Artech House. 14 | 15 | ambiguity = abs((1.0 - abs(time_delay / pulse_width)) .*... 16 | sinc(doppler_frequency .* (pulse_width - abs(time_delay)))).^2; 17 | 18 | if length(time_delay) == 1 && abs(time_delay) > pulse_width 19 | ambiguity(:) = 0; 20 | else 21 | ambiguity(abs(time_delay) > pulse_width) = 0; 22 | end -------------------------------------------------------------------------------- /mlradar/libs/antennas/array/tschebyscheff_coefficients.m: -------------------------------------------------------------------------------- 1 | function a = tschebyscheff_coefficients(N, sll) 2 | %% Calculate the tschebyscheff coefficients 3 | % :param N: number of points in the window. 4 | % :param sll: the desired sidelobe level (dB). 5 | % :return: The Tschebyscheff window coefficients. 6 | % 7 | % Created by: Lee A. Harrison 8 | % On: 4/26/2019 9 | % 10 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 11 | % This file is part of Introduction to Radar Using Python and MATLAB 12 | % and can not be copied and/or distributed without the express permission of Artech House. 13 | 14 | z0 = cosh( 1/(N-1) * acosh(10^(sll/20)) ); 15 | 16 | if mod(N,2) == 0 17 | 18 | M = N/2; 19 | 20 | for n = 1:M 21 | a(n) = 0; 22 | for q = n:M 23 | a(n) = a(n) + (-1)^(M-q) * z0^(2*q-1) * ( factorial(q+M-2) * (2*M - 1) )... 24 | / ( factorial(q-n)*factorial(q+n-1)*factorial(M-q) ); 25 | end 26 | end 27 | 28 | else 29 | 30 | M = (N-1)/2; 31 | 32 | for n = 1:M+1 33 | a(n) = 0; 34 | for q = n:M+1 35 | a(n) = a(n) + (-1)^(M-q+1) * z0^(2*(q-1)) * ( factorial(q+M-2) * (2*M) )... 36 | / ( factorial(q-n)*factorial(q+n-2)*factorial(M-q+1) ); 37 | end 38 | end 39 | end 40 | 41 | 42 | 43 | -------------------------------------------------------------------------------- /mlradar/libs/detection/Q.m: -------------------------------------------------------------------------------- 1 | function [ val ] = Q(x, y, eps) 2 | % Marcum's Q function algorithm by Parl. 3 | % :param x: The first argument of the Q function. 4 | % :param y: The second argument of the Q function. 5 | % :param eps: The convergence criteria. 6 | % :return: The evaluation of the Q function of (x, y, eps). 7 | % 8 | % 9 | % Created by: Lee A. Harrison 10 | % On: 10/11/2018 11 | % 12 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 13 | % This file is part of Introduction to Radar Using Python and MATLAB 14 | % and can not be copied and/or distributed without the express permission of Artech House. 15 | 16 | n = 1; 17 | 18 | alpha_n_1 = 0; 19 | d1 = y / x; 20 | 21 | if x < y 22 | alpha_n_1 = 1; 23 | d1 = x / y; 24 | end 25 | 26 | alpha_n_2 = 0.0; 27 | beta_n_1 = 0.5; 28 | beta_n_2 = 0.0; 29 | beta_n = 0.0; 30 | dn = d1; 31 | 32 | while beta_n < 1.0 / eps 33 | alpha_n = dn + 2.0 * n / (x * y) * alpha_n_1 + alpha_n_2; 34 | beta_n = 1.0 + 2.0 * n / (x * y) * beta_n_1 + beta_n_2; 35 | 36 | dn = dn * d1; 37 | 38 | alpha_n_2 = alpha_n_1; 39 | alpha_n_1 = alpha_n; 40 | 41 | beta_n_2 = beta_n_1; 42 | beta_n_1 = beta_n; 43 | 44 | n = n + 1; 45 | end 46 | 47 | if x < y 48 | val = alpha_n / (2.0 * beta_n) * exp(-(x - y) ^ 2 / 2.0); 49 | else 50 | val = 1.0 - (alpha_n / (2.0 * beta_n) * exp(-(x - y) ^ 2 / 2.0)); 51 | end 52 | 53 | end 54 | 55 | -------------------------------------------------------------------------------- /mlradar/libs/detection/binary_integration.m: -------------------------------------------------------------------------------- 1 | function [ pd_binary, pfa_binary ] = binary_integration( m, n, pd, pfa ) 2 | % Calculate the probability of detection for M of N integration. 3 | % Calcualte the probability of false alarm for M of N integration. 4 | % :param m: The number of required detections. 5 | % :param n: The total number of measurements. 6 | % :param pd: The probability of detection for a single measurement. 7 | % :return: The probability of M on N detections. 8 | % :return: The probability false alarm for M on N detections. 9 | % 10 | % Created by: Lee A. Harrison 11 | % On: 10/11/2018 12 | % 13 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 14 | % This file is part of Introduction to Radar Using Python and MATLAB 15 | % and can not be copied and/or distributed without the express permission of Artech House. 16 | 17 | pd_binary = 0; 18 | pfa_binary = 0; 19 | 20 | for k = m:n 21 | pd_binary = pd_binary + nchoosek(n, k) * pd ^ k * (1.0 - pd) ^ (n - k); 22 | pfa_binary = pfa_binary + nchoosek(n, k) * pfa ^ k * (1.0 - pfa) ^ (n - k); 23 | end 24 | 25 | end 26 | 27 | -------------------------------------------------------------------------------- /mlradar/libs/detection/coherent_integration.m: -------------------------------------------------------------------------------- 1 | function [ pd ] = coherent_integration(signal_to_noise, number_of_pulses, probability_of_false_alarm, swerling_type) 2 | % Calculate the probability of detection using coherent integration. 3 | % :param signal_to_noise: The signal to noise ratio. 4 | % :param number_of_pulses: The number of pulses to be coherently integrated. 5 | % :param probability_of_false_alarm: The probability of false alarm. 6 | % :param swerling_type: The Swerling target type (0, 1, or 3). 7 | % :return: The probability of detection. 8 | 9 | % Created by: Lee A. Harrison 10 | % On: 10/11/2018 11 | % 12 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 13 | % This file is part of Introduction to Radar Using Python and MATLAB 14 | % and can not be copied and/or distributed without the express permission of Artech House. 15 | 16 | pd = zeros(1, numel(signal_to_noise)); 17 | 18 | % Calculate the probability of detection based on the Swerling type 19 | if strcmp(swerling_type, 'Swerling 0') 20 | for i = 1:numel(signal_to_noise) 21 | pd(i) = Q(sqrt(2.0 * number_of_pulses * signal_to_noise(i)), sqrt(-2.0 * log(probability_of_false_alarm)), 1e-6); 22 | end 23 | elseif strcmp(swerling_type, 'Swerling 1') 24 | for i = 1:numel(signal_to_noise) 25 | pd(i) = exp(log(probability_of_false_alarm) / (number_of_pulses * signal_to_noise(i) + 1.0)); 26 | end 27 | elseif strcmp(swerling_type, 'Swerling 3') 28 | for i = 1:numel(signal_to_noise) 29 | pd(i) = (1.0 - (2.0 * number_of_pulses * log(probability_of_false_alarm)) / ... 30 | (2.0 + number_of_pulses * signal_to_noise(i)) ^ 2) * exp((2.0 * log(probability_of_false_alarm)) / ... 31 | (2.0 + number_of_pulses * signal_to_noise(i))); 32 | end 33 | end 34 | 35 | 36 | end 37 | 38 | -------------------------------------------------------------------------------- /mlradar/libs/detection/pd_gaussian.m: -------------------------------------------------------------------------------- 1 | function [ pd ] = pd_gaussian(signal_to_noise, probability_false_alarm) 2 | % Calculate the probability of detection for a given signal to noise ratio and probability of false alarm 3 | % when the noise is Gaussian (non-coherent detection). 4 | % :param signal_to_noise: The signal to noise ratio. 5 | % :param probability_false_alarm: The probability of false alarm. 6 | % :return: The probability of detection. 7 | 8 | % Created by: Lee A. Harrison 9 | % On: 10/11/2018 10 | % 11 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 12 | % This file is part of Introduction to Radar Using Python and MATLAB 13 | % and can not be copied and/or distributed without the express permission of Artech House. 14 | 15 | % Calculate the voltage threshold 16 | voltage_threshold = erfinv(1.0 - 2.0 * probability_false_alarm) * sqrt(2.0); 17 | 18 | % Calculate the signal amplitude based on signal to noise ratio 19 | amplitude = sqrt(2.0 * signal_to_noise); 20 | 21 | % Calculate the probability of detection 22 | pd = 0.5 * (1.0 - erf((voltage_threshold - amplitude) / sqrt(2.0))); 23 | 24 | 25 | end 26 | 27 | -------------------------------------------------------------------------------- /mlradar/libs/detection/pd_rayleigh.m: -------------------------------------------------------------------------------- 1 | function [ pd ] = pd_rayleigh(signal_to_noise, probability_false_alarm) 2 | % Calculate the probability of detection for a given signal to noise ratio and probability of false alarm 3 | % when the noise is Rayleigh (coherent detection). 4 | % :param signal_to_noise: The signal to noise ratio. 5 | % :param probability_false_alarm: The probability of false alarm. 6 | % :return: The probability of detection. 7 | % 8 | % Created by: Lee A. Harrison 9 | % On: 10/11/2018 10 | % 11 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 12 | % This file is part of Introduction to Radar Using Python and MATLAB 13 | % and can not be copied and/or distributed without the express permission of Artech House. 14 | 15 | pd = zeros(1, length(signal_to_noise)); 16 | 17 | % Calculate the probability of detection 18 | for i = 1:length(signal_to_noise) 19 | pd(i) = Q(sqrt(2.0 * signal_to_noise(i)), sqrt(-2.0 * log(probability_false_alarm)), 1e-6); 20 | end 21 | 22 | end 23 | 24 | -------------------------------------------------------------------------------- /mlradar/libs/detection/single_pulse_snr.m: -------------------------------------------------------------------------------- 1 | function [ signal_to_noise ] = single_pulse_snr(probability_of_detection, probability_of_false_alarm) 2 | % Calculate the required signal to noise ratio given a probability of detection and probability of false alarm. 3 | % :param probability_of_detection: The probability of detection. 4 | % :param probability_of_false_alarm: The probability of false alarm. 5 | % :return: The required signal to noise ratio. 6 | % 7 | % Created by: Lee A. Harrison 8 | % On: 10/11/2018 9 | % 10 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 11 | % This file is part of Introduction to Radar Using Python and MATLAB 12 | % and can not be copied and/or distributed without the express permission of Artech House. 13 | 14 | 15 | % Starting values 16 | signal_to_noise = 1.0; 17 | delta = 100.0; 18 | 19 | % Loop until required SNR is found 20 | while 1 21 | if probability_of_detection > pd_rayleigh(signal_to_noise, probability_of_false_alarm); 22 | signal_to_noise = signal_to_noise + delta; 23 | else 24 | signal_to_noise = signal_to_noise - delta; 25 | end 26 | 27 | delta = 0.5 * delta; 28 | 29 | if abs(probability_of_detection - pd_rayleigh(signal_to_noise, probability_of_false_alarm)) < 1e-6 30 | break 31 | end 32 | end 33 | 34 | 35 | end -------------------------------------------------------------------------------- /mlradar/libs/detection/single_pulse_snr_swerling.m: -------------------------------------------------------------------------------- 1 | function [ signal_to_noise ] = single_pulse_snr_swerling(pd, pfa, number_of_pulses, swerling_type) 2 | % Compute the required signal to noise ratio given a probability of detection and probability of false alarm. 3 | % :param pd: The probability of detection. 4 | % :param pfa: The probability of false alarm. 5 | % :param number_of_pulses: The number of pulses to be integrated. 6 | % :param swerling_type: The Swerling model type. 7 | % :return: The required signal to noise ratio. 8 | 9 | % Created by: Lee A. Harrison 10 | % On: 10/11/2018 11 | % 12 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 13 | % This file is part of Introduction to Radar Using Python and MATLAB 14 | % and can not be copied and/or distributed without the express permission of Artech House. 15 | 16 | signal_to_noise = 1.0; 17 | delta = 1000.0; 18 | 19 | while 1 20 | if pd > non_coherent_integration(signal_to_noise, pfa, number_of_pulses, swerling_type); 21 | signal_to_noise = signal_to_noise + delta; 22 | else 23 | signal_to_noise = signal_to_noise - delta; 24 | end 25 | 26 | if signal_to_noise < 0.0 27 | signal_to_noise = 1e-6; 28 | end 29 | 30 | delta = 0.5 * delta; 31 | 32 | if abs(pd - non_coherent_integration(signal_to_noise, pfa, number_of_pulses, swerling_type)) < 1e-6 33 | break; 34 | end 35 | end 36 | 37 | end 38 | 39 | -------------------------------------------------------------------------------- /mlradar/libs/detection/snr_gain.m: -------------------------------------------------------------------------------- 1 | function [ snr ] = snr_gain(probability_of_detection, probability_of_false_alarm, number_of_pulses, signal_to_noise_nci) 2 | % Calculate the required single pulse signal to noise for non-coherent integration (gain method Peebles). 3 | % :param probability_of_detection: The probability of detection. 4 | % :param probability_of_false_alarm: The probability of false alarm. 5 | % :param number_of_pulses: The number of pulses to be non-coherently integrated. 6 | % :param signal_to_noise_nci: The signal to noise ratio for non-coherent integration. 7 | % :return: The requried single pulse signal to noise ratio. 8 | % 9 | % Created by: Lee A. Harrison 10 | % On: 10/11/2018 11 | % 12 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 13 | % This file is part of Introduction to Radar Using Python and MATLAB 14 | % and can not be copied and/or distributed without the express permission of Artech House. 15 | 16 | gain = 6.79 * (1.0 + 0.235 * probability_of_detection) * (1.0 + log10(1.0/probability_of_false_alarm) / 46.6)... 17 | .* log10(number_of_pulses) .* (1.0 - 0.14 * log10(number_of_pulses) + 0.01831 * log10(number_of_pulses) .^ 2); 18 | 19 | snr = 10.0 * log10(signal_to_noise_nci) - gain; 20 | 21 | end 22 | 23 | -------------------------------------------------------------------------------- /mlradar/libs/detection/snr_reduction.m: -------------------------------------------------------------------------------- 1 | function [ snr ] = snr_reduction(number_of_pulses, signal_to_noise_nci) 2 | % Calculate the required single pulse signal to noise for non-coherent integration (loss method Curry). 3 | % :param number_of_pulses: The number of pulses to be non-coherently integrated. 4 | % :param signal_to_noise_nci: The signal to noise ratio for non-coherent integration. 5 | % :return: The required single pulse signal to noise ratio. 6 | % 7 | % Created by: Lee A. Harrison 8 | % On: 10/11/2018 9 | % 10 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 11 | % This file is part of Introduction to Radar Using Python and MATLAB 12 | % and can not be copied and/or distributed without the express permission of Artech House. 13 | 14 | snr = 10.0 * log10(signal_to_noise_nci ./ (2.0 * number_of_pulses) + ... 15 | sqrt(signal_to_noise_nci .^ 2 ./ (4.0 * number_of_pulses .^ 2) + signal_to_noise_nci ./ number_of_pulses)); 16 | 17 | end 18 | 19 | -------------------------------------------------------------------------------- /mlradar/libs/ecm/burn_through_range_escort.m: -------------------------------------------------------------------------------- 1 | function br = burn_through_range_escort(peak_power, antenna_gain, target_rcs, radar_bandwidth, losses, jammer_range,... 2 | jammer_to_signal_req, effective_radiated_power, jammer_bandwidth, antenna_gain_jammer_direction) 3 | %% Calculate the burn through range for escort jamming. 4 | % :param peak_power: The peak transmitted power of the radar (W). 5 | % :param antenna_gain: The gain of the radar antenna. 6 | % :param target_rcs: The target radar cross section (m^2). 7 | % :param radar_bandwidth: The radar receiver bandwidth (Hz). 8 | % :param jammer_bandwidth: The jammer's transmitting bandwith (Hz). 9 | % :param effective_radiated_power: The jammer's effective radiated power (W). 10 | % :param losses: The radar losses. 11 | % :param effective_radiated_power: The jammer's effective radiated power (W). 12 | % :param jammer_to_signal_req: The jammer to signal ratio required to perform a specific radar function. 13 | % :param jammer_range: The range from the radar to the jammer (m). 14 | % :param antenna_gain_jammer_direction: The gain of the radar antenna in the direction of the jammer. 15 | % :return: The burn through range (m). 16 | % 17 | % Created by: Lee A. Harrison 18 | % On: 5/25/2019 19 | % 20 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 21 | % This file is part of Introduction to Radar Using Python and MATLAB 22 | % and can not be copied and/or distributed without the express permission of Artech House. 23 | 24 | % Check the bandwidth 25 | if jammer_bandwidth > radar_bandwidth 26 | jammer_bandwidth = radar_bandwidth; 27 | end 28 | 29 | % Calculate the burn through range 30 | br = (jammer_to_signal_req * (peak_power * antenna_gain .^ 2 * target_rcs * jammer_range .^ 2 * jammer_bandwidth)./... 31 | (effective_radiated_power * antenna_gain_jammer_direction * 4.0 * pi * radar_bandwidth * losses)) .^ 0.25; 32 | -------------------------------------------------------------------------------- /mlradar/libs/ecm/burn_through_range_selfscreen.m: -------------------------------------------------------------------------------- 1 | function br = burn_through_range_selfscreen(peak_power, antenna_gain, target_rcs,... 2 | radar_bandwidth, losses, jammer_to_signal_req, effective_radiated_power, jammer_bandwidth) 3 | %% Calculate the burn through range for a self screening jammer. 4 | % :param peak_power: The peak transmitted power of the radar (W). 5 | % :param antenna_gain: The gain of the radar antenna. 6 | % :param target_rcs: The target radar cross section (m^2). 7 | % :param radar_bandwidth: The radar receiver bandwidth (Hz). 8 | % :param jammer_bandwidth: The jammer's transmitting bandwith (Hz). 9 | % :param effective_radiated_power: The jammer's effective radiated power (W). 10 | % :param losses: The radar losses. 11 | % :param effective_radiated_power: The jammer's effective radiated power (W). 12 | % :param jammer_to_signal_req: The jammer to signal required to perform a specific radar function. 13 | % :return: The burn through range (m). 14 | % 15 | % Created by: Lee A. Harrison 16 | % On: 5/25/2019 17 | % 18 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 19 | % This file is part of Introduction to Radar Using Python and MATLAB 20 | % and can not be copied and/or distributed without the express permission of Artech House. 21 | 22 | % Check the bandwidth 23 | if jammer_bandwidth > radar_bandwidth 24 | jammer_bandwidth = radar_bandwidth; 25 | end 26 | 27 | % Calculate the burn through range 28 | br = sqrt(jammer_to_signal_req * (peak_power * antenna_gain * target_rcs * jammer_bandwidth) ./... 29 | (effective_radiated_power * 4.0 * pi * radar_bandwidth * losses)); 30 | -------------------------------------------------------------------------------- /mlradar/libs/ecm/crossover_range_escort.m: -------------------------------------------------------------------------------- 1 | function cr = crossover_range_escort(peak_power, antenna_gain, target_rcs, jammer_range, jammer_bandwidth,... 2 | effective_radiated_power, radar_bandwidth, losses, antenna_gain_jammer_direction) 3 | %% Calculate the crossover range for escort jamming. 4 | % :param peak_power: The peak transmitted power of the radar (W). 5 | % :param antenna_gain: The gain of the radar antenna. 6 | % :param target_rcs: The target radar cross section (m^2). 7 | % :param jammer_range: The range from the radar to the jammer (m). 8 | % :param jammer_bandwidth: The jammer's transmitting bandwith (Hz). 9 | % :param effective_radiated_power: The jammer's effective radiated power (W). 10 | % :param radar_bandwidth: The radar receiver bandwidth (Hz). 11 | % :param losses: The radar losses. 12 | % :param antenna_gain_jammer_direction: The gain of the radar antenna in the direction of the jammer. 13 | % :return: The crossover range (m). 14 | % 15 | % Created by: Lee A. Harrison 16 | % On: 5/25/2019 17 | % 18 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 19 | % This file is part of Introduction to Radar Using Python and MATLAB 20 | % and can not be copied and/or distributed without the express permission of Artech House. 21 | 22 | % Check the bandwidth 23 | if jammer_bandwidth > radar_bandwidth 24 | jammer_bandwidth = radar_bandwidth; 25 | end 26 | 27 | cr = ((peak_power * antenna_gain .^ 2 * target_rcs * jammer_bandwidth * jammer_range .^ 2) ./ ... 28 | (effective_radiated_power * 4.0 * pi * radar_bandwidth * losses * antenna_gain_jammer_direction)) .^ 0.25; 29 | 30 | -------------------------------------------------------------------------------- /mlradar/libs/ecm/crossover_range_selfscreen.m: -------------------------------------------------------------------------------- 1 | function cr = crossover_range_selfscreen(peak_power, antenna_gain, ... 2 | target_rcs, jammer_bandwidth, effective_radiated_power, radar_bandwidth, losses) 3 | %% Calculate the crossover range for a self screening jammer. 4 | % :param peak_power: The peak transmitted power of the radar (W). 5 | % :param antenna_gain: The gain of the radar antenna. 6 | % :param target_rcs: The target radar cross section (m^2). 7 | % :param jammer_bandwidth: The jammer's transmitting bandwith (Hz). 8 | % :param effective_radiated_power: The jammer's effective radiated power (W). 9 | % :param radar_bandwidth: The radar receiver bandwidth (Hz). 10 | % :param losses: The radar losses. 11 | % :return: The crossover range (m). 12 | % 13 | % Created by: Lee A. Harrison 14 | % On: 5/25/2019 15 | % 16 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 17 | % This file is part of Introduction to Radar Using Python and MATLAB 18 | % and can not be copied and/or distributed without the express permission of Artech House. 19 | 20 | % Check the bandwidth 21 | if jammer_bandwidth > radar_bandwidth 22 | jammer_bandwidth = radar_bandwidth; 23 | end 24 | 25 | % Calculate the crossover range 26 | cr = sqrt((peak_power * antenna_gain * target_rcs * jammer_bandwidth) ./... 27 | (effective_radiated_power * 4.0 * pi * radar_bandwidth * losses)); 28 | -------------------------------------------------------------------------------- /mlradar/libs/ecm/jammer_to_signal.m: -------------------------------------------------------------------------------- 1 | function [ js ] = jammer_to_signal(peak_power, antenna_gain, target_rcs, ... 2 | jammer_range, jammer_bandwidth, jammer_erp, target_range, ... 3 | radar_bandwidth, losses, antenna_gain_jammer_direction) 4 | %% Calculate the jammer to signal ratio. 5 | % :param peak_power: The peak transmitted power of the radar (W). 6 | % :param antenna_gain: The gain of the radar antenna. 7 | % :param target_rcs: The target radar cross section (m^2). 8 | % :param jammer_range: The range from the radar to the jammer (m). 9 | % :param jammer_bandwidth: The jammer's transmitting bandwith (Hz). 10 | % :param jammer_erp: The jammer's effective radiated power (W). 11 | % :param target_range: The range to the target (m). 12 | % :param radar_bandwidth: The radar receiver bandwidth (Hz). 13 | % :param losses: The radar losses. 14 | % :param antenna_gain_jammer_direction: The gain of the radar antenna in the direction of the jammer. 15 | % :return: The signal to jammer ratio. 16 | % 17 | % Created by: Lee A. Harrison 18 | % On: 5/25/2019 19 | % 20 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 21 | % This file is part of Introduction to Radar Using Python and MATLAB 22 | % and can not be copied and/or distributed without the express permission of Artech House. 23 | 24 | % Check the bandwidth 25 | if jammer_bandwidth > radar_bandwidth 26 | jammer_bandwidth = radar_bandwidth; 27 | end 28 | 29 | js = (jammer_erp * 4.0 * pi * target_range .^ 4 * radar_bandwidth * losses ... 30 | * antenna_gain_jammer_direction)./ (peak_power * antenna_gain .^ 2 * ... 31 | target_rcs * jammer_bandwidth * jammer_range .^ 2); -------------------------------------------------------------------------------- /mlradar/libs/radar_range/bistatic_equation/power_at_radar_bistatic.m: -------------------------------------------------------------------------------- 1 | function pr = power_at_radar_bistatic(peak_power, transmit_antenna_gain, receive_antenna_gain, transmit_target_range, receive_target_range, frequency, bistatic_target_rcs) 2 | %% Calculate the power at the radar for bistatic configurations. 3 | % :param peak_power: The peak transmitted power (W). 4 | % :param transmit_antenna_gain: The gain of the transmitting antenna. 5 | % :param receive_antenna_gain: The gain of the receiving antenna. 6 | % :param transmit_target_range: The range from the transmitting radar to the target (m). 7 | % :param receive_target_range: The range from the receiving radar to the target (m). 8 | % :param frequency: The operating frequency (Hz). 9 | % :param bistatic_target_rcs: The target bistatic radar cross section (m^2). 10 | % :return: The power at the radar for the bistatic case (W). 11 | % 12 | % Created by: Lee A. Harrison 13 | % On: 6/21/2018 14 | % 15 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 16 | % This file is part of Introduction to Radar Using Python and MATLAB 17 | % and can not be copied and/or distributed without the express permission of Artech House. 18 | 19 | % Speed of light 20 | c = 299792458; 21 | 22 | % Calculate the wavelength 23 | wavelength = c / frequency; 24 | 25 | % Calculate the power at the radar 26 | pr = (peak_power * transmit_antenna_gain * receive_antenna_gain * bistatic_target_rcs * wavelength .^ 2) ./ ... 27 | ((4.0 * pi) ^ 3 * transmit_target_range .^ 2 * receive_target_range .^ 2); -------------------------------------------------------------------------------- /mlradar/libs/radar_range/hertzian_dipole/directivity.m: -------------------------------------------------------------------------------- 1 | function D = directivity(relative_permittivity, relative_permeability, frequency, current, length, theta) 2 | %% Calculate the directivity for the Hertzian dipole. 3 | % :param relative_permittivity: The relative permittivity. 4 | % :param relative_permeability: The relative permeability. 5 | % :param frequency: The operating frequency (Hz). 6 | % :param current: The current on the dipole (A). 7 | % :param length: The length of the dipole (m). 8 | % :param theta: The angle to the field point (radians). 9 | % :return: THe directivity of the Hertzian dipole. 10 | % 11 | % Created by: Lee A. Harrison 12 | % On: 6/21/2018 13 | % 14 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 15 | % This file is part of Introduction to Radar Using Python and MATLAB 16 | % and can not be copied and/or distributed without the express permission of Artech House. 17 | 18 | % Get the total radiated power 19 | power_radiated = total_radiated_power(relative_permittivity, relative_permeability, frequency, current, length); 20 | 21 | % Calculate the direc 22 | D = 4.0 * pi * radiation_intensity(relative_permittivity, relative_permeability,... 23 | frequency, current, length, theta) / power_radiated; 24 | 25 | end -------------------------------------------------------------------------------- /mlradar/libs/radar_range/hertzian_dipole/electric_field.m: -------------------------------------------------------------------------------- 1 | function E = electric_field( relative_permittivity, relative_permeability, frequency, current, element_length, r, theta ) 2 | %% Calculate the electric far field for the Hertzian dipole. 3 | % :param relative_permittivity: The relative permittivity. 4 | % :param relative_permeability: The relative permeability. 5 | % :param frequency: The operating frequency (Hz). 6 | % :param current: The current on the dipole (A). 7 | % :param element_length: The element_length of the dipole (m). 8 | % :param r: The range to the field point (m). 9 | % :param theta: The angle to the field point (radians). 10 | % :return: The electric far field for the Hertzian dipole (theta-hat) (V/m). 11 | % 12 | % Created by: Lee A. Harrison 13 | % On: 6/21/2018 14 | % 15 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 16 | % This file is part of Introduction to Radar Using Python and MATLAB 17 | % and can not be copied and/or distributed without the express permission of Artech House. 18 | 19 | % Permeability and permittivity 20 | mu_0 = 4 * pi * 1e-7; 21 | epsilon_0 = 8.854187817620389e-12; 22 | 23 | % The speed of light 24 | c = 299792458; 25 | 26 | % Calculate the angular frequency and material parameters 27 | omega = 2.0 * pi * frequency; 28 | mu = relative_permeability * mu_0; 29 | epsilon = relative_permittivity * epsilon_0; 30 | 31 | % Calculate the wavenumber 32 | k = omega / c; 33 | 34 | % Calculate the impedance 35 | eta = sqrt(mu / epsilon); 36 | 37 | % Calculate the electric field 38 | E = 1j * eta * k * current * element_length * exp(-1j * k * r) * sin(theta) ./ (4.0 * pi * r); 39 | 40 | end -------------------------------------------------------------------------------- /mlradar/libs/radar_range/hertzian_dipole/magnetic_field.m: -------------------------------------------------------------------------------- 1 | function H = magnetic_field(frequency, current, element_length, r, theta) 2 | %% Calculate the electric far field for the Hertzian dipole. 3 | % :param frequency: The operating frequency (Hz). 4 | % :param current: The current on the dipole (A). 5 | % :param element_length: The element_length of the dipole (m). 6 | % :param r: The range to the field point (m). 7 | % :param theta: The angle to the field point (radians). 8 | % 9 | % Created by: Lee A. Harrison 10 | % On: 6/21/2018 11 | % 12 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 13 | % This file is part of Introduction to Radar Using Python and MATLAB 14 | % and can not be copied and/or distributed without the express permission of Artech House. 15 | 16 | % The speed of light 17 | c = 299792458; 18 | 19 | % Calculate the angular frequency and material parameters 20 | omega = 2.0 * pi * frequency; 21 | 22 | % Calculate the wavenumber 23 | k = omega / c; 24 | 25 | % Calculate the magnetic field 26 | H = 1j * k * current * element_length * exp(-1j * k * r) * sin(theta) ./ (4.0 * pi * r); 27 | 28 | 29 | end 30 | 31 | -------------------------------------------------------------------------------- /mlradar/libs/radar_range/hertzian_dipole/power_density.m: -------------------------------------------------------------------------------- 1 | function pd = power_density(relative_permittivity, relative_permeability, frequency, current, element_length, r, theta) 2 | %% Calculate the power density radiated by the Hertzian dipole. 3 | % :param relative_permittivity: The relative permittivity. 4 | % :param relative_permeability: The relative permeability. 5 | % :param frequency: The operating frequency (Hz). 6 | % :param current: The current on the dipole (A). 7 | % :param element_length: The element_length of the dipole (m). 8 | % :param r: The range to the field point (m). 9 | % :param theta: The angle to the field point (radians). 10 | % :return: The power density radiated by the Hertzian dipole (W/m^2). 11 | % 12 | % Created by: Lee A. Harrison 13 | % On: 6/21/2018 14 | % 15 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 16 | % This file is part of Introduction to Radar Using Python and MATLAB 17 | % and can not be copied and/or distributed without the express permission of Artech House. 18 | 19 | % Permeability and permittivity 20 | mu_0 = 4 * pi * 1e-7; 21 | epsilon_0 = 8.854187817620389e-12; 22 | 23 | % The speed of light 24 | c = 299792458; 25 | 26 | % Calculate the angular frequency and material parameters 27 | omega = 2.0 * pi * frequency; 28 | mu = relative_permeability * mu_0; 29 | epsilon = relative_permittivity * epsilon_0; 30 | 31 | % Calculate the wavenumber 32 | k = omega / c; 33 | 34 | % Calculate the impedance 35 | eta = sqrt(mu / epsilon); 36 | 37 | pd = 0.5 * eta * (k * current * element_length * sin(theta) ./ (4.0 * pi * r)) .^ 2; 38 | 39 | 40 | end 41 | 42 | -------------------------------------------------------------------------------- /mlradar/libs/radar_range/hertzian_dipole/radiation_intensity.m: -------------------------------------------------------------------------------- 1 | function U = radiation_intensity(relative_permittivity, relative_permeability, frequency, current, element_length, theta) 2 | %% Calculate the radiation intensity for the Hertzian dipole. 3 | % :param relative_permittivity: The relative permittivity. 4 | % :param relative_permeability: The relative permeability. 5 | % :param frequency: The operating frequency (Hz). 6 | % :param current: The current on the dipole (A). 7 | % :param element_length: The element_length of the dipole (m). 8 | % :param theta: The angle to the field point (radians). 9 | % :return: The radiation intensity for the Hertzian dipole (W/steradian). 10 | % 11 | % Created by: Lee A. Harrison 12 | % On: 6/21/2018 13 | % 14 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 15 | % This file is part of Introduction to Radar Using Python and MATLAB 16 | % and can not be copied and/or distributed without the express permission of Artech House. 17 | 18 | % Permeability and permittivity 19 | mu_0 = 4 * pi * 1e-7; 20 | epsilon_0 = 8.854187817620389e-12; 21 | 22 | % The speed of light 23 | c = 299792458; 24 | 25 | % Calculate the angular frequency and material parameters 26 | omega = 2.0 * pi * frequency; 27 | mu = relative_permeability * mu_0; 28 | epsilon = relative_permittivity * epsilon_0; 29 | 30 | % Calculate the wavenumber 31 | k = omega / c; 32 | 33 | % Calculate the impedance 34 | eta = sqrt(mu / epsilon); 35 | 36 | % Calculate the radiation intensity 37 | U = 0.5 * eta * (k * current * element_length * sin(theta) ./ (4.0 * pi)) .^ 2; 38 | 39 | 40 | end 41 | 42 | -------------------------------------------------------------------------------- /mlradar/libs/radar_range/hertzian_dipole/total_radiated_power.m: -------------------------------------------------------------------------------- 1 | function total_power = total_radiated_power(relative_permittivity, relative_permeability, frequency, current, element_length) 2 | %% Calculate the total power radiated by the Hertzian dipole. 3 | % :param relative_permittivity: The relative permittivity. 4 | % :param relative_permeability: The relative permeability. 5 | % :param frequency: The operating frequency (Hz). 6 | % :param current: The current on the dipole (A). 7 | % :param element_length: The element_length of the dipole (m). 8 | % :return: The total power radiated byt the Hertzian dipole (W). 9 | % 10 | % Created by: Lee A. Harrison 11 | % On: 6/21/2018 12 | % 13 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 14 | % This file is part of Introduction to Radar Using Python and MATLAB 15 | % and can not be copied and/or distributed without the express permission of Artech House. 16 | 17 | % Permeability and permittivity 18 | mu_0 = 4 * pi * 1e-7; 19 | epsilon_0 = 8.854187817620389e-12; 20 | 21 | % The speed of light 22 | c = 299792458; 23 | 24 | % Calculate the material parameters 25 | mu = relative_permeability * mu_0; 26 | epsilon = relative_permittivity * epsilon_0; 27 | 28 | % Calculate the wavelength 29 | wavelength = c / frequency; 30 | 31 | % Calculate the impedance 32 | eta = sqrt(mu / epsilon); 33 | 34 | % Calculate the total power radiated 35 | total_power = eta * pi / 3.0 * (current * element_length / wavelength) ^ 2; 36 | 37 | end 38 | 39 | -------------------------------------------------------------------------------- /mlradar/libs/radar_range/range_equation/loop_gain.m: -------------------------------------------------------------------------------- 1 | function lg = loop_gain(reference_range, reference_rcs, reference_snr) 2 | %% Calculate the loop gain given the reference range information. 3 | % :param reference_range: Reference range for the radar (m). 4 | % :param reference_rcs: Reference radar cross section for the radar (m^2). 5 | % :param reference_snr: Reference signal to noise ratio for the radar. 6 | % :return: The loop gain for the radar. 7 | % 8 | % Created by: Lee A. Harrison 9 | % On: 6/21/2018 10 | % 11 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 12 | % This file is part of Introduction to Radar Using Python and MATLAB 13 | % and can not be copied and/or distributed without the express permission of Artech House. 14 | 15 | % Calculate the loop gain 16 | lg = reference_range .^ 4 * reference_snr ./ reference_rcs; -------------------------------------------------------------------------------- /mlradar/libs/radar_range/range_equation/maximum_range.m: -------------------------------------------------------------------------------- 1 | function r_max = maximum_range(system_temperature, bandwidth, noise_factor, losses, signal_to_noise, peak_power, antenna_gain, frequency, target_rcs) 2 | %% Calculate the maximum range that the radar can detect the target. 3 | % :param system_temperature: The system temperature (K). 4 | % :param bandwidth: The operating bandwidth (Hz). 5 | % :param noise_factor: The receiver noise factor. 6 | % :param losses: The system losses. 7 | % :param signal_to_noise: The operating signal to noise ratio. 8 | % :param peak_power: The peak transmitted power (W). 9 | % :param antenna_gain: The gain of the transmitting antenna. 10 | % :param frequency: The operating frequency (Hz). 11 | % :param target_rcs: The target radar cross section (m^2). 12 | % :return: The maximum range at which a target can be detected (m). 13 | % 14 | % Created by: Lee A. Harrison 15 | % On: 6/21/2018 16 | % 17 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 18 | % This file is part of Introduction to Radar Using Python and MATLAB 19 | % and can not be copied and/or distributed without the express permission of Artech House. 20 | 21 | % First, calculate the minimum detectable signal 22 | min_signal = minimum_detectable_signal(system_temperature, bandwidth, noise_factor, losses, signal_to_noise); 23 | 24 | % Calculate the maximum detection range 25 | r_max = ((peak_power * antenna_gain ^ 2 * (299792458 / frequency) ^ 2 * target_rcs) ./ ((4.0 * pi) ^ 3 * min_signal)) .^ 0.25; -------------------------------------------------------------------------------- /mlradar/libs/radar_range/range_equation/minimum_detectable_signal.m: -------------------------------------------------------------------------------- 1 | function p_min = minimum_detectable_signal(system_temperature, bandwidth, noise_factor, losses, signal_to_noise) 2 | %% Calculate the minimum detectable signal based upon the SNR at the output of the receiver. 3 | % :param system_temperature: The system temperature (K). 4 | % :param bandwidth: The operating bandwidth (Hz). 5 | % :param noise_factor: The receiver noise factor. 6 | % :param losses: The system losses. 7 | % :param signal_to_noise: The minimum output signal to noise ratio. 8 | % :return: The minimum detectable signal (W). 9 | % 10 | % Created by: Lee A. Harrison 11 | % On: 6/21/2018 12 | % 13 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 14 | % This file is part of Introduction to Radar Using Python and MATLAB 15 | % and can not be copied and/or distributed without the express permission of Artech House. 16 | 17 | % Boltzmann's constant 18 | k = 1.38064852e-23; 19 | 20 | % Calculate the minimum detectable signal 21 | p_min = k * system_temperature * bandwidth * noise_factor * losses * signal_to_noise; -------------------------------------------------------------------------------- /mlradar/libs/radar_range/range_equation/output_snr.m: -------------------------------------------------------------------------------- 1 | function snr = output_snr(system_temperature, bandwidth, noise_factor, losses, peak_power, antenna_gain, frequency, target_rcs, target_range) 2 | %% Calculate the signal to noise ratio at the output of the receiver. 3 | % :param system_temperature: The system temperature (K). 4 | % :param bandwidth: The operating bandwidth (Hz). 5 | % :param noise_factor: The receiver noise factor. 6 | % :param losses: The system losses. 7 | % :param peak_power: The peak transmitted power (W). 8 | % :param antenna_gain: The gain of the transmitting antenna. 9 | % :param frequency: The operating frequency (Hz). 10 | % :param target_rcs: The target radar cross section (m^2). 11 | % :param target_range: The target distance from the transmitting antenna (m). 12 | % :return: The signal to noise ratio at the output of the receiver. 13 | % 14 | % Created by: Lee A. Harrison 15 | % On: 6/21/2018 16 | % 17 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 18 | % This file is part of Introduction to Radar Using Python and MATLAB 19 | % and can not be copied and/or distributed without the express permission of Artech House. 20 | 21 | % Speed of light 22 | c = 299792458; 23 | 24 | % Boltzmann's constant 25 | k = 1.38064852e-23; 26 | 27 | % Calculate the output signal to noise ratio 28 | snr = (peak_power * antenna_gain ^ 2 * (c / frequency) ^ 2 * target_rcs) ./ ... 29 | ((4.0 * pi) ^ 3 * k * system_temperature * bandwidth * noise_factor * losses * target_range .^ 4); -------------------------------------------------------------------------------- /mlradar/libs/radar_range/range_equation/power_at_radar.m: -------------------------------------------------------------------------------- 1 | function pr = power_at_radar(peak_power, antenna_gain, target_range, frequency, target_rcs) 2 | %% Calculate the power at the radar. 3 | % :param peak_power: The peak transmitted power (W). 4 | % :param antenna_gain: The gain of the transmitting antenna. 5 | % :param target_range: The target distance from the transmitting antenna (m). 6 | % :param frequency: The operating frequency (Hz). 7 | % :param target_rcs: The target radar cross section (m^2). 8 | % :return: The power at the radar (W). 9 | % 10 | % Created by: Lee A. Harrison 11 | % On: 6/21/2018 12 | % 13 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 14 | % This file is part of Introduction to Radar Using Python and MATLAB 15 | % and can not be copied and/or distributed without the express permission of Artech House. 16 | 17 | % Calculate the wavelength 18 | wavelength = 299792458 / frequency; 19 | 20 | % Calculate the power at the radar 21 | pr = (peak_power * antenna_gain ^ 2 * wavelength ^ 2 * target_rcs) ./ ((4.0 * pi) ^ 3 * target_range .^ 4); 22 | 23 | end -------------------------------------------------------------------------------- /mlradar/libs/radar_range/range_equation/power_density_radar.m: -------------------------------------------------------------------------------- 1 | function pd = power_density_radar(peak_power, antenna_gain, target_range) 2 | %% Calculate the power density at a point in space. 3 | % :param peak_power: The peak transmitted power (W). 4 | % :param antenna_gain: The gain of the transmitting antenna. 5 | % :param target_range: The target distance from the transmitting antenna (m). 6 | % :return: The power density at the target (W/m^2). 7 | % 8 | % Created by: Lee A. Harrison 9 | % On: 6/21/2018 10 | % 11 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 12 | % This file is part of Introduction to Radar Using Python and MATLAB 13 | % and can not be copied and/or distributed without the express permission of Artech House. 14 | 15 | % Calculate the power density 16 | pd = peak_power * antenna_gain ./ (4.0 * pi * target_range .^ 2); 17 | 18 | end -------------------------------------------------------------------------------- /mlradar/libs/radar_range/search_eqaution/output_snr_search.m: -------------------------------------------------------------------------------- 1 | function snr = output_snr_search(power_aperture, system_temperature, noise_factor, losses, target_range, search_volume, scan_time, target_rcs) 2 | %% Calculate the output signal to noise ratio for the search radar range equation. 3 | % :param power_aperture: The power aperture product (W m^2). 4 | % :param system_temperature: The system temperature (K). 5 | % :param noise_factor: The receiver noise factor. 6 | % :param losses: The system losses. 7 | % :param target_range: The target distance from the transmitting antenna (m). 8 | % :param search_volume: The volume to search (steradians). 9 | % :param scan_time: The time to scan the volume (s). 10 | % :param target_rcs: The target radar cross section (m^2). 11 | % :return: The output signal to noise ratio. 12 | % 13 | % Created by: Lee A. Harrison 14 | % On: 6/21/2018 15 | % 16 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 17 | % This file is part of Introduction to Radar Using Python and MATLAB 18 | % and can not be copied and/or distributed without the express permission of Artech House. 19 | 20 | % Boltzmann's constant 21 | k = 1.38064852e-23; 22 | 23 | % Calculate the output signal to noise ratio 24 | snr = (power_aperture * target_rcs * scan_time) ./ ((4.0 * pi) ^ 3 * k * system_temperature * noise_factor * losses * target_range .^ 4 * search_volume); -------------------------------------------------------------------------------- /mlradar/libs/radar_range/search_eqaution/power_aperture.m: -------------------------------------------------------------------------------- 1 | function pa = power_aperture(system_temperature, noise_factor, losses, signal_to_noise, target_range, search_volume, scan_time, target_rcs) 2 | %% Calculate the power aperture product. 3 | % :param system_temperature: The system temperature (K). 4 | % :param noise_factor: The receiver noise factor. 5 | % :param losses: The system losses. 6 | % :param signal_to_noise: The signal to noise ratio. 7 | % :param target_range: The target distance from the transmitting antenna (m). 8 | % :param search_volume: The volume to search (steradians). 9 | % :param scan_time: The time to scan the volume (s). 10 | % :param target_rcs: The target radar cross section (m^2). 11 | % :return: The power aperture product (dB). 12 | % 13 | % Created by: Lee A. Harrison 14 | % On: 6/21/2018 15 | % 16 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 17 | % This file is part of Introduction to Radar Using Python and MATLAB 18 | % and can not be copied and/or distributed without the express permission of Artech House. 19 | 20 | % Boltzmann's constant 21 | k = 1.38064852e-23; 22 | 23 | % Calculate the power aperture 24 | pa = signal_to_noise * (4.0 * pi * k * system_temperature * noise_factor * losses * target_range .^ 4 * search_volume) ./ (target_rcs * scan_time); -------------------------------------------------------------------------------- /mlradar/libs/rcs/cone.facet: -------------------------------------------------------------------------------- 1 | Cone 2 | 22 3 | 0 0 0 4 | 1.4000 0 0 5 | 1.3315 0.4326 0 6 | 1.1326 0.8229 0 7 | 0.8229 1.1326 0 8 | 0.4326 1.3315 0 9 | 0.0000 1.4000 0 10 | -0.4326 1.3315 0 11 | -0.8229 1.1326 0 12 | -1.1326 0.8229 0 13 | -1.3315 0.4326 0 14 | -1.4000 0.0000 0 15 | -1.3315 -0.4326 0 16 | -1.1326 -0.8229 0 17 | -0.8229 -1.1326 0 18 | -0.4326 -1.3315 0 19 | -0.0000 -1.4000 0 20 | 0.4326 -1.3315 0 21 | 0.8229 -1.1326 0 22 | 1.1326 -0.8229 0 23 | 1.3315 -0.4326 0 24 | 0 0 5.2248 25 | 40 26 | 0 2 1 27 | 0 3 2 28 | 0 4 3 29 | 0 5 4 30 | 0 6 5 31 | 0 7 6 32 | 0 8 7 33 | 0 9 8 34 | 0 10 9 35 | 0 11 10 36 | 0 12 11 37 | 0 13 12 38 | 0 14 13 39 | 0 15 14 40 | 0 16 15 41 | 0 17 16 42 | 0 18 17 43 | 0 19 18 44 | 0 20 19 45 | 0 1 20 46 | 21 1 2 47 | 21 2 3 48 | 21 3 4 49 | 21 4 5 50 | 21 5 6 51 | 21 6 7 52 | 21 7 8 53 | 21 8 9 54 | 21 9 10 55 | 21 10 11 56 | 21 11 12 57 | 21 12 13 58 | 21 13 14 59 | 21 14 15 60 | 21 15 16 61 | 21 16 17 62 | 21 17 18 63 | 21 18 19 64 | 21 19 20 65 | 21 20 1 -------------------------------------------------------------------------------- /mlradar/libs/rcs/cylinder_oblique_rcs_2d.m: -------------------------------------------------------------------------------- 1 | function [ rcs_te, rcs_tm ] = cylinder_oblique_rcs_2d(frequency, radius, incident_angle, observation_angle, number_of_modes) 2 | %% Calculate the bistatic radar cross section for the infinite cylinder with oblique incidence. 3 | % :param frequency: The frequency of the incident energy (Hz). 4 | % :param radius: The radius of the cylinder (m). 5 | % :param incident_angle: The angle of incidence from z-axis (deg). 6 | % :param observation_angle: The observation angle (deg). 7 | % :param number_of_modes: The number of terms to take in the summation. 8 | % :return: The bistatic radar cross section for the infinite cylinder (m^2). 9 | 10 | % Created by: Lee A. Harrison 11 | % On: 1/15/2019 12 | % 13 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 14 | % This file is part of Introduction to Radar Using Python and MATLAB 15 | % and can not be copied and/or distributed without the express permission of Artech House. 16 | 17 | % Speed of light 18 | c = 299792458; 19 | 20 | % Wavelength 21 | wavelength = c / frequency; 22 | 23 | % Wavenumber 24 | k = 2.0 * pi / wavelength; 25 | 26 | % Initialize the sum 27 | s_tm = 0; 28 | s_te = 0; 29 | 30 | phi = observation_angle * pi / 180; 31 | theta_i = incident_angle * pi / 180; 32 | 33 | % Argument for Bessel and Hankel functions 34 | z = k * radius * sin(theta_i); 35 | 36 | for n = 0:(number_of_modes + 1) 37 | en = 2.0; 38 | if n == 0 39 | en = 1.0; 40 | end 41 | 42 | an = besselj(n, z) / besselh(n, 2, z); 43 | 44 | jp = n * besselj(n, z) / z - besselj(n + 1, z); 45 | hp = n * besselh(n, 2, z) / z - besselh(n + 1, 2, z); 46 | 47 | bn = -jp / hp; 48 | 49 | s_tm = s_tm + en * an * cos(n * phi); 50 | s_te = s_te + en * bn * cos(n * phi); 51 | end 52 | 53 | rcs_tm = 2.0 * wavelength / (pi * sin(theta_i)) * abs(s_tm) ^ 2; 54 | rcs_te = 2.0 * wavelength / (pi * sin(theta_i)) * abs(s_te) ^ 2; -------------------------------------------------------------------------------- /mlradar/libs/rcs/cylinder_oblique_rcs_3d.m: -------------------------------------------------------------------------------- 1 | function [ rcs_te, rcs_tm ] = cylinder_oblique_rcs_3d(frequency, radius, incident_angle, observation_angle, number_of_modes, length) 2 | %% Calculate the bistatic radar cross section for a finite length cylinder with oblique incidence. 3 | % :param frequency: The frequency of the incident energy (Hz). 4 | % :param radius: The radius of the cylinder (m). 5 | % :param incident_angle: The angle of incidence from z-axis (deg). 6 | % :param observation_angle: The observation angle (deg). 7 | % :param number_of_modes: The number of terms to take in the summation. 8 | % :param length: The length of the cylinder (m). 9 | % :return: The bistatic radar cross section for the infinite cylinder (m^2). 10 | 11 | % Created by: Lee A. Harrison 12 | % On: 1/15/2019 13 | % 14 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 15 | % This file is part of Introduction to Radar Using Python and MATLAB 16 | % and can not be copied and/or distributed without the express permission of Artech House. 17 | 18 | % Speed of light 19 | c = 299792458; 20 | 21 | % Wavelength 22 | wavelength = c / frequency; 23 | 24 | theta_i = incident_angle * pi / 180; 25 | theta_o = theta_i; 26 | 27 | % Calculate the 2D RCS 28 | [rcs_te, rcs_tm] = cylinder_oblique_rcs_2d(frequency, radius, incident_angle, observation_angle, number_of_modes); 29 | 30 | % Scale factor 31 | value = 2.0 * length ^ 2 / wavelength * sin(theta_o) ^ 2 * sinc(length / wavelength * (cos(theta_i) + cos(theta_o))) ^ 2; 32 | 33 | % Scale the values 34 | rcs_te = rcs_te * value; 35 | rcs_tm = rcs_tm * value; -------------------------------------------------------------------------------- /mlradar/libs/rcs/cylinder_rcs_2d.m: -------------------------------------------------------------------------------- 1 | function [ rcs_te, rcs_tm ] = cylinder_rcs_2d( frequency, radius, observation_angle, number_of_modes ) 2 | %% Calculate the bistatic radar cross section for the infinite cylinder. 3 | % :param frequency: The frequency of the incident energy (Hz). 4 | % :param radius: The radius of the cylinder (m). 5 | % :param observation_angle: The observation angle (deg). 6 | % :param number_of_modes: The number of terms to take in the summation. 7 | % :return: The bistatic radar cross section for the infinite cylinder (m^2). 8 | 9 | % Created by: Lee A. Harrison 10 | % On: 1/15/2019 11 | % 12 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 13 | % This file is part of Introduction to Radar Using Python and MATLAB 14 | % and can not be copied and/or distributed without the express permission of Artech House. 15 | 16 | % Speed of light 17 | c = 299792458; 18 | 19 | % Wavelength 20 | wavelength = c / frequency; 21 | 22 | % Wavenumber 23 | k = 2.0 * pi / wavelength; 24 | 25 | % Argument for Bessel and Hankel functions 26 | z = k * radius; 27 | 28 | % Initialize the sum 29 | s_tm = 0; 30 | s_te = 0; 31 | 32 | phi = observation_angle * pi / 180; 33 | 34 | for n = 0:(number_of_modes + 1) 35 | en = 2.0; 36 | if n == 0 37 | en = 1.0; 38 | end 39 | 40 | an = besselj(n, z) / besselh(n, 2, z); 41 | 42 | jp = n * besselj(n, z) / z - besselj(n + 1, z); 43 | hp = n * besselh(n, 2, z) / z - besselh(n + 1, 2, z); 44 | 45 | bn = -jp / hp; 46 | 47 | s_tm = s_tm + en * an * cos(n * phi); 48 | s_te = s_te + en * bn * cos(n * phi); 49 | 50 | rcs_tm = 2.0 * wavelength / pi * abs(s_tm) .^ 2; 51 | rcs_te = 2.0 * wavelength / pi * abs(s_te) .^ 2; 52 | 53 | end -------------------------------------------------------------------------------- /mlradar/libs/rcs/cylinder_rcs_3d.m: -------------------------------------------------------------------------------- 1 | function [ rcs_te, rcs_tm ] = cylinder_rcs_3d( frequency, radius, observation_angle, number_of_modes, length ) 2 | %% Calculate the bistatic radar cross section for a finite length cylinder. 3 | % :param frequency: The frequency of the incident energy (Hz). 4 | % :param radius: The radius of the cylinder (m). 5 | % :param observation_angle: The observation angle (deg). 6 | % :param number_of_modes: The number of terms to take in the summation. 7 | % :param length: The length of the cylinder (m). 8 | % :return: The bistatic radar cross section for the infinite cylinder (m^2). 9 | 10 | % Created by: Lee A. Harrison 11 | % On: 1/15/2019 12 | % 13 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 14 | % This file is part of Introduction to Radar Using Python and MATLAB 15 | % and can not be copied and/or distributed without the express permission of Artech House. 16 | 17 | % Speed of light 18 | c = 299792458; 19 | 20 | % Wavelength 21 | wavelength = c / frequency; 22 | 23 | % First calculate the 2D rcs 24 | [rcs_te, rcs_tm] = cylinder_rcs_2d(frequency, radius, observation_angle, number_of_modes); 25 | 26 | % Scaling factor 27 | value = 2.0 * length ^ 2 / wavelength; 28 | 29 | rcs_te = rcs_te * value; 30 | rcs_tm = rcs_tm * value; -------------------------------------------------------------------------------- /mlradar/libs/rcs/plate.facet: -------------------------------------------------------------------------------- 1 | Rectangular Plate 2 | 4 3 | 0.0 0.0 0.0 4 | 3.0 0.0 0.0 5 | 0.0 5.0 0.0 6 | 3.0 5.0 0.0 7 | 2 8 | 0 1 2 9 | 1 3 2 -------------------------------------------------------------------------------- /mlradar/libs/rcs/rcs_frustum.m: -------------------------------------------------------------------------------- 1 | function [ rcs ] = rcs_frustum( frequency, nose_radius, base_radius, length, incident_angle ) 2 | %% Calculate the radar cross section of a frustum. 3 | % :param frequency: The operating frequency (Hz). 4 | % :param nose_radius: The radius of the nose (m). 5 | % :param base_radius: The radius of the base (m). 6 | % :param length: The length (m). 7 | % :param incident_angle: The incident angle (rad). 8 | % :return: The radar cross section of the frustum (m^2). 9 | 10 | % Created by: Lee A. Harrison 11 | % On: 1/15/2019 12 | % 13 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 14 | % This file is part of Introduction to Radar Using Python and MATLAB 15 | % and can not be copied and/or distributed without the express permission of Artech House. 16 | 17 | % Speed of light 18 | c = 299792458; 19 | 20 | % Wavelength 21 | wavelength = c / frequency; 22 | 23 | % Wavenumber 24 | k = 2.0 * pi / wavelength; 25 | 26 | % Calculate the half cone angle 27 | half_cone_angle = atan((base_radius - nose_radius) / length); 28 | 29 | % Calculate the heights 30 | z2 = base_radius * tan(half_cone_angle); 31 | z1 = nose_radius * tan(half_cone_angle); 32 | 33 | % Calculate the RCS 34 | if abs(incident_angle - (0.5 * pi + half_cone_angle)) < 1e-12; 35 | % Specular 36 | rcs = 8.0 / 9.0 * pi * (z2 ^ 1.5 - z1 ^ 1.5) ^ 2 * sin(half_cone_angle) / (wavelength * cos(half_cone_angle) ^ 4); 37 | elseif incident_angle < 1e-3 38 | % Base 39 | rcs = wavelength ^ 2 * (k * base_radius) ^ 4 / (4.0 * pi); 40 | elseif pi - incident_angle < 1e-3 41 | % Nose 42 | rcs = wavelength ^ 2 * (k * nose_radius) ^ 4 / (4.0 * pi); 43 | else 44 | rcs = wavelength * base_radius / (8.0 * pi * sin(incident_angle)) * (tan(incident_angle - half_cone_angle)) ^ 2; 45 | end -------------------------------------------------------------------------------- /mlradar/libs/rcs/read_facet_model.m: -------------------------------------------------------------------------------- 1 | function [vertices, faces] = read_facet_model(facet_file) 2 | %% Read a model facet file 3 | 4 | % Created by: Lee A. Harrison 5 | % Cretaed on: 1/17/2019 6 | % 7 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 8 | % This file is part of Introduction to Radar Using Python and MATLAB 9 | % and can not be copied and/or distributed without the express permission of Artech House. 10 | 11 | % Open the file 12 | fid = fopen(facet_file, 'r'); 13 | 14 | % Read the name of the model 15 | model_name = fgetl(fid); 16 | 17 | % Read the number of vertices 18 | number_of_vertices = str2num(fgetl(fid)); 19 | 20 | % Read the vertices 21 | vertices = zeros(number_of_vertices, 3); 22 | 23 | for i = 1:number_of_vertices 24 | line = strtrim(fgetl(fid)); 25 | line_list = strsplit(line, ' '); 26 | 27 | % Parse the values 28 | vertices(i,:) = [str2num(line_list{1}), str2num(line_list{2}), str2num(line_list{3})]; 29 | end 30 | 31 | 32 | % Read the number of faces 33 | number_of_faces = str2num(fgetl(fid)); 34 | 35 | % Read the faces 36 | faces = zeros(number_of_faces, 3); 37 | 38 | for i = 1:number_of_faces 39 | line = strtrim(fgetl(fid)); 40 | line_list = strsplit(line, ' '); 41 | 42 | % Parse the values 43 | faces(i,:) = [str2num(line_list{1}), str2num(line_list{2}), str2num(line_list{3})]; 44 | end 45 | 46 | faces = faces + 1; 47 | 48 | % Close the file 49 | fclose(fid); 50 | 51 | end 52 | -------------------------------------------------------------------------------- /mlradar/libs/rcs/rectangular_plate.m: -------------------------------------------------------------------------------- 1 | function [ rcs_tm, rcs_te ] = rectangular_plate(frequency, width, length, incident_theta, observation_theta, observation_phi) 2 | %% Calculate the bistatic radar cross section for a rectangular plate. 3 | % :param frequency: The frequency of the incident energy (Hz). 4 | % :param width: The width of the plate (m). 5 | % :param length: The length of the plate (m). 6 | % :param incident_theta: The incident angle theta (deg). 7 | % :param observation_theta: The observation angle theta (deg). 8 | % :param observation_phi: The observation angle phi (deg). 9 | % :return: The bistatic radar cross section (m^2). 10 | 11 | % Created by: Lee A. Harrison 12 | % On: 1/17/2019 13 | % 14 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 15 | % This file is part of Introduction to Radar Using Python and MATLAB 16 | % and can not be copied and/or distributed without the express permission of Artech House. 17 | 18 | % Speed of light 19 | c = 299792458; 20 | 21 | % Wavelength 22 | wavelength = c / frequency; 23 | 24 | theta_i = pi / 180 * incident_theta; 25 | theta_o = pi / 180 * observation_theta; 26 | 27 | phi_o = pi / 180 * observation_phi; 28 | 29 | x = width / wavelength * sin(theta_o) * cos(phi_o); 30 | y = length / wavelength * (sin(theta_o) * sin(phi_o) - sin(theta_i)); 31 | 32 | rcs_tm = 4.0 * pi * (length * width / wavelength) ^ 2 * (cos(theta_i) ^ 2 * (cos(theta_o) ^ 2 * cos(phi_o) ^ 2 + sin(phi_o) ^ 2)) * sinc(x) ^ 2 * sinc(y) ^ 2; 33 | 34 | rcs_te = 4.0 * pi * (length * width / wavelength) ^ 2 * (cos(theta_o) ^ 2 * sin(phi_o) ^ 2 + cos(phi_o) ^ 2) * sinc(x) ^ 2 * sinc(y) ^ 2; -------------------------------------------------------------------------------- /mlradar/libs/rcs/strip_rcs.m: -------------------------------------------------------------------------------- 1 | function [ rcs_te, rcs_tm ] = strip_rcs(frequency, width, incident_angle, observation_angle) 2 | %% Calculate the bistatic radar cross section for a 2D strip. 3 | % :param frequency: The frequency of the incident energy (Hz). 4 | % :param width: The width of the strip (m). 5 | % :param incident_angle: The incident angle (deg). 6 | % :param observation_angle: The observation angle (deg). 7 | % :return: The bistatic radar cross section (m^2). 8 | 9 | % Created by: Lee A. Harrison 10 | % On: 1/15/2019 11 | % 12 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 13 | % This file is part of Introduction to Radar Using Python and MATLAB 14 | % and can not be copied and/or distributed without the express permission of Artech House. 15 | 16 | % Speed of light 17 | c = 299792458; 18 | 19 | % Wavelength 20 | wavelength = c / frequency; 21 | 22 | % Wavenumber 23 | k = 2.0 * pi / wavelength; 24 | 25 | phi_i = incident_angle * pi / 180; 26 | 27 | phi_o = observation_angle * pi / 180; 28 | 29 | rcs_tm = k * width ^ 2 * sin(phi_i) * sinc(width / wavelength * (cos(phi_o) + cos(phi_i))) ^ 2; 30 | 31 | rcs_te = k * width ^ 2 * sin(phi_o) * sinc(width / wavelength * (cos(phi_o) + cos(phi_i))) ^ 2; -------------------------------------------------------------------------------- /mlradar/libs/receivers/cascade_noise_figure.m: -------------------------------------------------------------------------------- 1 | function total_nf = cascade_noise_figure(gain, noise_figure) 2 | %% Calculate the total noise figure for a cascaded network. 3 | % :param gain: The gain of each component (dB). 4 | % :param noise_figure: The noise figure of each component (dB). 5 | % :return: The total noise figure (dB). 6 | % 7 | % Created by: Lee A. Harrison 8 | % On: 9/18/2018 9 | % 10 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 11 | % This file is part of Introduction to Radar Using Python and MATLAB 12 | % and can not be copied and/or distributed without the express permission of Artech House. 13 | 14 | % Convert noise figure and gain to linear units 15 | noise_factor = 10.0 .^ (noise_figure / 10.0); 16 | gain_linear = 10.0 .^ (gain / 10.0); 17 | 18 | % Start with the first component 19 | total = noise_factor(1); 20 | 21 | % Loop over the remaining components 22 | for i = 2:length(noise_factor) 23 | total = total + (noise_factor(i) - 1.0) / prod(gain_linear(1:i-1)); 24 | end 25 | 26 | % Return the total noise figure 27 | total_nf = 10.0 * log10(total); 28 | end 29 | 30 | -------------------------------------------------------------------------------- /mlradar/libs/receivers/chirp.m: -------------------------------------------------------------------------------- 1 | function [ signal ] = chirp(t, start_frequency, t1, end_frequency) 2 | %% Generate a chirp waveform 3 | % :param t: The time array (s). 4 | % :param start_frequency: The starting frequency of the chirp (Hz). 5 | % :param t1: The time at which the end frequency is specified (s). 6 | % :param end_frequency: The ending frequency of the chirp (Hz). 7 | % 8 | % Created by: Lee A. Harrison 9 | % On: 9/18/2018 10 | % 11 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 12 | % This file is part of Introduction to Radar Using Python and MATLAB 13 | % and can not be copied and/or distributed without the express permission of Artech House. 14 | 15 | f = start_frequency + 0.5 * (end_frequency - start_frequency) * t / t1; 16 | 17 | signal = cos(2.0 * pi * f .* t); 18 | 19 | end -------------------------------------------------------------------------------- /mlradar/libs/receivers/coherent_detector.m: -------------------------------------------------------------------------------- 1 | function [ in_phase, quadrature ] = coherent_detector(if_signal, center_frequency, bandwidth, sample_frequency, time) 2 | %% Calculate the baseband I and Q signals from the IF signal. 3 | % :param if_signal: The input IF signal to the detector. 4 | % :param center_frequency: The center frequency of the IF signal (Hz). 5 | % :param bandwidth: The bandwidth of the IF signal (Hz). 6 | % :param sample_frequency: The sampling rate (Hz). 7 | % :param time: The time vector for the IF signal (s). 8 | % :return: The baseband I and Q signals. 9 | % 10 | % Created by: Lee A. Harrison 11 | % On: 9/18/2018 12 | % 13 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 14 | % This file is part of Introduction to Radar Using Python and MATLAB 15 | % and can not be copied and/or distributed without the express permission of Artech House. 16 | 17 | % Shift the IF signal to baseband by mixing with the oscillator frequency 18 | in_phase = if_signal .* exp(-1j * 2.0 * pi * center_frequency * time); 19 | quadrature = if_signal .* exp(-1j * (2.0 * pi * center_frequency * time + 0.5 * pi)); 20 | 21 | % Calculate the spectra 22 | frequencies = fftfreq(round(sample_frequency), 1.0 / sample_frequency); 23 | i_freq = fft(in_phase); 24 | q_freq = fft(quadrature); 25 | 26 | % Use 6th order Butterworth low pass filter 27 | [zb, pb, kb] = butter(6, 2.0 * pi * (0.5 * bandwidth), 'low'); 28 | [b, a] = zp2tf(zb, pb, kb); 29 | [h, w] = freqs(b, a, frequencies * pi / 180.); 30 | 31 | i_freq = i_freq * h; 32 | q_freq = q_freq * h; 33 | 34 | % Calculate the time domain I/Q of the signal 35 | in_phase = ifft(i_freq); 36 | quadrature = ifft(q_freq); 37 | 38 | end 39 | 40 | -------------------------------------------------------------------------------- /mlradar/libs/receivers/envelope_detector.m: -------------------------------------------------------------------------------- 1 | function y = envelope_detector( if_signal ) 2 | %% Calculate the amplitude envelope of the IF signal. 3 | % :param if_signal: The signal at IF. 4 | % :return: The amplitude envelope. 5 | % 6 | % Created by: Lee A. Harrison 7 | % On: 9/18/2018 8 | % 9 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 10 | % This file is part of Introduction to Radar Using Python and MATLAB 11 | % and can not be copied and/or distributed without the express permission of Artech House. 12 | 13 | n = length(if_signal); 14 | X = fft(if_signal, n); 15 | h = zeros(1, n); 16 | h(1) = 1; 17 | h(2:n/2 + 1) = 2.0 * ones(1, n/2); 18 | h(n/2 + 1) = 1; 19 | Z = X.*h; 20 | y = abs((ifft(Z, n))); 21 | 22 | 23 | end 24 | 25 | -------------------------------------------------------------------------------- /mlradar/libs/receivers/quantization.m: -------------------------------------------------------------------------------- 1 | function [ quantized_signal, error_signal ] = quantization(if_signal, number_of_bits) 2 | %% Calculate the quantized signal for a given number of bits. 3 | % :param if_signal: The sampled analog signal to be quantized. 4 | % :param number_of_bits: The number of bits in the ADC. 5 | % :return: The quantized signal. 6 | % 7 | % Created by: Lee A. Harrison 8 | % On: 9/18/2018 9 | % 10 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 11 | % This file is part of Introduction to Radar Using Python and MATLAB 12 | % and can not be copied and/or distributed without the express permission of Artech House. 13 | 14 | % Calculate the LSB level 15 | lsb = 2.0 / (2.0 ^ number_of_bits - 1); 16 | 17 | % Calculate the quantized signal 18 | quantized_signal = lsb * round((if_signal + 1.0) / lsb) - 1.0; 19 | 20 | % Calculate the error between the analog signal and the quantized signal 21 | error_signal = if_signal - quantized_signal; 22 | 23 | 24 | -------------------------------------------------------------------------------- /mlradar/libs/receivers/sensitivity_time_control.m: -------------------------------------------------------------------------------- 1 | function [ receive_range, attenuation ] = sensitivity_time_control(pulse_repetition_frequency, pulse_width) 2 | %% Calculate the STC attenuation. 3 | % :param pulse_repetition_frequency: The PRF (Hz). 4 | % :param pulse_width: The pulse width (s). 5 | % :return: The normalized STC attenuation. 6 | % 7 | % Created by: Lee A. Harrison 8 | % On: 9/18/2018 9 | % 10 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 11 | % This file is part of Introduction to Radar Using Python and MATLAB 12 | % and can not be copied and/or distributed without the express permission of Artech House. 13 | 14 | % Speed of light (m/s) 15 | c = 299792458; 16 | 17 | % Calculate the PRI 18 | pulse_repetition_interval = 1.0 / pulse_repetition_frequency; 19 | 20 | % Find the minimum and maximum ranges 21 | minimum_range = 0.5 * c * pulse_width; 22 | maximum_range = 0.5 * c * pulse_repetition_interval; 23 | 24 | % Set up the range array 25 | receive_range = linspace(0, maximum_range, 1000); 26 | 27 | % Calculate and return the attenuation 28 | attenuation = 1.0 ./ receive_range .^ 3.5; 29 | attenuation(receive_range < minimum_range) = 1.0 ./ minimum_range .^ 3.5; 30 | 31 | end 32 | 33 | -------------------------------------------------------------------------------- /mlradar/libs/utils/cosint.m: -------------------------------------------------------------------------------- 1 | function a = cosint(x) 2 | %% Calculate the cos integral 3 | % :param x: The argument of the cos integral 4 | % :return: The value of the cos integral. 5 | % 6 | % Created by: Lee A. Harrison 7 | % On: 2/20/2019 8 | % 9 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 10 | % This file is part of Introduction to Radar Using Python and MATLAB 11 | % and can not be copied and/or distributed without the express permission of Artech House. 12 | 13 | [m, n] = size(x); 14 | 15 | a = zeros(m,n); 16 | 17 | for im = 1:m 18 | for in = 1:n 19 | a(im, in) = 0.57721 + log(x) + integral(@cosint_arg, 1e-6, x(im, in)); 20 | end 21 | end 22 | 23 | end 24 | 25 | -------------------------------------------------------------------------------- /mlradar/libs/utils/cosint_arg.m: -------------------------------------------------------------------------------- 1 | function si = cosint_arg(t) 2 | si = (cos(t) - 1.0) ./ t; -------------------------------------------------------------------------------- /mlradar/libs/utils/db.m: -------------------------------------------------------------------------------- 1 | function [ x_db ] = db( x_lin ) 2 | %% Convert from linear units to decibels 3 | % :param x_lin: The value in linear units. 4 | % :return: The value in decibels. 5 | % 6 | % Created by: Lee A. Harrison 7 | % On: 6/18/2018 8 | % 9 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 10 | % This file is part of Introduction to Radar Using Python and MATLAB 11 | % and can not be copied and/or distributed without the express permission of Artech House. 12 | 13 | x_db = 10 * log10( x_lin ); 14 | 15 | end 16 | 17 | -------------------------------------------------------------------------------- /mlradar/libs/utils/ecef_to_lla.m: -------------------------------------------------------------------------------- 1 | function [lat, lon, alt] = ecef_to_lla(ecef_x, ecef_y, ecef_z) 2 | %% Convert coordinates in ECEF to LLA. 3 | % :param ecef_x: The x coordinate of the point (meters). 4 | % :param ecef_y: The y coordinate of the point (meters). 5 | % :param ecef_z: The z coordinate of the point (meters). 6 | % :return: The LLA coordinates of the point. 7 | % 8 | % Created by: Lee A. Harrison 9 | % On: 6/18/2018 10 | % 11 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 12 | % This file is part of Introduction to Radar Using Python and MATLAB 13 | % and can not be copied and/or distributed without the express permission of Artech House. 14 | 15 | %% Earth constants 16 | effective_earth_radius = 6378137; 17 | earth_eccentricity = 8.1819190842622e-2; 18 | 19 | %% Effective polar radius 20 | earth_radius_polar = sqrt(effective_earth_radius^2 * (1. - earth_eccentricity^2)); 21 | 22 | ep = sqrt((effective_earth_radius^2 - earth_radius_polar^2) / earth_radius_polar^2); 23 | 24 | %% Radius in xy plane 25 | r = sqrt(ecef_x * ecef_x + ecef_y * ecef_y); 26 | 27 | %% Angle from the xy plane 28 | theta = atan2(effective_earth_radius * ecef_z, earth_radius_polar * r); 29 | 30 | %% Calculate the coordinates 31 | lat = atan2((ecef_z + ep^2 * earth_radius_polar * sin(theta)^3), (r - earth_eccentricity^2 * effective_earth_radius * cos(theta)^3)); 32 | 33 | lon = mod(atan2(ecef_y, ecef_x), 2. * pi); 34 | 35 | alt = r / cos(lat) - effective_earth_radius / sqrt(1. - earth_eccentricity^2 * sin(lat)^2); -------------------------------------------------------------------------------- /mlradar/libs/utils/fftfreq.m: -------------------------------------------------------------------------------- 1 | function [ frequencies ] = fftfreq( n, dt ) 2 | %% Helper function similar to SciPy 3 | % :param n: The number of elements in the array. 4 | % :param dt: The time step in the array. 5 | % :return: The corresponding frequency array. 6 | % 7 | % Created by: Lee A. Harrison 8 | % On: 4/27/2019 9 | % 10 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 11 | % This file is part of Introduction to Radar Using Python and MATLAB 12 | % and can not be copied and/or distributed without the express permission of Artech House. 13 | 14 | % Maximum frequency (+/-) 15 | f_max = 1.0 / (2.0 * dt); 16 | 17 | % Frequency step 18 | df = 1.0 / (n * dt); 19 | 20 | % Calculate the frequencies 21 | f_space = linspace(0, 2.0 * f_max - df, n); 22 | 23 | frequencies = mod(f_space + f_max, 2.0 * f_max) - f_max; -------------------------------------------------------------------------------- /mlradar/libs/utils/lin.m: -------------------------------------------------------------------------------- 1 | function [ x_lin ] = lin( x_db ) 2 | %% Convert from decibels to linear units 3 | % :param x_db: The value in decibels. 4 | % :return: The value in linear units. 5 | % 6 | % Created by: Lee A. Harrison 7 | % On: 6/18/2018 8 | % 9 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 10 | % This file is part of Introduction to Radar Using Python and MATLAB 11 | % and can not be copied and/or distributed without the express permission of Artech House. 12 | 13 | x_lin = 10 .^ (x_db ./ 10); 14 | 15 | end 16 | 17 | -------------------------------------------------------------------------------- /mlradar/libs/utils/lla_to_ecef.m: -------------------------------------------------------------------------------- 1 | function [ecef_x, ecef_y, ecef_z] = lla_to_ecef(lat, lon, alt) 2 | 3 | %% Convert coordinates in LLA to ECEF. 4 | % :param lat: The latitude of the point (radians). 5 | % :param lon: The Longitude of the point (radians). 6 | % :param alt: The altitude of the point (meters). 7 | % :return: The ECEF coordinates of the point (meters). 8 | % 9 | % Created by: Lee A. Harrison 10 | % On: 6/18/2018 11 | % 12 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 13 | % This file is part of Introduction to Radar Using Python and MATLAB 14 | % and can not be copied and/or distributed without the express permission of Artech House. 15 | 16 | %% Earth constants 17 | effective_earth_radius = 6378137; 18 | earth_eccentricity = 8.1819190842622e-2; 19 | 20 | % Radius of curvature 21 | radius = effective_earth_radius / sqrt(1. - earth_eccentricity ^ 2 * sin(lat) ^ 2); 22 | 23 | % Calculate the coordinates 24 | ecef_x = (radius + alt) * cos(lat) * cos(lon); 25 | ecef_y = (radius + alt) * cos(lat) * sin(lon); 26 | ecef_z = ((1. - earth_eccentricity^2) * radius + alt) * sin(lat); 27 | -------------------------------------------------------------------------------- /mlradar/libs/utils/sinc.m: -------------------------------------------------------------------------------- 1 | function [ s ] = sinc( x ) 2 | %% Calculate the sinc function 3 | % :param x: Argument of the sinc function. 4 | % :return: The value of sinc(x). 5 | % 6 | % Created by: Lee A. Harrison 7 | % On: 6/18/2018 8 | % 9 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 10 | % This file is part of Introduction to Radar Using Python and MATLAB 11 | % and can not be copied and/or distributed without the express permission of Artech House. 12 | 13 | s = ones(size(x)); 14 | index = x ~= 0.0; 15 | s(index) = sin(pi * x(index)) ./ (pi * x(index)); 16 | 17 | end 18 | 19 | -------------------------------------------------------------------------------- /mlradar/libs/utils/sinint.m: -------------------------------------------------------------------------------- 1 | function a = sinint(x) 2 | %% Calculate the sin integral 3 | % :param x: The argument of the sin integral 4 | % :return: The value of the sin integral. 5 | % 6 | % Created by: Lee A. Harrison 7 | % On: 2/20/2019 8 | % 9 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 10 | % This file is part of Introduction to Radar Using Python and MATLAB 11 | % and can not be copied and/or distributed without the express permission of Artech House. 12 | 13 | [m, n] = size(x); 14 | 15 | a = zeros(m,n); 16 | 17 | for im = 1:m 18 | for in = 1:n 19 | a(im, in) = integral(@sinint_arg, 1e-6, x(im, in)); 20 | end 21 | end 22 | 23 | end 24 | 25 | -------------------------------------------------------------------------------- /mlradar/libs/utils/sinint_arg.m: -------------------------------------------------------------------------------- 1 | function si = sinint_arg(t) 2 | si = sin(t) ./ t; -------------------------------------------------------------------------------- /mlradar/libs/wave_propagation/apparent_elevation.m: -------------------------------------------------------------------------------- 1 | function theta_apparent = apparent_elevation(theta_true, height) 2 | %% Calculate the apparent elevation of the target. 3 | % :param theta_true: The true elevation angle (degrees). 4 | % :param height: The height of the radar (km). 5 | % :return: The apparent elevation angle of the target (degrees). 6 | % 7 | % Created by: Lee A. Harrison 8 | % On: 6/18/2018 9 | % 10 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 11 | % This file is part of Introduction to Radar Using Python and MATLAB 12 | % and can not be copied and/or distributed without the express permission of Artech House. 13 | 14 | theta_apparent = theta_true - 180/pi * integral(@integrand, height, 1000); 15 | 16 | function dz = integrand(z) 17 | %% Determine the integrand for calculating the apparent elevation angle 18 | % :param z: The altitude (km). 19 | % :return: The integrand. 20 | 21 | % Effective radius of the Earth (km) 22 | re = 6378.137; 23 | 24 | % Standard values 25 | a = 0.000315; 26 | b = 0.1361; 27 | 28 | % Refractive index and derivative as a function of altitude 29 | n_z = 1. + a * exp(-b * z); 30 | np_z = -(a * b * exp(-b * z)); 31 | 32 | % Refractive index at the given height 33 | n_h = 1. + a * exp(-b * height); 34 | 35 | tan_phi = tan(acos(((re + height) * n_h) ./ ((re + z) .* n_z) .* cos(theta_true * pi/180))); 36 | 37 | dz = np_z ./ (n_z .* tan_phi); 38 | end 39 | 40 | end -------------------------------------------------------------------------------- /mlradar/libs/wave_propagation/apparent_elevation_approximate.m: -------------------------------------------------------------------------------- 1 | function theta_apparent = apparent_elevation_approximate(theta_true, height) 2 | %% Calculate the apparent elevation angle with the approximate equation. 3 | % :param theta_true: The true elevation angle (degrees). 4 | % :param height: The height of the radar (km). 5 | % :return: The approximated apparent elevation angle (degrees). 6 | % 7 | % Created by: Lee A. Harrison 8 | % On: 6/18/2018 9 | % 10 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 11 | % This file is part of Introduction to Radar Using Python and MATLAB 12 | % and can not be copied and/or distributed without the express permission of Artech House. 13 | 14 | angle_correction = 1. / (1.728 + 0.5411 * theta_true + 0.03723 * theta_true^2 + ... 15 | height * (0.1815 + 0.06272 * theta_true + 0.01380 * theta_true^2) + height^2 * (0.01727 + 0.008288 * theta_true)); 16 | 17 | theta_apparent = theta_true + angle_correction; -------------------------------------------------------------------------------- /mlradar/libs/wave_propagation/apparent_range.m: -------------------------------------------------------------------------------- 1 | function range = apparent_range(radar_lla, target_lla) 2 | %% Calculate the apparent range due to refraction. 3 | % :param radar_lla: The radar location in LLA (deg, deg, m). 4 | % :param target_lla: The target location in LLA (deg, deg, m). 5 | % :return: The apparent range from the radar to the target (meters). 6 | % 7 | % Created by: Lee A. Harrison 8 | % On: 6/18/2018 9 | % 10 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 11 | % This file is part of Introduction to Radar Using Python and MATLAB 12 | % and can not be copied and/or distributed without the express permission of Artech House. 13 | 14 | % Convert the radar and target locations 15 | [x,y,z] = lla_to_ecef(radar_lla(1) * pi/180, radar_lla(2) * pi/180, radar_lla(3)); 16 | radar_ecef(1) = x; radar_ecef(2) = y; radar_ecef(3) = z; 17 | 18 | [x,y,z] = lla_to_ecef(target_lla(1) * pi/180, target_lla(2) * pi/180, target_lla(3)); 19 | target_ecef(1) = x; target_ecef(2) = y; target_ecef(3) = z; 20 | 21 | % Standard values 22 | a = 0.000315; 23 | b = 0.1361; 24 | 25 | % Find the vector from the radar to the target 26 | line_of_sight = target_ecef - radar_ecef; 27 | 28 | % Divide the line of sight into many points for the summation 29 | number_of_points = 1000; 30 | 31 | delta = line_of_sight / (number_of_points - 1); 32 | 33 | % Loop over all the points and perform the summation to find the additional length 34 | s = 0; 35 | 36 | for i = 1:number_of_points 37 | % Find the altitude of each point 38 | l = radar_ecef + delta * (i - 1); 39 | [~, ~, alt] = ecef_to_lla(l(1), l(2), l(3)); 40 | s = s + ((1. + a * exp(-b * alt / 1.e3)) - 1.) * norm(delta); 41 | end 42 | 43 | range.true = norm(line_of_sight); 44 | range.apparent = s + norm(line_of_sight); -------------------------------------------------------------------------------- /mlradar/libs/wave_propagation/brewster_angle.m: -------------------------------------------------------------------------------- 1 | function theta = brewster_angle(frequency, relative_permittivity, relative_permeability, conductivity) 2 | %% Calculate the Brewster angle. 3 | % :param frequency: The operating frequency (Hz). 4 | % :param relative_permittivity: The relative permittivty. 5 | % :param relative_permeability: The relative permeability. 6 | % :param conductivity: The conductivity (S). 7 | % :return: The Brewster angle (radians). 8 | % 9 | % Created by: Lee A. Harrison 10 | % On: 6/18/2018 11 | % 12 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 13 | % This file is part of Introduction to Radar Using Python and MATLAB 14 | % and can not be copied and/or distributed without the express permission of Artech House. 15 | 16 | % Get the wave impedance and propagation constant for each material 17 | pw = plane_wave_parameters(frequency, relative_permittivity, relative_permeability, conductivity); 18 | 19 | term1 = (pw.wave_impedance(1) / pw.wave_impedance(2))^2; 20 | 21 | term2 = (pw.propagation_constant(1) / pw.propagation_constant(2))^2; 22 | 23 | theta = asin(sqrt((term1 - 1.) / (term1 - term2))) * 180. / pi; -------------------------------------------------------------------------------- /mlradar/libs/wave_propagation/cloud_fog_attenuation.m: -------------------------------------------------------------------------------- 1 | function attenuation = cloud_fog_attenuation(frequency, liquid_water_temperature, liquid_water_density) 2 | %% Calculate the specific attenuation due to cloud or fog. 3 | % :param frequency: The operating frequency (GHz). 4 | % :param liquid_water_temperature: The liquid water temperature (K). 5 | % :param liquid_water_density: The liquid water density (g/m^3) 6 | % :return: The specific attenuation (dB/km) 7 | % 8 | % Created by: Lee A. Harrison 9 | % On: 6/18/2018 10 | % 11 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 12 | % This file is part of Introduction to Radar Using Python and MATLAB 13 | % and can not be copied and/or distributed without the express permission of Artech House. 14 | 15 | % Calculate the relative water temperature 16 | theta = 300 / liquid_water_temperature; 17 | 18 | % Calculate the principal and secondary relaxation frequencies 19 | fp = 20.20 - 146. * (theta - 1.) + 316. * (theta - 1.)^2; 20 | fs = 39.8 * fp; 21 | 22 | % Preliminary calculations for the permittivity 23 | eps_0 = 77.66 + 103.3 *(theta - 1.); 24 | eps_1 = 0.0671 * eps_0; 25 | eps_2 = 3.52; 26 | 27 | % Calculate the complex permittivity 28 | eps_p = (eps_0 - eps_1) ./ (1. + (frequency/fp).^2) + (eps_1 - eps_2) ./ (1. + (frequency/fs).^2); 29 | 30 | eps_pp = frequency * (eps_0 - eps_1) ./ (fp * (1. + (frequency/fp).^2)) + frequency * (eps_1 - eps_2) ./ (fs * (1. + (frequency/fs).^2)); 31 | 32 | % Calculate the impedance 33 | eta = (2. + eps_p) ./ eps_pp; 34 | 35 | % Calculate the specific impedance 36 | k_l = 0.819 .* frequency ./ (eps_pp .* (1 + eta.^2)); 37 | 38 | attenuation = k_l .* liquid_water_density; 39 | -------------------------------------------------------------------------------- /mlradar/libs/wave_propagation/critical_angle.m: -------------------------------------------------------------------------------- 1 | function theta = critical_angle(frequency, relative_permittivity, relative_permeability, conductivity) 2 | %% Calculate the critical angle for total reflection. 3 | % :param frequency: The operating frequency (Hz). 4 | % :param relative_permittivity: The relative permittivty. 5 | % :param relative_permeability: The relative permeability. 6 | % :param conductivity: The conductivity (S). 7 | % :return: The critical angle (radians). 8 | % 9 | % Created by: Lee A. Harrison 10 | % On: 6/18/2018 11 | % 12 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 13 | % This file is part of Introduction to Radar Using Python and MATLAB 14 | % and can not be copied and/or distributed without the express permission of Artech House. 15 | 16 | % Get the wave impedance and propagation constant for each material 17 | pw = plane_wave_parameters(frequency, relative_permittivity, relative_permeability, conductivity); 18 | 19 | theta = asin(pw.propagation_constant(2) / pw.propagation_constant(1)) * 180. / pi; -------------------------------------------------------------------------------- /mlradar/libs/wave_propagation/ducting.m: -------------------------------------------------------------------------------- 1 | function critical_angle = ducting(refractivity_gradient, duct_thickness) 2 | %% Calculate the critical angle for ducting. 3 | % :param refractivity_gradient: The refractivity gradient (N/km). 4 | % :param duct_thickness: The duct thickness (meters). 5 | % :return: The critical angle for ducting to occur (radians). 6 | % 7 | % Created by: Lee A. Harrison 8 | % On: 6/18/2018 9 | % 10 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 11 | % This file is part of Introduction to Radar Using Python and MATLAB 12 | % and can not be copied and/or distributed without the express permission of Artech House. 13 | 14 | for iDuct = 1:numel(duct_thickness) 15 | critical_angle(iDuct,:) = sqrt(2.e-6 * abs(refractivity_gradient) * duct_thickness(iDuct) * 1e-3); 16 | end -------------------------------------------------------------------------------- /mlradar/libs/wave_propagation/plane_wave_parameters.m: -------------------------------------------------------------------------------- 1 | function pw = plane_wave_parameters(frequency, relative_permittivity, relative_permeability, conductivity) 2 | %% Calculate the parameters from Table 2.2. 3 | % :param frequency: The operating frequency (Hz). 4 | % :param relative_permittivity: The relative permittivity. 5 | % :param relative_permeability: The relative permeability. 6 | % :param conductivity: The conductivity (S). 7 | % :return: The parameters listed in Table 2.2. 8 | % 9 | % Created by: Lee A. Harrison 10 | % On: 6/18/2018 11 | % 12 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 13 | % This file is part of Introduction to Radar Using Python and MATLAB 14 | % and can not be copied and/or distributed without the express permission of Artech House. 15 | 16 | mu_0 = 4 * pi * 1e-7; 17 | epsilon_0 = 8.854187817620389e-12; 18 | 19 | % Calculate the angular frequency and material parameters 20 | omega = 2.0 * pi * frequency; 21 | mu = relative_permeability * mu_0; 22 | epsilon = relative_permittivity * epsilon_0; 23 | 24 | % Calculate the propagation constant 25 | pw.propagation_constant = 1j * omega .* sqrt(mu .* epsilon) .* sqrt(1 - 1j * conductivity ./ (omega * epsilon)); 26 | 27 | % Calculate the phase constant 28 | pw.phase_constant = imag(pw.propagation_constant); 29 | 30 | % Calculate the attenuation constant 31 | pw.attenuation_constant = real(pw.propagation_constant); 32 | 33 | % Calculate the wave impedance 34 | pw.wave_impedance = 1j * omega .* mu ./ pw.propagation_constant; 35 | 36 | % Calculate the skin depth 37 | i = pw.attenuation_constant == 0; 38 | pw.skin_depth(i) = 0.0; 39 | 40 | i= pw.attenuation_constant ~= 0; 41 | pw.skin_depth(i) = 1. ./ pw.attenuation_constant(i); 42 | 43 | % Calculate the wavelength and phase velocity 44 | pw.wavelength = 2. * pi ./ pw.phase_constant; 45 | pw.phase_velocity = omega ./ pw.phase_constant; -------------------------------------------------------------------------------- /mlradar/libs/wave_propagation/vegetation_attenuation.m: -------------------------------------------------------------------------------- 1 | function attenuation = vegetation_attenuation(distance, specific_attenuation, maximum_attenuation) 2 | %% Calculate the attenuation due to vegetation. 3 | % :param distance: The distance into the vegetation (meters). 4 | % :param specific_attenuation: The specific attenuation of the vegetation (dB/km). 5 | % :param maximum_attenuation: The maximum attenuation of the vegetation (dB). 6 | % :return: The attenuation due to the vegetation (dB). 7 | % 8 | % Created by: Lee A. Harrison 9 | % On: 6/18/2018 10 | % 11 | % Copyright (C) 2019 Artech House (artech@artechhouse.com) 12 | % This file is part of Introduction to Radar Using Python and MATLAB 13 | % and can not be copied and/or distributed without the express permission of Artech House. 14 | 15 | attenuation = maximum_attenuation * (1. - exp(-distance * specific_attenuation / maximum_attenuation)); -------------------------------------------------------------------------------- /mlradar/libs/wave_propagation/water_vapor_spectral_attenuation.txt: -------------------------------------------------------------------------------- 1 | 22.235080 .1079 2.144 26.38 .76 5.087 1.00 2 | 67.803960 .0011 8.732 28.58 .69 4.930 .82 3 | 119.995940 .0007 8.353 29.48 .70 4.780 .79 4 | 183.310087 2.273 .668 29.06 .77 5.022 .85 5 | 321.225630 .0470 6.179 24.04 .67 4.398 .54 6 | 325.152888 1.514 1.541 28.23 .64 4.893 .74 7 | 336.227764 .0010 9.825 26.93 .69 4.740 .61 8 | 380.197353 11.67 1.048 28.11 .54 5.063 .89 9 | 390.134508 .0045 7.347 21.52 .63 4.810 .55 10 | 437.346667 .0632 5.048 18.45 .60 4.230 .48 11 | 439.150807 .9098 3.595 20.07 .63 4.483 .52 12 | 443.018343 .1920 5.048 15.55 .60 5.083 .50 13 | 448.001085 10.41 1.405 25.64 .66 5.028 .67 14 | 470.888999 .3254 3.597 21.34 .66 4.506 .65 15 | 474.689092 1.260 2.379 23.20 .65 4.804 .64 16 | 488.490108 .2529 2.852 25.86 .69 5.201 .72 17 | 503.568532 .0372 6.731 16.12 .61 3.980 .43 18 | 504.482692 .0124 6.731 16.12 .61 4.010 .45 19 | 547.676440 .9785 .158 26.00 .70 4.500 1.00 20 | 552.020960 .1840 .158 26.00 .70 4.500 1.00 21 | 556.935985 497.0 .159 30.86 .69 4.552 1.00 22 | 620.700807 5.015 2.391 24.38 .71 4.856 .68 23 | 645.766085 .0067 8.633 18.00 .60 4.000 .50 24 | 658.005280 .2732 7.816 32.10 .69 4.140 1.00 25 | 752.033113 243.4 .396 30.86 .68 4.352 .84 26 | 841.051732 .0134 8.177 15.90 .33 5.760 .45 27 | 859.965698 .1325 8.055 30.60 .68 4.090 .84 28 | 899.303175 .0547 7.914 29.85 .68 4.530 .90 29 | 902.611085 .0386 8.429 28.65 .70 5.100 .95 30 | 906.205957 .1836 5.110 24.08 .70 4.700 .53 31 | 916.171582 8.400 1.441 26.73 .70 5.150 .78 32 | 923.112692 .0079 10.293 29.00 .70 5.000 .80 33 | 970.315022 9.009 1.919 25.50 .64 4.940 .67 34 | 987.926764 134.6 .257 29.85 .68 4.550 .90 35 | 1780.0 22300.0 0.952 176.20 .50 30.5 5.0 -------------------------------------------------------------------------------- /pyradar/Chapter01/__init__.py: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/RadarBook/software/971a6407379fc0dc9fe8f37b118a6fd1e7d59d2d/pyradar/Chapter01/__init__.py -------------------------------------------------------------------------------- /pyradar/Chapter01/ui/__init__.py: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/RadarBook/software/971a6407379fc0dc9fe8f37b118a6fd1e7d59d2d/pyradar/Chapter01/ui/__init__.py -------------------------------------------------------------------------------- /pyradar/Chapter02/__init__.py: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/RadarBook/software/971a6407379fc0dc9fe8f37b118a6fd1e7d59d2d/pyradar/Chapter02/__init__.py -------------------------------------------------------------------------------- /pyradar/Chapter02/ui/__init__.py: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/RadarBook/software/971a6407379fc0dc9fe8f37b118a6fd1e7d59d2d/pyradar/Chapter02/ui/__init__.py -------------------------------------------------------------------------------- /pyradar/Chapter03/__init__.py: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/RadarBook/software/971a6407379fc0dc9fe8f37b118a6fd1e7d59d2d/pyradar/Chapter03/__init__.py -------------------------------------------------------------------------------- /pyradar/Chapter03/ui/__init__.py: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/RadarBook/software/971a6407379fc0dc9fe8f37b118a6fd1e7d59d2d/pyradar/Chapter03/ui/__init__.py -------------------------------------------------------------------------------- /pyradar/Chapter04/__init__.py: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/RadarBook/software/971a6407379fc0dc9fe8f37b118a6fd1e7d59d2d/pyradar/Chapter04/__init__.py -------------------------------------------------------------------------------- /pyradar/Chapter04/ui/__init__.py: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/RadarBook/software/971a6407379fc0dc9fe8f37b118a6fd1e7d59d2d/pyradar/Chapter04/ui/__init__.py -------------------------------------------------------------------------------- /pyradar/Chapter05/__init__.py: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/RadarBook/software/971a6407379fc0dc9fe8f37b118a6fd1e7d59d2d/pyradar/Chapter05/__init__.py -------------------------------------------------------------------------------- /pyradar/Chapter05/ui/BinaryIntegration_ui.py: -------------------------------------------------------------------------------- 1 | # -*- coding: utf-8 -*- 2 | 3 | # Form implementation generated from reading ui file 'Chapter05\BinaryIntegration.ui' 4 | # 5 | # Created by: PyQt5 UI code generator 5.10 6 | # 7 | # WARNING! All changes made in this file will be lost! 8 | 9 | -------------------------------------------------------------------------------- /pyradar/Chapter05/ui/CFAR_ui.py: -------------------------------------------------------------------------------- 1 | # -*- coding: utf-8 -*- 2 | 3 | # Form implementation generated from reading ui file 'Chapter05\CFAR.ui' 4 | # 5 | # Created by: PyQt5 UI code generator 5.10 6 | # 7 | # WARNING! All changes made in this file will be lost! 8 | 9 | -------------------------------------------------------------------------------- /pyradar/Chapter05/ui/__init__.py: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/RadarBook/software/971a6407379fc0dc9fe8f37b118a6fd1e7d59d2d/pyradar/Chapter05/ui/__init__.py -------------------------------------------------------------------------------- /pyradar/Chapter06/__init__.py: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/RadarBook/software/971a6407379fc0dc9fe8f37b118a6fd1e7d59d2d/pyradar/Chapter06/__init__.py -------------------------------------------------------------------------------- /pyradar/Chapter06/ui/RayleignNoisePd_ui.py: -------------------------------------------------------------------------------- 1 | # -*- coding: utf-8 -*- 2 | 3 | # Form implementation generated from reading ui file 'Chapter06\RayleignNoisePd.ui' 4 | # 5 | # Created by: PyQt5 UI code generator 5.10 6 | # 7 | # WARNING! All changes made in this file will be lost! 8 | 9 | -------------------------------------------------------------------------------- /pyradar/Chapter06/ui/SinglePulsePd_ui.py: -------------------------------------------------------------------------------- 1 | # -*- coding: utf-8 -*- 2 | 3 | # Form implementation generated from reading ui file 'Chapter06\SinglePulsePd.ui' 4 | # 5 | # Created by: PyQt5 UI code generator 5.10 6 | # 7 | # WARNING! All changes made in this file will be lost! 8 | 9 | -------------------------------------------------------------------------------- /pyradar/Chapter06/ui/__init__.py: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/RadarBook/software/971a6407379fc0dc9fe8f37b118a6fd1e7d59d2d/pyradar/Chapter06/ui/__init__.py -------------------------------------------------------------------------------- /pyradar/Chapter07/__init__.py: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/RadarBook/software/971a6407379fc0dc9fe8f37b118a6fd1e7d59d2d/pyradar/Chapter07/__init__.py -------------------------------------------------------------------------------- /pyradar/Chapter07/ui/__init__.py: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/RadarBook/software/971a6407379fc0dc9fe8f37b118a6fd1e7d59d2d/pyradar/Chapter07/ui/__init__.py -------------------------------------------------------------------------------- /pyradar/Chapter08/__init__.py: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/RadarBook/software/971a6407379fc0dc9fe8f37b118a6fd1e7d59d2d/pyradar/Chapter08/__init__.py -------------------------------------------------------------------------------- /pyradar/Chapter08/ui/__init__.py: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/RadarBook/software/971a6407379fc0dc9fe8f37b118a6fd1e7d59d2d/pyradar/Chapter08/ui/__init__.py -------------------------------------------------------------------------------- /pyradar/Chapter09/__init__.py: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/RadarBook/software/971a6407379fc0dc9fe8f37b118a6fd1e7d59d2d/pyradar/Chapter09/__init__.py -------------------------------------------------------------------------------- /pyradar/Chapter09/ui/__init__.py: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/RadarBook/software/971a6407379fc0dc9fe8f37b118a6fd1e7d59d2d/pyradar/Chapter09/ui/__init__.py -------------------------------------------------------------------------------- /pyradar/Chapter10/__init__.py: -------------------------------------------------------------------------------- 1 | """ 2 | Project: RadarBook 3 | File: __init__.py.py 4 | Created by: Lee A. Harrison 5 | One: 2/10/2019 6 | Created with: PyCharm 7 | """ -------------------------------------------------------------------------------- /pyradar/Chapter10/ui/__init__.py: -------------------------------------------------------------------------------- 1 | """ 2 | Project: RadarBook 3 | File: __init__.py.py 4 | Created by: Lee A. Harrison 5 | One: 2/10/2019 6 | Created with: PyCharm 7 | """ -------------------------------------------------------------------------------- /pyradar/Chapter11/__init__.py: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/RadarBook/software/971a6407379fc0dc9fe8f37b118a6fd1e7d59d2d/pyradar/Chapter11/__init__.py -------------------------------------------------------------------------------- /pyradar/Chapter11/ui/__init__.py: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/RadarBook/software/971a6407379fc0dc9fe8f37b118a6fd1e7d59d2d/pyradar/Chapter11/ui/__init__.py -------------------------------------------------------------------------------- /pyradar/Libs/__init__.py: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/RadarBook/software/971a6407379fc0dc9fe8f37b118a6fd1e7d59d2d/pyradar/Libs/__init__.py -------------------------------------------------------------------------------- /pyradar/Libs/ambiguity/__init__.py: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/RadarBook/software/971a6407379fc0dc9fe8f37b118a6fd1e7d59d2d/pyradar/Libs/ambiguity/__init__.py -------------------------------------------------------------------------------- /pyradar/Libs/ambiguity/frank_code.py: -------------------------------------------------------------------------------- 1 | """ 2 | Project: RadarBook 3 | File: frank_code.py 4 | Created by: Lee A. Harrison 5 | One: 1/26/2019 6 | Created with: PyCharm 7 | 8 | Copyright (C) 2019 Artech House (artech@artechhouse.com) 9 | This file is part of Introduction to Radar Using Python and MATLAB 10 | and can not be copied and/or distributed without the express permission of Artech House. 11 | """ 12 | from scipy.constants import pi 13 | from numpy import exp 14 | 15 | 16 | def n_phase_code(n): 17 | """ 18 | Generate an N-phase Frank code sequence. 19 | :param n: The sequence groups. 20 | :return: The Frank code sequence (length N^2). 21 | """ 22 | phi = [2.0 * pi / float(n) * i * j for i in range(n) for j in range(n)] 23 | return [exp(1j * p) for p in phi] 24 | -------------------------------------------------------------------------------- /pyradar/Libs/ambiguity/prn_code.py: -------------------------------------------------------------------------------- 1 | """ 2 | Project: RadarBook 3 | File: prn_code.py 4 | Created by: Lee A. Harrison 5 | One: 1/25/2019 6 | Created with: PyCharm 7 | 8 | Copyright (C) 2019 Artech House (artech@artechhouse.com) 9 | This file is part of Introduction to Radar Using Python and MATLAB 10 | and can not be copied and/or distributed without the express permission of Artech House. 11 | """ 12 | 13 | 14 | def mls(register_length, feedback_taps): 15 | """ 16 | Generate a maximum length sequence based on the register length and feedback taps. 17 | :param register_length: The length of the linear feedback shift register. 18 | :param feedback_taps: The bits to use as feedback. 19 | :return: The maximum length sequence. 20 | """ 21 | # Initialize the linear feedback shift register 22 | register = [i % 2 for i in range(register_length)] 23 | 24 | # For the output sequence 25 | sequence = [] 26 | 27 | # Generate the output PRN based on the register length 28 | for i in range(2 ** register_length - 1): 29 | 30 | # Calculate the feedback based on the taps and modulo 2 addition 31 | s = sum([register[i - 1] for i in feedback_taps]) % 2 32 | 33 | # Shift bits to the rights 34 | for k in reversed(range(len(register[1:]))): 35 | register[k + 1] = register[k] 36 | 37 | # Stored feedback into bit 0 38 | register[0] = s 39 | 40 | # Append the output sequence 41 | sequence.append(register[register_length - 1]) 42 | 43 | return [-1 if x == 0 else x for x in sequence] 44 | -------------------------------------------------------------------------------- /pyradar/Libs/antenna/__init__.py: -------------------------------------------------------------------------------- 1 | """ 2 | Project: RadarBook 3 | Module: __init__.py 4 | Author: aharrison 5 | 6 | Created: January 1/22/2018 9:55 AM 7 | """ -------------------------------------------------------------------------------- /pyradar/Libs/antenna/aperture/__init__.py: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/RadarBook/software/971a6407379fc0dc9fe8f37b118a6fd1e7d59d2d/pyradar/Libs/antenna/aperture/__init__.py -------------------------------------------------------------------------------- /pyradar/Libs/antenna/array/__init__.py: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/RadarBook/software/971a6407379fc0dc9fe8f37b118a6fd1e7d59d2d/pyradar/Libs/antenna/array/__init__.py -------------------------------------------------------------------------------- /pyradar/Libs/antenna/array/circular_uniform.py: -------------------------------------------------------------------------------- 1 | """ 2 | Project: RadarBook 3 | File: circular_uniform.py 4 | Created by: Lee A. Harrison 5 | On: 7/6/2018 6 | Created with: PyCharm 7 | 8 | Copyright (C) 2019 Artech House (artech@artechhouse.com) 9 | This file is part of Introduction to Radar Using Python and MATLAB 10 | and can not be copied and/or distributed without the express permission of Artech House. 11 | """ 12 | from scipy.constants import pi, c 13 | from numpy import sin, cos, amax, arange, exp 14 | 15 | 16 | def array_factor(number_of_elements, radius, frequency, scan_angle_theta, scan_angle_phi, theta, phi): 17 | """ 18 | Calculate the array factor for a circular uniform array. 19 | :param number_of_elements: The number of elements in the array. 20 | :param radius: The radius of the circular loop (m). 21 | :param frequency: The operating frequency (Hz). 22 | :param scan_angle_theta: The theta scan angle of the main beam (rad). 23 | :param scan_angle_phi: The phi scan angle of the main beam (rad). 24 | :param theta: The theta pattern angle (rad). 25 | :param phi: The phi pattern angle (rad). 26 | :return: The array factor of a circular uniform array. 27 | """ 28 | # Calculate the wavenumber 29 | k = 2.0 * pi * frequency / c 30 | 31 | # Calculate the angular position of each element 32 | phi_n = 2.0 * pi / number_of_elements * arange(number_of_elements) 33 | 34 | # Calculate the phase term 35 | af = 0.0 36 | for p in phi_n: 37 | af += exp(1j * (k * radius) * (sin(theta) * cos(phi - p) - sin(scan_angle_theta) * cos(scan_angle_phi - p))) 38 | 39 | return af / amax(af) 40 | -------------------------------------------------------------------------------- /pyradar/Libs/antenna/horn/__init__.py: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/RadarBook/software/971a6407379fc0dc9fe8f37b118a6fd1e7d59d2d/pyradar/Libs/antenna/horn/__init__.py -------------------------------------------------------------------------------- /pyradar/Libs/antenna/linear_wire/__init__.py: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/RadarBook/software/971a6407379fc0dc9fe8f37b118a6fd1e7d59d2d/pyradar/Libs/antenna/linear_wire/__init__.py -------------------------------------------------------------------------------- /pyradar/Libs/antenna/loop/__init__.py: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/RadarBook/software/971a6407379fc0dc9fe8f37b118a6fd1e7d59d2d/pyradar/Libs/antenna/loop/__init__.py -------------------------------------------------------------------------------- /pyradar/Libs/detection/__init__.py: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/RadarBook/software/971a6407379fc0dc9fe8f37b118a6fd1e7d59d2d/pyradar/Libs/detection/__init__.py -------------------------------------------------------------------------------- /pyradar/Libs/detection/binary_integration.py: -------------------------------------------------------------------------------- 1 | """ 2 | Project: RadarBook 3 | File: binary_integration.py 4 | Created by: Lee A. Harrison 5 | One: 10/11/2018 6 | Created with: PyCharm 7 | 8 | Copyright (C) 2019 Artech House (artech@artechhouse.com) 9 | This file is part of Introduction to Radar Using Python and MATLAB 10 | and can not be copied and/or distributed without the express permission of Artech House. 11 | """ 12 | from scipy.special import binom 13 | 14 | 15 | def probability_of_detection(m, n, pd): 16 | """ 17 | Calculate the probability of detection for M of N integration. 18 | :param m: The number of required detections. 19 | :param n: The total number of measurements. 20 | :param pd: The probability of detection for a single measurement. 21 | :return: The probability of M on N detections. 22 | """ 23 | return sum([binom(n, k) * pd ** k * (1.0 - pd) ** (n - k) for k in range(m, n + 1)]) 24 | 25 | 26 | def probability_of_false_alarm(m, n, pfa): 27 | """ 28 | Calcualte the probability of false alarm for M of N integration. 29 | :param m: The number of required detections. 30 | :param n: The total number of measurements. 31 | :param pfa: The probability of false alarm for a single measurement. 32 | :return: The probability false alarm for M on N detections. 33 | """ 34 | return sum([binom(n, k) * pfa ** k * (1.0 - pfa) ** (n - k) for k in range(m, n + 1)]) 35 | -------------------------------------------------------------------------------- /pyradar/Libs/ecm/__init__.py: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/RadarBook/software/971a6407379fc0dc9fe8f37b118a6fd1e7d59d2d/pyradar/Libs/ecm/__init__.py -------------------------------------------------------------------------------- /pyradar/Libs/python_icon.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/RadarBook/software/971a6407379fc0dc9fe8f37b118a6fd1e7d59d2d/pyradar/Libs/python_icon.png -------------------------------------------------------------------------------- /pyradar/Libs/radar_range/__init__.py: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/RadarBook/software/971a6407379fc0dc9fe8f37b118a6fd1e7d59d2d/pyradar/Libs/radar_range/__init__.py -------------------------------------------------------------------------------- /pyradar/Libs/rcs/__init__.py: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/RadarBook/software/971a6407379fc0dc9fe8f37b118a6fd1e7d59d2d/pyradar/Libs/rcs/__init__.py -------------------------------------------------------------------------------- /pyradar/Libs/rcs/cone.facet: -------------------------------------------------------------------------------- 1 | Cone 2 | 22 3 | 0 0 0 4 | 1.4000 0 0 5 | 1.3315 0.4326 0 6 | 1.1326 0.8229 0 7 | 0.8229 1.1326 0 8 | 0.4326 1.3315 0 9 | 0.0000 1.4000 0 10 | -0.4326 1.3315 0 11 | -0.8229 1.1326 0 12 | -1.1326 0.8229 0 13 | -1.3315 0.4326 0 14 | -1.4000 0.0000 0 15 | -1.3315 -0.4326 0 16 | -1.1326 -0.8229 0 17 | -0.8229 -1.1326 0 18 | -0.4326 -1.3315 0 19 | -0.0000 -1.4000 0 20 | 0.4326 -1.3315 0 21 | 0.8229 -1.1326 0 22 | 1.1326 -0.8229 0 23 | 1.3315 -0.4326 0 24 | 0 0 5.2248 25 | 40 26 | 0 2 1 27 | 0 3 2 28 | 0 4 3 29 | 0 5 4 30 | 0 6 5 31 | 0 7 6 32 | 0 8 7 33 | 0 9 8 34 | 0 10 9 35 | 0 11 10 36 | 0 12 11 37 | 0 13 12 38 | 0 14 13 39 | 0 15 14 40 | 0 16 15 41 | 0 17 16 42 | 0 18 17 43 | 0 19 18 44 | 0 20 19 45 | 0 1 20 46 | 21 1 2 47 | 21 2 3 48 | 21 3 4 49 | 21 4 5 50 | 21 5 6 51 | 21 6 7 52 | 21 7 8 53 | 21 8 9 54 | 21 9 10 55 | 21 10 11 56 | 21 11 12 57 | 21 12 13 58 | 21 13 14 59 | 21 14 15 60 | 21 15 16 61 | 21 16 17 62 | 21 17 18 63 | 21 18 19 64 | 21 19 20 65 | 21 20 1 -------------------------------------------------------------------------------- /pyradar/Libs/rcs/infinite_strip.py: -------------------------------------------------------------------------------- 1 | """ 2 | Project: RadarBook 3 | File: infinite_strip.py 4 | Created by: Lee A. Harrison 5 | On: 10/30/2018 6 | Created with: PyCharm 7 | 8 | Copyright (C) 2019 Artech House (artech@artechhouse.com) 9 | This file is part of Introduction to Radar Using Python and MATLAB 10 | and can not be copied and/or distributed without the express permission of Artech House. 11 | """ 12 | from numpy import radians, sin, cos, sinc 13 | from scipy.constants import c, pi 14 | 15 | 16 | def radar_cross_section(frequency, width, incident_angle, observation_angle): 17 | """ 18 | Calculate the bistatic radar cross section for a 2D strip. 19 | :param frequency: The frequency of the incident energy (Hz). 20 | :param width: The width of the strip (m). 21 | :param incident_angle: The incident angle (deg). 22 | :param observation_angle: The observation angle (deg). 23 | :return: The bistatic radar cross section (m^2). 24 | """ 25 | # Wavelength 26 | wavelength = c / frequency 27 | 28 | # Wavenumber 29 | k = 2.0 * pi / wavelength 30 | 31 | phi_i = radians(incident_angle) 32 | phi_o = radians(observation_angle) 33 | 34 | rcs_tm = k * width ** 2 * sin(phi_i) * sinc(width / wavelength * (cos(phi_o) + cos(phi_i))) ** 2 35 | 36 | rcs_te = k * width ** 2 * sin(phi_o) * sinc(width / wavelength * (cos(phi_o) + cos(phi_i))) ** 2 37 | 38 | return rcs_tm, rcs_te 39 | -------------------------------------------------------------------------------- /pyradar/Libs/rcs/plate.facet: -------------------------------------------------------------------------------- 1 | Rectangular Plate 2 | 4 3 | 0.0 0.0 0.0 4 | 3.0 0.0 0.0 5 | 0.0 5.0 0.0 6 | 3.0 5.0 0.0 7 | 2 8 | 0 1 2 9 | 1 3 2 -------------------------------------------------------------------------------- /pyradar/Libs/receivers/__init__.py: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/RadarBook/software/971a6407379fc0dc9fe8f37b118a6fd1e7d59d2d/pyradar/Libs/receivers/__init__.py -------------------------------------------------------------------------------- /pyradar/Libs/receivers/envelope_detector.py: -------------------------------------------------------------------------------- 1 | """ 2 | Project: RadarBook 3 | File: envelope_detector.py 4 | Created by: Lee A. Harrison 5 | On: 9/18/2018 6 | Created with: PyCharm 7 | 8 | Copyright (C) 2019 Artech House (artech@artechhouse.com) 9 | This file is part of Introduction to Radar Using Python and MATLAB 10 | and can not be copied and/or distributed without the express permission of Artech House. 11 | """ 12 | from scipy.signal import hilbert 13 | 14 | 15 | def envelope(if_signal): 16 | """ 17 | Calculate the amplitude envelope of the IF signal. 18 | :param if_signal: The signal at IF. 19 | :return: The amplitude envelope. 20 | """ 21 | return abs(hilbert(if_signal)) 22 | -------------------------------------------------------------------------------- /pyradar/Libs/receivers/noise_figure.py: -------------------------------------------------------------------------------- 1 | """ 2 | Project: RadarBook 3 | File: noise_figure.py 4 | Created by: Lee A. Harrison 5 | On: 9/18/2018 6 | Created with: PyCharm 7 | 8 | Copyright (C) 2019 Artech House (artech@artechhouse.com) 9 | This file is part of Introduction to Radar Using Python and MATLAB 10 | and can not be copied and/or distributed without the express permission of Artech House. 11 | """ 12 | from numpy import log10, prod 13 | 14 | 15 | def total_noise_figure(gain, noise_figure): 16 | """ 17 | Calculate the total noise figure for a cascaded network. 18 | :param gain: The gain of each component (dB). 19 | :param noise_figure: The noise figure of each component (dB). 20 | :return: The total noise figure (dB). 21 | """ 22 | 23 | # Convert noise figure and gain to linear units 24 | noise_factor = [10.0 ** (nf / 10.0) for nf in noise_figure] 25 | gain_linear = [10.0 ** (g / 10.0) for g in gain] 26 | 27 | # Start with the first component 28 | total = noise_factor[0] 29 | 30 | # Loop over the remaining components 31 | i = 1 32 | for nf in noise_factor[1:]: 33 | total += (nf - 1.0) / prod(gain_linear[:i]) 34 | i += 1 35 | 36 | # Return the total noise figure 37 | return 10.0 * log10(total) 38 | -------------------------------------------------------------------------------- /pyradar/Libs/receivers/quantization.py: -------------------------------------------------------------------------------- 1 | """ 2 | Project: RadarBook 3 | File: quantization.py 4 | Created by: Lee A. Harrison 5 | On: 9/19/2018 6 | Created with: PyCharm 7 | 8 | Copyright (C) 2019 Artech House (artech@artechhouse.com) 9 | This file is part of Introduction to Radar Using Python and MATLAB 10 | and can not be copied and/or distributed without the express permission of Artech House. 11 | """ 12 | from numpy import around 13 | 14 | 15 | def quantize(if_signal, number_of_bits): 16 | """ 17 | Calculate the quantized signal for a given number of bits. 18 | :param if_signal: The sampled analog signal to be quantized. 19 | :param number_of_bits: The number of bits in the ADC. 20 | :return: The quantized signal. 21 | """ 22 | # Calculate the LSB level 23 | lsb = 2.0 / (2.0 ** number_of_bits - 1) 24 | 25 | # Calculate the quantized signal 26 | quantized_signal = lsb * around((if_signal + 1.0) / lsb) - 1.0 27 | 28 | # Calculate the error between the analog signal and the quantized signal 29 | error_signal = if_signal - quantized_signal 30 | 31 | return quantized_signal, error_signal 32 | -------------------------------------------------------------------------------- /pyradar/Libs/receivers/sensitivity_time_control.py: -------------------------------------------------------------------------------- 1 | """ 2 | Project: RadarBook 3 | File: sensitivity_time_control.py 4 | Created by: Lee A. Harrison 5 | On: 9/18/2018 6 | Created with: PyCharm 7 | 8 | Copyright (C) 2019 Artech House (artech@artechhouse.com) 9 | This file is part of Introduction to Radar Using Python and MATLAB 10 | and can not be copied and/or distributed without the express permission of Artech House. 11 | """ 12 | from scipy.constants import c 13 | from numpy import linspace 14 | 15 | 16 | def attenuation(pulse_repetition_frequency, pulse_width): 17 | """ 18 | Calculate the STC attenuation. 19 | :param pulse_repetition_frequency: The PRF (Hz). 20 | :param pulse_width: The pulse width (s). 21 | :return: The normalized STC attenuation. 22 | """ 23 | # Calculate the PRI 24 | pulse_repetition_interval = 1.0 / pulse_repetition_frequency 25 | 26 | # Find the minimum and maximum ranges 27 | minimum_range = 0.5 * c * pulse_width 28 | maximum_range = 0.5 * c * pulse_repetition_interval 29 | 30 | # Set up the range array 31 | receive_range = linspace(0, maximum_range, 1000) 32 | 33 | # Calculate and return the attenuation 34 | return receive_range, [1.0 / minimum_range ** 3.5 if r < minimum_range else 1.0 / r ** 3.5 for r in receive_range] 35 | -------------------------------------------------------------------------------- /pyradar/Libs/resources.qrc: -------------------------------------------------------------------------------- 1 | 2 | 3 | python_icon.png 4 | 5 | 6 | -------------------------------------------------------------------------------- /pyradar/Libs/sar/__init__.py: -------------------------------------------------------------------------------- 1 | """ 2 | Project: RadarBook 3 | File: __init__.py.py 4 | Created by: Lee A. Harrison 5 | One: 2/9/2019 6 | Created with: PyCharm 7 | """ -------------------------------------------------------------------------------- /pyradar/Libs/tracking/__init__.py: -------------------------------------------------------------------------------- 1 | """ 2 | Project: RadarBook 3 | File: __init__.py.py 4 | Created by: Lee A. Harrison 5 | One: 3/6/2019 6 | Created with: PyCharm 7 | """ -------------------------------------------------------------------------------- /pyradar/Libs/utils/__init__.py: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/RadarBook/software/971a6407379fc0dc9fe8f37b118a6fd1e7d59d2d/pyradar/Libs/utils/__init__.py -------------------------------------------------------------------------------- /pyradar/Libs/utils/ecef_to_lla.py: -------------------------------------------------------------------------------- 1 | """ 2 | Project: RadarBook 3 | File: ecef_to_lla.py 4 | Created by: Lee A. Harrison 5 | On: 3/18/2018 6 | Created with: PyCharm 7 | 8 | Copyright (C) 2019 Artech House (artech@artechhouse.com) 9 | This file is part of Introduction to Radar Using Python and MATLAB 10 | and can not be copied and/or distributed without the express permission of Artech House. 11 | """ 12 | from numpy import sqrt, sin, cos, arctan2, mod 13 | from scipy.constants import pi 14 | 15 | 16 | def convert(ecef_x, ecef_y, ecef_z): 17 | """ 18 | Convert coordinates in ECEF to LLA. 19 | :param ecef_x: The x coordinate of the point (m). 20 | :param ecef_y: The y coordinate of the point (m). 21 | :param ecef_z: The z coordinate of the point (m). 22 | :return: The LLA coordinates of the point (rad, rad, m). 23 | """ 24 | # Earth constants 25 | effective_earth_radius = 6378137 26 | earth_eccentricity = 8.1819190842622e-2 27 | 28 | # Effective polar radius 29 | earth_radius_polar = sqrt(effective_earth_radius**2 * (1. - earth_eccentricity**2)) 30 | 31 | ep = sqrt((effective_earth_radius**2 - earth_radius_polar**2) / earth_radius_polar**2) 32 | 33 | # Radius in xy plane 34 | r = sqrt(ecef_x * ecef_x + ecef_y * ecef_y) 35 | 36 | # Angle from the xy plane 37 | theta = arctan2(effective_earth_radius * ecef_z, earth_radius_polar * r) 38 | 39 | # Calculate the coordinates 40 | lat = arctan2((ecef_z + ep**2 * earth_radius_polar * sin(theta)**3), 41 | (r - earth_eccentricity**2 * effective_earth_radius * cos(theta)**3)) 42 | 43 | lon = mod(arctan2(ecef_y, ecef_x), 2. * pi) 44 | 45 | alt = r / cos(lat) - effective_earth_radius / sqrt(1. - earth_eccentricity**2 * sin(lat)**2) 46 | 47 | return lat, lon, alt 48 | -------------------------------------------------------------------------------- /pyradar/Libs/utils/lla_to_ecef.py: -------------------------------------------------------------------------------- 1 | """ 2 | Project: RadarBook 3 | File: lla_to_ecef.py 4 | Created by: Lee A. Harrison 5 | On: 3/18/2018 6 | Created with: PyCharm 7 | 8 | Copyright (C) 2019 Artech House (artech@artechhouse.com) 9 | This file is part of Introduction to Radar Using Python and MATLAB 10 | and can not be copied and/or distributed without the express permission of Artech House. 11 | """ 12 | from numpy import sqrt, sin, cos 13 | 14 | 15 | def convert(lat, lon, alt): 16 | """ 17 | Convert coordinates in LLA to ECEF. 18 | :param lat: The latitude of the point (rad). 19 | :param lon: The Longitude of the point (rad). 20 | :param alt: The altitude of the point (m). 21 | :return: The ECEF coordinates of the point (m). 22 | """ 23 | # Earth constants 24 | effective_earth_radius = 6378137 25 | earth_eccentricity = 8.1819190842622e-2 26 | 27 | # Radius of curvature 28 | radius = effective_earth_radius / sqrt(1. - earth_eccentricity ** 2 * sin(lat) ** 2) 29 | 30 | # Calculate the coordinates 31 | ecef_x = (radius + alt) * cos(lat) * cos(lon) 32 | ecef_y = (radius + alt) * cos(lat) * sin(lon) 33 | ecef_z = ((1. - earth_eccentricity**2) * radius + alt) * sin(lat) 34 | 35 | return ecef_x, ecef_y, ecef_z 36 | -------------------------------------------------------------------------------- /pyradar/Libs/utils/plot_settings.py: -------------------------------------------------------------------------------- 1 | """ 2 | Project: RadarBook 3 | File: plot_settings.py 4 | Created by: Lee A. Harrison 5 | On: 3/18/2018 6 | Created with: PyCharm 7 | 8 | Copyright (C) 2019 Artech House (artech@artechhouse.com) 9 | This file is part of Introduction to Radar Using Python and MATLAB 10 | and can not be copied and/or distributed without the express permission of Artech House. 11 | """ 12 | 13 | 14 | def settings(plt): 15 | """ 16 | Set default sizes for plotting, so that all plots are consistent. 17 | :param plt: The pyplot module. 18 | :return: 19 | """ 20 | # Get current size 21 | fig_size = plt.rcParams["figure.figsize"] 22 | 23 | # Set figure width of 12 and height of 9 24 | fig_size[0] = 12 25 | fig_size[1] = 9 26 | plt.rcParams["figure.figsize"] = fig_size 27 | 28 | # Define the sizes for each item 29 | title_size = 16 30 | axis_size = 14 31 | legend_size = 12 32 | 33 | # Use the tight layout 34 | plt.tight_layout() 35 | 36 | # Choose the size for each item 37 | plt.rc('axes', titlesize=title_size) 38 | plt.rc('axes', labelsize=axis_size) 39 | plt.rc('xtick', labelsize=axis_size) 40 | plt.rc('ytick', labelsize=axis_size) 41 | plt.rc('legend', fontsize=legend_size) 42 | 43 | # Turn on the grid 44 | plt.grid(linestyle=':', linewidth=0.5) 45 | 46 | 47 | def default_save(plt, fname): 48 | """ 49 | A default save utility for figures. 50 | :param plt: The pyplot module 51 | :param fname: The filename to use 52 | :return: 53 | """ 54 | plt.savefig(fname, dpi=1200, facecolor='w', edgecolor='w', orientation='portrait', papertype='letter', 55 | format='eps', transparent=False, bbox_inches=None, pad_inches=0.1, frameon=None) 56 | -------------------------------------------------------------------------------- /pyradar/Libs/wave_propagation/__init__.py: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/RadarBook/software/971a6407379fc0dc9fe8f37b118a6fd1e7d59d2d/pyradar/Libs/wave_propagation/__init__.py -------------------------------------------------------------------------------- /pyradar/Libs/wave_propagation/cloud_fog.py: -------------------------------------------------------------------------------- 1 | """ 2 | Project: RadarBook 3 | File: cloud_fog.py 4 | Created by: Lee A. Harrison 5 | On: 3/18/2018 6 | Created with: PyCharm 7 | 8 | Copyright (C) 2019 Artech House (artech@artechhouse.com) 9 | This file is part of Introduction to Radar Using Python and MATLAB 10 | and can not be copied and/or distributed without the express permission of Artech House. 11 | """ 12 | 13 | 14 | def attenuation(frequency, liquid_water_temperature, liquid_water_density): 15 | """ 16 | Calculate the specific attenuation due to cloud or fog. 17 | :param frequency: The operating frequency (GHz). 18 | :param liquid_water_temperature: The liquid water temperature (K). 19 | :param liquid_water_density: The liquid water density (g/m^3) 20 | :return: The specific attenuation (dB/km) 21 | """ 22 | 23 | # Calculate the relative water temperature 24 | theta = 300 / liquid_water_temperature 25 | 26 | # Calculate the principal and secondary relaxation frequencies 27 | fp = 20.20 - 146. * (theta - 1.) + 316. * (theta - 1.)**2 28 | fs = 39.8 * fp 29 | 30 | # Preliminary calculations for the permittivity 31 | eps_0 = 77.66 + 103.3 * (theta - 1.) 32 | eps_1 = 0.0671 * eps_0 33 | eps_2 = 3.52 34 | 35 | # Calculate the complex permittivity 36 | eps_p = (eps_0 - eps_1) / (1. + (frequency/fp)**2) + (eps_1 - eps_2) / (1. + (frequency/fs)**2) 37 | 38 | eps_pp = frequency * (eps_0 - eps_1) / (fp * (1. + (frequency/fp)**2)) + \ 39 | frequency * (eps_1 - eps_2) / (fs * (1. + (frequency/fs)**2)) 40 | 41 | # Calculate the impedance 42 | eta = (2. + eps_p) / eps_pp 43 | 44 | # Calculate the specific impedance 45 | k_l = 0.819 * frequency / (eps_pp * (1 + eta**2)) 46 | 47 | return k_l * liquid_water_density 48 | -------------------------------------------------------------------------------- /pyradar/Libs/wave_propagation/ducting.py: -------------------------------------------------------------------------------- 1 | """ 2 | Project: RadarBook 3 | File: ducting.py 4 | Created by: Lee A. Harrison 5 | On: 3/18/2018 6 | Created with: PyCharm 7 | 8 | Copyright (C) 2019 Artech House (artech@artechhouse.com) 9 | This file is part of Introduction to Radar Using Python and MATLAB 10 | and can not be copied and/or distributed without the express permission of Artech House. 11 | """ 12 | from numpy import sqrt 13 | 14 | 15 | def critical_angle(refractivity_gradient, duct_thickness): 16 | """ 17 | Calculate the critical angle for ducting. 18 | :param refractivity_gradient: The refractivity gradient (N/km). 19 | :param duct_thickness: The duct thickness (meters). 20 | :return: THe critical angle for ducting to occur (radians). 21 | """ 22 | 23 | return sqrt(2.e-6 * abs(refractivity_gradient) * duct_thickness * 1e-3) 24 | -------------------------------------------------------------------------------- /pyradar/Libs/wave_propagation/vegetation.py: -------------------------------------------------------------------------------- 1 | """ 2 | Project: RadarBook 3 | File: vegetation.py 4 | Created by: Lee A. Harrison 5 | On: 3/18/2018 6 | Created with: PyCharm 7 | 8 | Copyright (C) 2019 Artech House (artech@artechhouse.com) 9 | This file is part of Introduction to Radar Using Python and MATLAB 10 | and can not be copied and/or distributed without the express permission of Artech House. 11 | """ 12 | from numpy import exp 13 | 14 | 15 | def attenuation(distance, specific_attenuation, maximum_attenuation): 16 | """ 17 | Calculate the attenuation due to vegetation. 18 | :param distance: The distance into the vegetation (meters). 19 | :param specific_attenuation: The specific attenuation of the vegetation (dB/km). 20 | :param maximum_attenuation: The maximum attenuation of the vegetation (dB). 21 | :return: The attenuation due to the vegetation (dB). 22 | """ 23 | return maximum_attenuation * (1. - exp(-distance * specific_attenuation / maximum_attenuation)) 24 | -------------------------------------------------------------------------------- /pyradar/Libs/wave_propagation/water_vapor_spectral_attenuation.txt: -------------------------------------------------------------------------------- 1 | 22.235080 .1079 2.144 26.38 .76 5.087 1.00 2 | 67.803960 .0011 8.732 28.58 .69 4.930 .82 3 | 119.995940 .0007 8.353 29.48 .70 4.780 .79 4 | 183.310087 2.273 .668 29.06 .77 5.022 .85 5 | 321.225630 .0470 6.179 24.04 .67 4.398 .54 6 | 325.152888 1.514 1.541 28.23 .64 4.893 .74 7 | 336.227764 .0010 9.825 26.93 .69 4.740 .61 8 | 380.197353 11.67 1.048 28.11 .54 5.063 .89 9 | 390.134508 .0045 7.347 21.52 .63 4.810 .55 10 | 437.346667 .0632 5.048 18.45 .60 4.230 .48 11 | 439.150807 .9098 3.595 20.07 .63 4.483 .52 12 | 443.018343 .1920 5.048 15.55 .60 5.083 .50 13 | 448.001085 10.41 1.405 25.64 .66 5.028 .67 14 | 470.888999 .3254 3.597 21.34 .66 4.506 .65 15 | 474.689092 1.260 2.379 23.20 .65 4.804 .64 16 | 488.490108 .2529 2.852 25.86 .69 5.201 .72 17 | 503.568532 .0372 6.731 16.12 .61 3.980 .43 18 | 504.482692 .0124 6.731 16.12 .61 4.010 .45 19 | 547.676440 .9785 .158 26.00 .70 4.500 1.00 20 | 552.020960 .1840 .158 26.00 .70 4.500 1.00 21 | 556.935985 497.0 .159 30.86 .69 4.552 1.00 22 | 620.700807 5.015 2.391 24.38 .71 4.856 .68 23 | 645.766085 .0067 8.633 18.00 .60 4.000 .50 24 | 658.005280 .2732 7.816 32.10 .69 4.140 1.00 25 | 752.033113 243.4 .396 30.86 .68 4.352 .84 26 | 841.051732 .0134 8.177 15.90 .33 5.760 .45 27 | 859.965698 .1325 8.055 30.60 .68 4.090 .84 28 | 899.303175 .0547 7.914 29.85 .68 4.530 .90 29 | 902.611085 .0386 8.429 28.65 .70 5.100 .95 30 | 906.205957 .1836 5.110 24.08 .70 4.700 .53 31 | 916.171582 8.400 1.441 26.73 .70 5.150 .78 32 | 923.112692 .0079 10.293 29.00 .70 5.000 .80 33 | 970.315022 9.009 1.919 25.50 .64 4.940 .67 34 | 987.926764 134.6 .257 29.85 .68 4.550 .90 35 | 1780.0 22300.0 0.952 176.20 .50 30.5 5.0 -------------------------------------------------------------------------------- /pyradar/setup.py: -------------------------------------------------------------------------------- 1 | from setuptools import setup 2 | 3 | setup(name='RadarBook', 4 | version='0.1', 5 | description='Accompanying software for Introduction to Radar using Python and MATLAB', 6 | url='https://github.com/RadarBook/', 7 | author='Lee A. Harrison', 8 | author_email='pythonradarbook@gmail.com', 9 | license='', 10 | packages=['Chapter01','Chapter02','Chapter03','Chapter04','Chapter05','Chapter06','Chapter07','Chapter08','Chapter09','Chapter10','Chapter11','Libs'], 11 | zip_safe=False, 12 | install_requires=[ 13 | 'numpy', 14 | 'scipy', 15 | 'matplotlib', 16 | 'pyqt5', 17 | ]) 18 | --------------------------------------------------------------------------------