diff --git a/README.md b/README.md
index da1c267a1e4d9bda24d493a331eb6a26eb185719..bea9b0fbacdcc679c66c3853d45e2c1c22e749af 100644
--- a/README.md
+++ b/README.md
@@ -1,2 +1,8 @@
 # if3230_mp_mst
 
+Cara compile program OpenMP:
+gcc -o MST_OpenMP.out MST_OpenMP.c
+
+Cara menjalankan program OpenMP:
+./MST_OpenMP.out < "../test/test_case_01"
+./MST_OpenMP.out
\ No newline at end of file
diff --git a/src/MST_OpenMP b/src/MST_OpenMP
index bd3592b945561c7078d02e3a191cd7487125fa65..31321e2fd1b102ccd7c68b1d6467c0d5478aa3f0 100755
Binary files a/src/MST_OpenMP and b/src/MST_OpenMP differ
diff --git a/src/MST_OpenMP.c b/src/MST_OpenMP.c
index 24455ca754950efc1dffad7d444abca020f799e5..2abc5eaa62e4dc88e2632afcdc4c4154120cf9f2 100644
--- a/src/MST_OpenMP.c
+++ b/src/MST_OpenMP.c
@@ -87,6 +87,8 @@ void bubbleSort(Edge arr[], int n, int type)
                 }
             }
 }
+
+/// Create graph based from the adjacency matrix in file
 Graph *ReadArguments()
 {
     Graph *graph = (Graph *)(malloc(sizeof(Graph)));
@@ -118,58 +120,6 @@ Graph *ReadArguments()
     return graph;
 }
 
-
-// Create graph based from the adjacency matrix in file
-Graph *ReadFile(char fileName[])
-{
-    FILE *fptr;
-    char fileURL[] = "../test/";
-    strcat(fileURL, fileName);
-    fptr = fopen(fileURL, "r");
-
-    if (fptr == NULL)
-    {
-        printf("Error! Opening file");
-        exit(1);
-    }
-
-    Graph *graph = (Graph *)(malloc(sizeof(Graph)));
-
-    int V;
-    scanf(fptr, "%d ", &V);
-    graph->V = V;
-    graph->edge = (Edge *)(malloc(((V * V - V) / 2) * sizeof(Edge)));
-
-    // Read the adjacency matrix
-    int E = 0;
-
-    /*
-I/O cannot be parallized
-src : http://forum.openmp.org/forum/viewtopic.php?f=3&t=764
-In general reading and writing from a file from multiple threads is not a good idea unless the underlying operating system or I/O system really supports it (commonly referred to as parallel I/O).
-A lot of times the I/O routines can be used to read/write from separate files at the same time. That is because each I/O instance is keeping it's own data area telling which line it is reading or writing from. However, when you have multiple threads trying to read/write to the same file you need the I/O system to keep one data area for that file for all threads. This is not what is generally done, so you end up serializing (or somehow locking) the I/O. This of course, slows done the process and thus makes parallelizing I/O relatively impractical (since you will not see a speedup)
-    */
-    for (int i = 0; i < V; i++)
-    {
-        for (int j = 0; j < V; j++)
-        {
-            int weight;
-            scanf(fptr, "%d", &weight);
-            // printf("%d ", weight);
-            if ((weight != -1) && (i <= j))
-            {
-                graph->edge[E].src = i;
-                graph->edge[E].dest = j;
-                graph->edge[E].weight = weight;
-                E += 1;
-            }
-        }
-    }
-    // printf("\n");
-    graph->E = E;
-    return graph;
-}
-
 // Structure to represent a subset for union-find
 typedef struct
 {
@@ -238,7 +188,7 @@ int compare_src(const void *a, const void *b)
 }
 
 // Minimum Spanning Tree using Kruskal's Algorithm
-void KruskalMST(Graph *graph, Edge *result, int *e)
+void KruskalMST(Graph *graph, Edge result[], int *e)
 {
     int V = graph->V;
     int i = 0;
@@ -257,7 +207,6 @@ void KruskalMST(Graph *graph, Edge *result, int *e)
 
         int x = find(subsets, next_edge.src);
         int y = find(subsets, next_edge.dest);
-
         if (x != y)
         {
             result[(*e)++] = next_edge;
@@ -286,17 +235,18 @@ void printResult(Edge *result, int e)
         printf("%d-%d\n", result[i].src, result[i].dest);
     }
 }
+
 // Driver program to test above functions
 int main()
 {
     Graph *graph = ReadArguments();
-    Edge result;
-    int e;
+    Edge result[graph->V];
+    int e = 0;
     // PrintGraph(graph);
     int t = clock();
-    KruskalMST(graph, &result, &e);
+    KruskalMST(graph, result, &e);
     t = clock() - t;
-    printResult(&result, e);
-    printf("Waktu Eksekusi: %f ms", ((double)t) / CLOCKS_PER_SEC * 1000);
+    printResult(result, e);
+    printf("Waktu Eksekusi: %f ms\n", ((double)t) / CLOCKS_PER_SEC * 1000);
     return 0;
 }
\ No newline at end of file
diff --git a/src/MST_OpenMP.exe b/src/MST_OpenMP.exe
deleted file mode 100644
index 1f2aa1944a97aa5adb8acbf908532b7ce3a50f2b..0000000000000000000000000000000000000000
Binary files a/src/MST_OpenMP.exe and /dev/null differ
diff --git a/src/MST_Serial b/src/MST_Serial
index bea1adf661965ac3d204c4f6295699fcced39a09..3927436b13eb5c70e4182cc7a394f42e3bebbc5a 100755
Binary files a/src/MST_Serial and b/src/MST_Serial differ
diff --git a/src/MST_Serial.c b/src/MST_Serial.c
index 19967b51be573df4263aad055ba3277929df9f60..3da1b6347e3b4141f85a1a5ac174c11afe3457f3 100644
--- a/src/MST_Serial.c
+++ b/src/MST_Serial.c
@@ -43,7 +43,39 @@ void PrintGraph(Graph *graph)
         printf("%d -- %d = %d\n", graph->edge[i].src, graph->edge[i].dest, graph->edge[i].weight);
     }
 }
+void bubbleSort(Edge arr[], int n, int type)
+{
+    //Jika type ==1, maka diurutkan berdasarkan weight
+    //Jika type ==2, maka diurutkan berdasarkan src
+    int i, j;
+   for (i = 0; i < n - 1; i++)
 
+        for (j = 0; j < n - i - 1; j++)
+            if (type == 1)
+            {
+                if (arr[j].weight > arr[j + 1].weight)
+                {
+                        Edge temp = arr[j];
+                        arr[j] = arr[j + 1];
+                        arr[j + 1] = temp;
+                }
+            }
+            else
+            {
+                if (arr[j].src > arr[j + 1].src)
+                {
+                    Edge temp = arr[j];
+                    arr[j] = arr[j + 1];
+                    arr[j + 1] = temp;
+                }
+                else if (arr[j].src == arr[j + 1].src && arr[j].dest > arr[j + 1].dest)
+                {
+                    Edge temp = arr[j];
+                    arr[j] = arr[j + 1];
+                    arr[j + 1] = temp;
+                }
+            }
+}
 // Create graph based from the adjacency matrix in file
 Graph *ReadArguments()
 {
@@ -143,55 +175,64 @@ int compare_src(const void *a, const void *b)
 }
 
 // Minimum Spanning Tree using Kruskal's Algorithm
-void KruskalMST(Graph *graph)
+void KruskalMST(Graph *graph, Edge result[], int *e)
 {
     int V = graph->V;
-    Edge result[V];
-    int e = 0;
     int i = 0;
 
     // Step 1: Sort all the edges into correspondent sorted edges
-    qsort(graph->edge, graph->E, sizeof(graph->edge[0]), compare);
+    // qsort(graph->edge, graph->E, sizeof(graph->edge[0]), compare);
 
+    bubbleSort(graph->edge, graph->E, 1);
     // Step 2: Allocate memory for creating V subsets
     Subset *subsets = CreateSubset(V);
-    while ((e < V - 1) && (i < graph->E))
+
+    while (((*e) < V - 1) && (i < graph->E))
     {
         // Pick the smallest edge of the graph
         Edge next_edge = graph->edge[i++];
 
         int x = find(subsets, next_edge.src);
         int y = find(subsets, next_edge.dest);
-
         if (x != y)
         {
-            result[e++] = next_edge;
+            result[(*e)++] = next_edge;
             Union(subsets, x, y);
         }
     }
 
-    // Print all minimum spanning tree edges
+    bubbleSort(result, (*e), 2);
+    return;
+    // qsort(result, e, sizeof(result[0]), compare_src);
+}
 
-    qsort(result, e, sizeof(result[0]), compare_src);
-    printf("Minimum Spanning Tree Edges\n");
+void printResult(Edge *result, int e)
+{
+    // printf("%d\n", e);
     int minimumCost = 0;
-    for (i = 0; i < e; i++)
+    for (int i = 0; i < e; i++)
     {
-        printf("%d -- %d == %d\n", result[i].src, result[i].dest, result[i].weight);
         minimumCost += result[i].weight;
     }
-    printf("Minimum cost spanning tree: %d", minimumCost);
-    return;
+    printf("%d\n", minimumCost);
+    for (int i = 0; i < e; i++)
+    {
+        printf("%d-%d\n", result[i].src, result[i].dest);
+    }
 }
 
+
 // Driver program to test above functions
 int main()
 {
     Graph *graph = ReadArguments();
-    PrintGraph(graph);
+    Edge result[graph->V];
+    int e = 0;
+    // PrintGraph(graph);
     int t = clock();
-    KruskalMST(graph);
+    KruskalMST(graph, result, &e);
     t = clock() - t;
-    printf("\n\nWaktu Eksekusi: %f ms", ((double)t) / CLOCKS_PER_SEC * 1000);
+    printResult(result, e);
+    printf("Waktu Eksekusi: %f ms\n", ((double)t) / CLOCKS_PER_SEC * 1000);
     return 0;
 }
\ No newline at end of file
diff --git a/src/MST_Serial.exe b/src/MST_Serial.exe
deleted file mode 100644
index a27ad175acd9eb19d5a6dcf6e743717a58862686..0000000000000000000000000000000000000000
Binary files a/src/MST_Serial.exe and /dev/null differ