コード例 #1
0
    def test_calc_effective_throughput(self):
        psk_obj = fundamental.PSK(8)
        packet_length = 60

        SINRs_dB = np.array([11.4, 20.3])
        sinrs_linear = dB2Linear(SINRs_dB)

        expected_spectral_efficiency = np.sum(
            psk_obj.calcTheoreticalSpectralEfficiency(SINRs_dB, packet_length))

        spectral_efficiency = blockdiagonalization._calc_effective_throughput(
            sinrs_linear, psk_obj, packet_length)

        np.testing.assert_array_almost_equal(spectral_efficiency,
                                             expected_spectral_efficiency)
コード例 #2
0
    def __init__(self, ):
        SimulationRunner.__init__(self)

        SNR = np.array([0, 3, 6, 9, 12])
        M = 4
        self.modulator = fundamental.PSK(M)
        self.NSymbs = 500

        self.rep_max = 1000
        self.max_bit_errors = 1. / 100. * self.NSymbs * self.rep_max

        # self.progressbar_message = None
        self.progressbar_message = "{0}-PSK".format(M) + \
                                   " Simulation - SNR: {SNR}"

        # Add the parameters to the self.params variable
        self.params.add('SNR', SNR)
        self.params.set_unpack_parameter('SNR')
コード例 #3
0
    def __init__(self, ):
        super().__init__()

        SNR = np.array([0, 3, 6, 9, 12])
        M = 4
        modulator = fundamental.PSK(M)
        NSymbs = 500

        self.params.add('modulator', modulator)
        self.params.add('NSymbs', NSymbs)

        self.rep_max = 1000
        # self.max_bit_errors = 1. / 100. * NSymbs * self.rep_max
        max_bit_errors = 1. / 100. * NSymbs * self.rep_max
        self.params.add('max_bit_errors', max_bit_errors)

        # self.progressbar_message = None
        self.progressbar_message = "{0}-PSK".format(M) + \
                                   " Simulation - SNR: {SNR}"

        # Add the parameters to the self.params variable
        self.params.add('SNR', SNR)
        self.params.set_unpack_parameter('SNR')
コード例 #4
0
# xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx
# Cell and Grid Parameters
cell_radius = 1.0  # Cell radius (in Km)
num_cells = 3
num_clusters = 1

# Channel Parameters
Nr = np.ones(num_cells) * 2  # Number of receive antennas
Nt = np.ones(num_cells) * 2  # Number of transmit antennas
Ns_BD = Nt  # Number of streams (per user) in the BD algorithm
path_loss_obj = pathloss.PathLoss3GPP1()
multiuser_channel = pyphysim.channels.multiuser.MultiUserChannelMatrixExtInt()

# Modulation Parameters
M = 4
modulator = fundamental.PSK(M)

# Transmission Parameters
NSymbs = 500  # Number of symbols (/stream /user simulated at each iteration
SNR_dB = 15.
N0_dBm = -116.4  # Noise power (in dBm)

# External Interference Parameters
Pe_dBm = -10000  # transmit power (in dBm) of the ext. interference
ext_int_rank = 1  # Rank of the external interference

# xxxxxxxxxx General Parameters xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx
rep_max = 20000  # Maximum number of repetitions for each

pbar = progressbar.ProgressbarText(
    rep_max, message="Simulating for SNR: {0}".format(SNR_dB))
コード例 #5
0
    def test_block_diagonalize_no_waterfilling(self):
        Nr = np.array([2, 2])
        Nt = np.array([2, 2])
        K = Nt.size
        Nti = 1
        iPu = 1e-1  # Power for each user (linear scale)
        pe = 1e-3  # External interference power (in linear scale)
        noise_var = 1e-1

        # The modulator and packet_length are required in the
        # effective_throughput metric case
        psk_obj = fundamental.PSK(4)
        packet_length = 120

        multiUserChannel = multiuser.MultiUserChannelMatrixExtInt()
        multiUserChannel.randomize(Nr, Nt, K, Nti)
        multiUserChannel.noise_var = noise_var

        # Channel from all transmitters to the first receiver
        H1 = multiUserChannel.get_Hk_without_ext_int(0)
        # Channel from all transmitters to the second receiver
        H2 = multiUserChannel.get_Hk_without_ext_int(1)

        # Create the enhancedBD object
        enhancedBD_obj = blockdiagonalization.EnhancedBD(K, iPu, noise_var, pe)

        noise_plus_int_cov_matrix \
            = multiUserChannel.calc_cov_matrix_extint_plus_noise(pe)

        # xxxxx First we test without ext. int. handling xxxxxxxxxxxxxxxxxx
        enhancedBD_obj.set_ext_int_handling_metric(None)
        (Ms_all, Wk_all, Ns_all) \
            = enhancedBD_obj.block_diagonalize_no_waterfilling(
            multiUserChannel)
        Ms1 = Ms_all[0]
        Ms2 = Ms_all[1]

        self.assertEqual(Ms1.shape[1], Ns_all[0])
        self.assertEqual(Ms2.shape[1], Ns_all[1])

        # Most likely only one base station (the one with the worst
        # channel) will employ a precoder with total power of `Pu`,
        # while the other base stations will use less power.
        tol = 1e-10
        self.assertGreaterEqual(iPu + tol, np.linalg.norm(Ms1, 'fro')**2)
        # 1e-12 is included to avoid false test fails due to small
        # precision errors
        self.assertGreaterEqual(iPu + tol, np.linalg.norm(Ms2, 'fro')**2)

        # Test if the precoder block diagonalizes the channel
        self.assertNotAlmostEqual(np.linalg.norm(np.dot(H1, Ms1), 'fro'), 0)
        self.assertAlmostEqual(np.linalg.norm(np.dot(H1, Ms2), 'fro'), 0)
        self.assertNotAlmostEqual(np.linalg.norm(np.dot(H2, Ms2), 'fro'), 0)
        self.assertAlmostEqual(np.linalg.norm(np.dot(H2, Ms1), 'fro'), 0)

        # Equivalent sinrs (in linear scale)
        sinrs = np.empty(K, dtype=np.ndarray)
        sinrs[0] = blockdiagonalization.EnhancedBD._calc_linear_SINRs(
            np.dot(H1, Ms1), Wk_all[0], noise_plus_int_cov_matrix[0])
        sinrs[1] = blockdiagonalization.EnhancedBD._calc_linear_SINRs(
            np.dot(H2, Ms2), Wk_all[1], noise_plus_int_cov_matrix[1])

        # Spectral efficiency
        # noinspection PyPep8
        se = (np.sum(
            psk_obj.calcTheoreticalSpectralEfficiency(linear2dB(
                sinrs[0]), packet_length)) + np.sum(
                    psk_obj.calcTheoreticalSpectralEfficiency(
                        linear2dB(sinrs[1]), packet_length)))
        # xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx

        # xxxxx Now with the Naive Stream Reduction xxxxxxxxxxxxxxxxxxxxxxx
        num_streams = 1
        enhancedBD_obj.set_ext_int_handling_metric(
            'naive', {'num_streams': num_streams})

        (MsPk_naive_all, Wk_naive_all, Ns_naive_all) \
            = enhancedBD_obj.block_diagonalize_no_waterfilling(
            multiUserChannel)
        MsPk_naive_1 = MsPk_naive_all[0]
        MsPk_naive_2 = MsPk_naive_all[1]

        self.assertEqual(MsPk_naive_1.shape[1], Ns_naive_all[0])
        self.assertEqual(MsPk_naive_2.shape[1], Ns_naive_all[1])
        self.assertEqual(Ns_naive_all[0], num_streams)
        self.assertEqual(Ns_naive_all[1], num_streams)

        # Test if the square of the Frobenius norm of the precoder of each
        # user is equal to the power available to that user.
        self.assertAlmostEqual(iPu, np.linalg.norm(MsPk_naive_1, 'fro')**2)
        self.assertAlmostEqual(iPu, np.linalg.norm(MsPk_naive_2, 'fro')**2)

        # Test if MsPk really block diagonalizes the channel
        self.assertNotAlmostEqual(
            np.linalg.norm(np.dot(H1, MsPk_naive_1), 'fro'), 0)
        self.assertAlmostEqual(np.linalg.norm(np.dot(H1, MsPk_naive_2), 'fro'),
                               0)
        self.assertNotAlmostEqual(
            np.linalg.norm(np.dot(H2, MsPk_naive_2), 'fro'), 0)
        self.assertAlmostEqual(np.linalg.norm(np.dot(H2, MsPk_naive_1), 'fro'),
                               0)

        sinrs4 = np.empty(K, dtype=np.ndarray)
        sinrs4[0] = blockdiagonalization.EnhancedBD._calc_linear_SINRs(
            np.dot(H1, MsPk_naive_1), Wk_naive_all[0],
            noise_plus_int_cov_matrix[0])
        sinrs4[1] = blockdiagonalization.EnhancedBD._calc_linear_SINRs(
            np.dot(H2, MsPk_naive_2), Wk_naive_all[1],
            noise_plus_int_cov_matrix[1])

        # Spectral efficiency
        # se4 = (
        #     np.sum(psk_obj.calcTheoreticalSpectralEfficiency(
        #         linear2dB(sinrs4[0]),
        #         packet_length))
        #     +
        #     np.sum(psk_obj.calcTheoreticalSpectralEfficiency(
        #         linear2dB(sinrs4[1]),
        #         packet_length)))
        # xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx

        # xxxxx Now with the Fixed Stream Reduction xxxxxxxxxxxxxxxxxxxxxxx
        # The 'fixed' metric requires that metric_func_extra_args_dict is
        # provided and has the 'num_streams' key. If this is not the case
        # an exception is raised
        with self.assertRaises(AttributeError):
            enhancedBD_obj.set_ext_int_handling_metric('fixed')

        # Now let's test the fixed metric
        num_streams = 1
        enhancedBD_obj.set_ext_int_handling_metric(
            'fixed', {'num_streams': num_streams})

        (MsPk_fixed_all, Wk_fixed_all, Ns_fixed_all) \
            = enhancedBD_obj.block_diagonalize_no_waterfilling(
            multiUserChannel)
        MsPk_fixed_1 = MsPk_fixed_all[0]
        MsPk_fixed_2 = MsPk_fixed_all[1]

        self.assertEqual(MsPk_fixed_1.shape[1], Ns_fixed_all[0])
        self.assertEqual(MsPk_fixed_2.shape[1], Ns_fixed_all[1])
        self.assertEqual(Ns_fixed_all[0], num_streams)
        self.assertEqual(Ns_fixed_all[1], num_streams)

        # Test if the square of the Frobenius norm of the precoder of each
        # user is equal to the power available to that user.
        self.assertAlmostEqual(iPu, np.linalg.norm(MsPk_fixed_1, 'fro')**2)
        self.assertAlmostEqual(iPu, np.linalg.norm(MsPk_fixed_2, 'fro')**2)

        # Test if MsPk really block diagonalizes the channel
        self.assertNotAlmostEqual(
            np.linalg.norm(np.dot(H1, MsPk_fixed_1), 'fro'), 0)
        self.assertAlmostEqual(np.linalg.norm(np.dot(H1, MsPk_fixed_2), 'fro'),
                               0)
        self.assertNotAlmostEqual(
            np.linalg.norm(np.dot(H2, MsPk_fixed_2), 'fro'), 0)
        self.assertAlmostEqual(np.linalg.norm(np.dot(H2, MsPk_fixed_1), 'fro'),
                               0)

        sinrs5 = np.empty(K, dtype=np.ndarray)
        sinrs5[0] = blockdiagonalization.EnhancedBD._calc_linear_SINRs(
            np.dot(H1, MsPk_fixed_1), Wk_fixed_all[0],
            noise_plus_int_cov_matrix[0])
        sinrs5[1] = blockdiagonalization.EnhancedBD._calc_linear_SINRs(
            np.dot(H2, MsPk_fixed_2), Wk_fixed_all[1],
            noise_plus_int_cov_matrix[1])

        # Spectral efficiency
        # se5 = (
        #     np.sum(psk_obj.calcTheoreticalSpectralEfficiency(
        #         linear2dB(sinrs5[0]),
        #         packet_length))
        #     +
        #     np.sum(psk_obj.calcTheoreticalSpectralEfficiency(
        #         linear2dB(sinrs5[1]),
        #         packet_length)))
        # xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx

        # xxxxx Handling external interference xxxxxxxxxxxxxxxxxxxxxxxxxxxx
        # Handling external interference using the capacity metric
        enhancedBD_obj.set_ext_int_handling_metric('capacity')
        (MsPk_all, Wk_cap_all, Ns_cap_all) \
            = enhancedBD_obj.block_diagonalize_no_waterfilling(
            multiUserChannel)
        MsPk_cap_1 = MsPk_all[0]
        MsPk_cap_2 = MsPk_all[1]

        self.assertEqual(MsPk_cap_1.shape[1], Ns_cap_all[0])
        self.assertEqual(MsPk_cap_2.shape[1], Ns_cap_all[1])

        # Test if the square of the Frobenius norm of the precoder of each
        # user is equal to the power available to that user.
        self.assertAlmostEqual(iPu, np.linalg.norm(MsPk_cap_1, 'fro')**2)
        self.assertAlmostEqual(iPu, np.linalg.norm(MsPk_cap_2, 'fro')**2)

        # Test if MsPk really block diagonalizes the channel
        self.assertNotAlmostEqual(
            np.linalg.norm(np.dot(H1, MsPk_cap_1), 'fro'), 0)
        self.assertAlmostEqual(np.linalg.norm(np.dot(H1, MsPk_cap_2), 'fro'),
                               0)
        self.assertNotAlmostEqual(
            np.linalg.norm(np.dot(H2, MsPk_cap_2), 'fro'), 0)
        self.assertAlmostEqual(np.linalg.norm(np.dot(H2, MsPk_cap_1), 'fro'),
                               0)

        sinrs2 = np.empty(K, dtype=np.ndarray)
        sinrs2[0] = blockdiagonalization.EnhancedBD._calc_linear_SINRs(
            np.dot(H1, MsPk_cap_1), Wk_cap_all[0],
            noise_plus_int_cov_matrix[0])
        sinrs2[1] = blockdiagonalization.EnhancedBD._calc_linear_SINRs(
            np.dot(H2, MsPk_cap_2), Wk_cap_all[1],
            noise_plus_int_cov_matrix[1])

        # Spectral efficiency
        # noinspection PyPep8
        se2 = (np.sum(
            psk_obj.calcTheoreticalSpectralEfficiency(linear2dB(
                sinrs2[0]), packet_length)) + np.sum(
                    psk_obj.calcTheoreticalSpectralEfficiency(
                        linear2dB(sinrs2[1]), packet_length)))
        # xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx

        # xxxxx Handling external interference xxxxxxxxxxxxxxxxxxxxxxxxxxxx
        # Handling external interference using the effective_throughput metric
        enhancedBD_obj.set_ext_int_handling_metric(
            'effective_throughput', {
                'modulator': psk_obj,
                'packet_length': packet_length
            })

        (MsPk_effec_all, Wk_effec_all, Ns_effec_all) \
            = enhancedBD_obj.block_diagonalize_no_waterfilling(
            multiUserChannel)
        MsPk_effec_1 = MsPk_effec_all[0]
        MsPk_effec_2 = MsPk_effec_all[1]

        self.assertEqual(MsPk_effec_1.shape[1], Ns_effec_all[0])
        self.assertEqual(MsPk_effec_2.shape[1], Ns_effec_all[1])

        # Test if the square of the Frobenius norm of the precoder of each
        # user is equal to the power available to that user.
        self.assertAlmostEqual(iPu, np.linalg.norm(MsPk_effec_1, 'fro')**2)
        self.assertAlmostEqual(iPu, np.linalg.norm(MsPk_effec_2, 'fro')**2)

        # Test if MsPk really block diagonalizes the channel
        self.assertNotAlmostEqual(
            np.linalg.norm(np.dot(H1, MsPk_effec_1), 'fro'), 0)
        self.assertAlmostEqual(np.linalg.norm(np.dot(H1, MsPk_effec_2), 'fro'),
                               0)
        self.assertNotAlmostEqual(
            np.linalg.norm(np.dot(H2, MsPk_effec_2), 'fro'), 0)
        self.assertAlmostEqual(np.linalg.norm(np.dot(H2, MsPk_effec_1), 'fro'),
                               0)

        sinrs3 = np.empty(K, dtype=np.ndarray)
        sinrs3[0] = blockdiagonalization.EnhancedBD._calc_linear_SINRs(
            np.dot(H1, MsPk_effec_1), Wk_effec_all[0],
            noise_plus_int_cov_matrix[0])
        sinrs3[1] = blockdiagonalization.EnhancedBD._calc_linear_SINRs(
            np.dot(H2, MsPk_effec_2), Wk_effec_all[1],
            noise_plus_int_cov_matrix[1])

        # Spectral efficiency
        # noinspection PyPep8
        se3 = (np.sum(
            psk_obj.calcTheoreticalSpectralEfficiency(linear2dB(
                sinrs3[0]), packet_length)) + np.sum(
                    psk_obj.calcTheoreticalSpectralEfficiency(
                        linear2dB(sinrs3[1]), packet_length)))
        # xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx

        # Test if the effective_throughput obtains a better spectral
        # efficiency then the capacity and not handling interference.
        self.assertGreater(se3 + tol, se2)
        self.assertGreater(se3 + tol, se)
コード例 #6
0
    def test_set_ext_int_handling_metric(self):
        K = 3
        iPu = 1e-3  # Power for each user (linear scale)
        noise_var = 1e-4
        pe = 0

        # Create the EnhancedBD object
        enhancedBD_obj = blockdiagonalization.EnhancedBD(K, iPu, noise_var, pe)

        # xxxxx Test if an assert is raised for invalid arguments xxxxxxxxx
        with self.assertRaises(AttributeError):
            enhancedBD_obj.set_ext_int_handling_metric('lala')

        with self.assertRaises(AttributeError):
            # If we set the metric to effective_throughput but not provide
            # the modulator and packet_length attributes.
            enhancedBD_obj.set_ext_int_handling_metric('effective_throughput')

        with self.assertRaises(AttributeError):
            enhancedBD_obj.set_ext_int_handling_metric('naive')
        # xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx

        # xxxxx Test setting the metric to effective_throughput xxxxxxxxxxx
        psk_obj = fundamental.PSK(4)
        enhancedBD_obj.set_ext_int_handling_metric('effective_throughput', {
            'modulator': psk_obj,
            'packet_length': 120
        })
        self.assertEqual(enhancedBD_obj._metric_func,
                         blockdiagonalization._calc_effective_throughput)
        self.assertEqual(enhancedBD_obj.metric_name, "effective_throughput")

        metric_func_extra_args = enhancedBD_obj._metric_func_extra_args
        self.assertEqual(metric_func_extra_args['modulator'], psk_obj)
        self.assertEqual(metric_func_extra_args['packet_length'], 120)
        # xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx

        # xxxxx Test setting the metric to capacity xxxxxxxxxxxxxxxxxxxxxxx
        enhancedBD_obj.set_ext_int_handling_metric('capacity')
        self.assertEqual(enhancedBD_obj._metric_func,
                         calc_shannon_sum_capacity)
        self.assertEqual(enhancedBD_obj.metric_name, "capacity")
        # metric_func_extra_args is an empty dictionary for the capacity
        # metric
        self.assertEqual(enhancedBD_obj._metric_func_extra_args, {})
        # xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx

        # xxxxx Test setting the metric to None xxxxxxxxxxxxxxxxxxxxxxxxxxx
        enhancedBD_obj.set_ext_int_handling_metric(None)
        self.assertIsNone(enhancedBD_obj._metric_func)
        self.assertEqual(enhancedBD_obj.metric_name, "None")

        # metric_func_extra_args is an empty dictionary for the None metric
        self.assertEqual(enhancedBD_obj._metric_func_extra_args, {})

        # xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx

        # xxxxx Test setting the metric to naive xxxxxxxxxxxxxxxxxxxxxxxxxx
        enhancedBD_obj.set_ext_int_handling_metric('naive', {'num_streams': 2})
        self.assertIsNone(enhancedBD_obj._metric_func)
        self.assertEqual(enhancedBD_obj.metric_name, "naive")

        metric_func_extra_args = enhancedBD_obj._metric_func_extra_args
        self.assertEqual(metric_func_extra_args['num_streams'], 2)
コード例 #7
0
 def setUp(self):
     """Called before each test."""
     self.psk_obj = fundamental.PSK(4)
     self.psk_obj2 = fundamental.PSK(8)
コード例 #8
0
 def _update_modulator_object(self, ):
     """Updates the modulator object whenever M changes
     """
     self.modulator = mod.PSK(self.M)