diff --git a/.gitignore b/.gitignore
index b54ca37..180266e 100644
--- a/.gitignore
+++ b/.gitignore
@@ -77,7 +77,7 @@ target/
# Jupyter Notebook
.ipynb_checkpoints
-
+.virtual_documents
# IPython
profile_default/
ipython_config.py
diff --git a/hierarchical-nsa.ipynb b/hierarchical-nsa.ipynb
index c92a9ac..7c0a4c3 100644
--- a/hierarchical-nsa.ipynb
+++ b/hierarchical-nsa.ipynb
@@ -20,7 +20,7 @@
"\n",
"1. User-preferences Weights Calculations - Fuzzy Logic\n",
"2. Service QoS Weights Calculations - AHP\n",
- "3. Weights Normalisation such ∑ w_i = 1\n",
+ "3. Normalisation \n",
"4. Final Weights Calculation RAT layer\n",
"5. MEW\n",
"6. SAW"
@@ -181,16 +181,37 @@
"id": "4f998588-692a-428a-97fc-16721608a3bb",
"metadata": {},
"source": [
- "#### 3. Weights Normalisation"
+ "#### 3. Normalisation"
]
},
{
"cell_type": "code",
- "execution_count": null,
+ "execution_count": 331,
"id": "d47eb935-d633-4810-b9f3-fe62e9efb832",
"metadata": {},
"outputs": [],
- "source": []
+ "source": [
+ "def square_root_normalize(matrix, criteria_types):\n",
+ " \"\"\"\n",
+ " Normalize the matrix using square root normalization,\n",
+ " accounting for upward and downward criteria.\n",
+ " \n",
+ " :param matrix: numpy array of shape (n_rats, n_criteria)\n",
+ " :param criteria_types: list of strings, either 'up' or 'down' for each criterion\n",
+ " :return: normalized matrix\n",
+ " \"\"\"\n",
+ " normalized = np.zeros_like(matrix, dtype=float)\n",
+ " \n",
+ " for j in range(matrix.shape[1]):\n",
+ " if criteria_types[j] == 'up':\n",
+ " normalized[:, j] = matrix[:, j] / np.sqrt(np.sum(matrix[:, j]**2))\n",
+ " elif criteria_types[j] == 'down':\n",
+ " normalized[:, j] = 1 - (matrix[:, j] / np.sqrt(np.sum(matrix[:, j]**2)))\n",
+ " else:\n",
+ " raise ValueError(f\"Invalid criterion type: {criteria_types[j]}. Must be 'up' or 'down'.\")\n",
+ " \n",
+ " return normalized"
+ ]
},
{
"cell_type": "markdown",
@@ -200,14 +221,6 @@
"#### 4. Final Weights Calculation"
]
},
- {
- "cell_type": "code",
- "execution_count": null,
- "id": "66297d93-8ff7-4b64-bfd5-c76cb1ca4bc8",
- "metadata": {},
- "outputs": [],
- "source": []
- },
{
"cell_type": "markdown",
"id": "77ff1273-f181-4678-bfe6-1a51d9f44a55",
@@ -218,21 +231,11 @@
},
{
"cell_type": "code",
- "execution_count": 241,
+ "execution_count": 332,
"id": "ae5fa8b6-4113-421a-9112-10d1e270a8f3",
"metadata": {},
- "outputs": [
- {
- "name": "stdout",
- "output_type": "stream",
- "text": [
- "MEW Scores: [0.72184057 0.69568331 0.78690609]\n"
- ]
- }
- ],
+ "outputs": [],
"source": [
- "import numpy as np\n",
- "\n",
"def calculate_mew_scores(decision_matrix, weights):\n",
" \"\"\"\n",
" Calculate scores using the Multiple Exponen Weighted (MEW) method.\n",
@@ -257,24 +260,7 @@
" weighted_matrix = np.power(decision_matrix, weights)\n",
" mew_scores = np.prod(weighted_matrix, axis=1)\n",
" \n",
- " return mew_scores\n",
- "\n",
- "# Example usage\n",
- "if __name__ == \"__main__\":\n",
- " # Example normalized decision matrix (3 alternatives, 4 criteria)\n",
- " decision_matrix = np.array([\n",
- " [0.7, 0.8, 0.6, 0.9],\n",
- " [0.6, 0.7, 0.8, 0.7],\n",
- " [0.8, 0.9, 0.7, 0.8]\n",
- " ])\n",
- " \n",
- " # Example weights\n",
- " weights = np.array([0.3, 0.2, 0.3, 0.2])\n",
- " \n",
- " # Calculate MEW scores\n",
- " scores = calculate_mew_scores(decision_matrix, weights)\n",
- " \n",
- " print(\"MEW Scores:\", scores)"
+ " return mew_scores"
]
},
{
@@ -287,7 +273,7 @@
},
{
"cell_type": "code",
- "execution_count": 242,
+ "execution_count": 333,
"id": "2e4f5e3f-31ee-48a6-aeee-b87de52da99c",
"metadata": {},
"outputs": [],
@@ -328,7 +314,7 @@
},
{
"cell_type": "code",
- "execution_count": 243,
+ "execution_count": 334,
"id": "da5ed195-d7d2-4cb3-a799-a7b119ad7dbd",
"metadata": {},
"outputs": [],
@@ -346,169 +332,27 @@
},
{
"cell_type": "code",
- "execution_count": 244,
+ "execution_count": 373,
"id": "eb58539e-692c-43a9-8339-85cfcaae7c7b",
"metadata": {},
- "outputs": [
- {
- "data": {
- "text/html": [
- "
\n",
- "\n",
- "
\n",
- " \n",
- " \n",
- " | \n",
- " 0 | \n",
- " 1 | \n",
- " 2 | \n",
- " 3 | \n",
- " 4 | \n",
- " 5 | \n",
- " 6 | \n",
- " 7 | \n",
- " 8 | \n",
- " 9 | \n",
- "
\n",
- " \n",
- " \n",
- " \n",
- " 0 | \n",
- " Criteria | \n",
- " P | \n",
- " C | \n",
- " D | \n",
- " J | \n",
- " L | \n",
- " T | \n",
- " CL | \n",
- " CC | \n",
- " S | \n",
- "
\n",
- " \n",
- " 1 | \n",
- " 3G | \n",
- " 800 | \n",
- " 10 | \n",
- " 20 | \n",
- " 10 | \n",
- " 1 | \n",
- " 0.03 | \n",
- " 1 | \n",
- " 70 | \n",
- " 10 | \n",
- "
\n",
- " \n",
- " 2 | \n",
- " 4G | \n",
- " 500 | \n",
- " 1 | \n",
- " 10 | \n",
- " 5 | \n",
- " 0.1 | \n",
- " 1 | \n",
- " 1 | \n",
- " 40 | \n",
- " 30 | \n",
- "
\n",
- " \n",
- " 3 | \n",
- " 5G | \n",
- " 300 | \n",
- " 0.1 | \n",
- " 1 | \n",
- " 1 | \n",
- " 0.01 | \n",
- " 20 | \n",
- " 1 | \n",
- " 20 | \n",
- " 30 | \n",
- "
\n",
- " \n",
- " 4 | \n",
- " 6G | \n",
- " 100 | \n",
- " 0.01 | \n",
- " 0.8 | \n",
- " 0.5 | \n",
- " 0.009 | \n",
- " 1000 | \n",
- " 1 | \n",
- " 0.5 | \n",
- " 40 | \n",
- "
\n",
- " \n",
- " 5 | \n",
- " LEO | \n",
- " 1000 | \n",
- " 2 | \n",
- " 50 | \n",
- " 10 | \n",
- " 0.45 | \n",
- " 0.1 | \n",
- " 1 | \n",
- " 1000 | \n",
- " 15 | \n",
- "
\n",
- " \n",
- " 6 | \n",
- " NaN | \n",
- " down | \n",
- " down | \n",
- " down | \n",
- " down | \n",
- " down | \n",
- " up | \n",
- " down | \n",
- " up | \n",
- " up | \n",
- "
\n",
- " \n",
- "
\n",
- "
"
- ],
- "text/plain": [
- " 0 1 2 3 4 5 6 7 8 9\n",
- "0 Criteria P C D J L T CL CC S\n",
- "1 3G 800 10 20 10 1 0.03 1 70 10\n",
- "2 4G 500 1 10 5 0.1 1 1 40 30\n",
- "3 5G 300 0.1 1 1 0.01 20 1 20 30\n",
- "4 6G 100 0.01 0.8 0.5 0.009 1000 1 0.5 40\n",
- "5 LEO 1000 2 50 10 0.45 0.1 1 1000 15\n",
- "6 NaN down down down down down up down up up"
- ]
- },
- "execution_count": 244,
- "metadata": {},
- "output_type": "execute_result"
- }
- ],
+ "outputs": [],
"source": [
- "df = pd.read_csv(file_path+\"/decision_matrix.csv\",header = None)\n",
- "df"
+ "df = pd.read_csv(file_path+\"/decision_matrix.csv\",header = None)"
]
},
{
"cell_type": "code",
- "execution_count": 245,
+ "execution_count": 374,
"id": "a44a2674-b7c7-402a-a929-705049ab77d4",
"metadata": {},
"outputs": [],
"source": [
+ "criteria_types = df.iloc[6:,1:].values[0]\n",
+ "\n",
"dm_rat = df.iloc[1:6,1:7].values.astype(np.float64)\n",
- "dm_ap = df.iloc[1:6,7:11].values.astype(np.float64)"
+ "dm_ap = df.iloc[1:6,7:11].values.astype(np.float64)\n",
+ "\n",
+ "normal_dm_rat = square_root_normalize(dm_rat, criteria_types[:6])"
]
},
{
@@ -521,7 +365,7 @@
},
{
"cell_type": "code",
- "execution_count": 264,
+ "execution_count": 339,
"id": "21390f8d-04d4-4658-9dc2-9d8a53bda734",
"metadata": {},
"outputs": [],
@@ -548,7 +392,7 @@
},
{
"cell_type": "code",
- "execution_count": 250,
+ "execution_count": 340,
"id": "18c9de10-b8e6-4d71-b2bf-2cb56d56292d",
"metadata": {},
"outputs": [],
@@ -559,7 +403,7 @@
},
{
"cell_type": "code",
- "execution_count": 205,
+ "execution_count": 341,
"id": "d2fce88a-8d3b-4731-ae38-a40d958d87d7",
"metadata": {},
"outputs": [],
@@ -575,21 +419,10 @@
},
{
"cell_type": "code",
- "execution_count": 269,
+ "execution_count": 342,
"id": "9eba5fd3-be57-483d-bc3f-19cffedd365b",
"metadata": {},
- "outputs": [
- {
- "data": {
- "text/plain": [
- "array([0.2, 0.0, 0.0], dtype=object)"
- ]
- },
- "execution_count": 269,
- "metadata": {},
- "output_type": "execute_result"
- }
- ],
+ "outputs": [],
"source": [
"def userspref_weights(criteria, users_prefs): # returns a matrix of weights user [1...U] x prefs [Q,P,C]\n",
" userspref_weights = np.zeros_like(users_prefs)\n",
@@ -598,36 +431,24 @@
" userspref_weights[i] = pref_weights(criteria[:2],users_prefs[i])\n",
" #print(pref_weights(criteria[:2],users_prefs[i]))\n",
" #print(userpref_weights[i])\n",
- " return userspref_weights\n",
- "\n",
- "asf = userspref_weights(dm_rat[0], users_prefs)\n",
- "\n",
- "asf[1]\n",
- "asf[]"
+ " return userspref_weights"
]
},
{
"cell_type": "code",
- "execution_count": 270,
+ "execution_count": 343,
"id": "b685c01e-8738-41c8-a7a3-1ab52749aabb",
"metadata": {},
"outputs": [],
"source": [
"def qos_nomarlisation(user_weights, service_weights):\n",
" normal_uw = user_weights[1:] if np.sum(user_weights[1:]) <= 0 else user_weights[1:]/np.sum(user_weights[1:])\n",
- " return np.concatenate((normal_uw * (1 - user_weights[0]) , service_weights * user_weights[0]))\n",
- "\n",
- "\n",
- "#userspref_weights(dm_rat[0],users_prefs)[1][1:]\n",
- "\n",
- "#uw = np.array([0.5,0.4,0.8])\n",
- "#sw = np.array([0.2,0.4,0.1,0.3])\n",
- "#qos_nomarlisation(uw,sw)"
+ " return np.concatenate((normal_uw * (1 - user_weights[0]) , service_weights * user_weights[0]))"
]
},
{
"cell_type": "code",
- "execution_count": 273,
+ "execution_count": 344,
"id": "787edd08-2aed-4c8c-acea-c4af9fd9d198",
"metadata": {},
"outputs": [],
@@ -645,40 +466,65 @@
},
{
"cell_type": "code",
- "execution_count": 275,
+ "execution_count": null,
+ "id": "95657465-343b-4522-bd2b-2d8ca636cb18",
+ "metadata": {},
+ "outputs": [],
+ "source": [
+ "def hadamard_product(A, B):\n",
+ " # Ensure matrices have the same shape\n",
+ " if A.shape != B.shape:\n",
+ " raise ValueError(\"Matrices must have the same shape\")\n",
+ " \n",
+ " # Perform element-wise multiplication\n",
+ " return A * B # In NumPy, * operator performs element-wise multiplication for arrays"
+ ]
+ },
+ {
+ "cell_type": "code",
+ "execution_count": 345,
"id": "aff14bef-628e-4fed-b740-40577a0fd0af",
"metadata": {},
+ "outputs": [],
+ "source": [
+ "rat_user_weights = np.zeros((5,27,6))\n",
+ "for i in range(5): \n",
+ " rat_user_weights[i] = users_service_weights(dm_rat[i],users_prefs,services_weights)[:, 0, :] # service 1 at index 0\n",
+ " #print(rat_user_weights[0])\n",
+ " #print(users_service_weights(dm_rat[i],users_prefs,services_weights)[:, 0, :])"
+ ]
+ },
+ {
+ "cell_type": "code",
+ "execution_count": 348,
+ "id": "ab841183-4557-489b-b7c7-63992e03d02a",
+ "metadata": {},
"outputs": [
{
"data": {
"text/plain": [
"array([[0. , 0. , 0.11300636, 0.02349906, 0.05243455,\n",
" 0.01106003],\n",
- " [0. , 0. , 0.02438016, 0.01272753, 0.05410509,\n",
- " 0.10878722],\n",
- " [0. , 0. , 0.11304389, 0.05237821, 0.02351262,\n",
- " 0.01106529],\n",
- " [0. , 0. , 0.05 , 0.05 , 0.05 ,\n",
- " 0.05 ]])"
+ " [0.14545455, 0.65454545, 0.11300636, 0.02349906, 0.05243455,\n",
+ " 0.01106003],\n",
+ " [0.4 , 0.4 , 0.11300636, 0.02349906, 0.05243455,\n",
+ " 0.01106003],\n",
+ " [0.4 , 0.4 , 0.11300636, 0.02349906, 0.05243455,\n",
+ " 0.01106003],\n",
+ " [0. , 0.8 , 0.11300636, 0.02349906, 0.05243455,\n",
+ " 0.01106003]])"
]
},
- "execution_count": 275,
+ "execution_count": 348,
"metadata": {},
"output_type": "execute_result"
}
],
"source": [
- "#for rat_criteria in dm_rat:\n",
- "users_service_weights(dm_rat[0],users_prefs,services_weights)[][] \n"
+ "#for i in range(27):\n",
+ "# hadamard_product(rat_user_weights[:,i,:],normal_md_rat)\n",
+ " "
]
- },
- {
- "cell_type": "code",
- "execution_count": null,
- "id": "d212fd1b-0181-41ea-b373-18d30c063352",
- "metadata": {},
- "outputs": [],
- "source": []
}
],
"metadata": {