SEARCHING

Pada suatu data seringkali dibutuhkan pembacaan kembali informasi (retrieval information) dengan cara searching. Searching adalah pencarian data dengan cara menelusuri data-data tersebut. Tempat pencarian data dapat berupa array dalam memori, bisa juga pada file pada external storage.

Sequential Search

Adalah suatu teknik pencarian data dalam array ( 1 dimensi ) yang akan menelusuri semua elemen-elemen array dari awal sampai akhir, dimana data-data tidak perlu diurutkan terlebih dahulu. Kemungkinan terbaik (best case) adalah jika data yang dicari terletak di indeks array terdepan (elemen array pertama) sehingga waktu yang dibutuhkan untuk pencarian data sangat sebentar (minimal). Kemungkinan terburuk (worst case) adalah jika data yang dicari terletak di indeks array terakhir (elemen array terakhir) sehingga waktu yang dibutuhkan untuk pencarian data sangat lama (maksimal).
Misalnya terdapat array satu dimensi sebagai berikut:


Kemudian program akan meminta data yang akan dicari, misalnya 6. Jika ada maka akan ditampilkan tulisan “ADA”, sedangkan jika tidak ada maka akan ditampilkan tulisan “TIDAK ADA”.


Binary Search



Data yang ada harus diurutkan terlebih dahulu berdasarkan suatu urutan tertentu yang dijadikan kunci pencarian. Binary Search adalah teknik pencarian data dalam dengan cara membagi data menjadi dua bagian setiap kali terjadi proses pencarian.
Prinsip pencarian biner adalah:

  • Data diambil dari posisi 1 sampai posisi akhir N

  • Kemudian cari posisi data tengah dengan rumus: (posisi awal + posisi akhir) / 2

  • Kemudian data yang dicari dibandingkan dengan data yang di tengah, apakah sama atau lebih kecil, atau lebih besar?

  • Jika lebih besar, maka proses pencarian dicari dengan posisi awal adalah posisi tengah + 1

  • Jika lebih kecil, maka proses pencarian dicari dengan posisi akhir adalah posisi tengah – 1Jika data sama, berarti ketemu.
  • Sorting

    Pengurutan data dalam struktur data sangat penting terutama untuk data yang beripe
    data numerik ataupun karakter. Pengurutan dapat dilakukan secara ascending (urut naik) dan descending (urut turun). Pengurutan (Sorting) adalah proses pengurutan data yang sebelumnya disusun secara acak sehingga tersusun secara teratur menurut aturan tertentu.
    Contoh:
    Data Acak : 5 6 8 1 3 25 10
    Ascending : 1 3 5 6 8 10 25
    Descending : 25 10 8 6 5 3 1



    Metode Pengurutan Data


    •Pengurutan berdasarkan perbandingan (comparison-based sorting)
    Bubble sort, exchange sort
    •Pengurutan berdasarkan prioritas (priority queue sorting method)
    Selection sort, heap sort (menggunakan tree)
    •Pengurutan berdasarkan penyisipan dan penjagaan terurut (insert and keep sorted method)
    Insertion sort, tree sort
    •Pengurutan berdasarkan pembagian dan penguasaan (devide and conquer method)
    Quick sort, merge sort
    •Pengurutan berkurang menurun (diminishing increment sort method)
    Shell sort (pengembangan insertion)



    DEKLARASI ARRAY UNTUK SORTING
    Deklarasikan secara global:
    int data[100];
    int n; //untuk jumlah data



    Prosedur Tukar 2 Buah Data:
    void tukar(int a,int b){
    int tmp;
    tmp = data[a];
    data[a] = data[b];
    data[b] = tmp;
    }

    BUBLE SORT
    Metode sorting termudah. Diberi nama “Bubble” karena proses pengurutan secara berangsurangsur bergerak/berpindah ke posisinya yang tepat, seperti
    gelembung yang keluar dari sebuah gelas bersoda. Bubble Sort mengurutkan data dengan cara membandingkan elemen sekarang dengan elemen berikutnya. Jika elemen sekarang lebih besar dari elemen berikutnya maka kedua elemen tersebut ditukar, jika pengurutan ascending. Jika elemen sekarang lebih kecil dari elemen berikutnya, maka kedua elemen tersebut ditukar, jika pengurutan descending. Algoritma ini seolah-olah menggeser satu per satu elemen dari kanan ke kiri atau kiri ke kanan, tergantung jenis pengurutannya. Ketika satu proses telah selesai, maka bubble sort akan mengulangi proses, demikian seterusnya. Kapan berhentinya? Bubble sort berhenti jika seluruh array telah diperiksa dan tidak
    ada pertukaran lagi yang bisa dilakukan, serta tercapai perurutan yang telah diinginkan.













    Pada gambar disamping, pengecekan dimulai dari data yang paling akhir, kemudian bandingkan dengan data di depannya, jika data di depannya besar maka ditukar.










    Pada proses kedua, pengecekan dilakukan sampai dengan data ke-2 karena data pertama
    pasti sudah paling kecil.














    EXCHANGE SORT


    Sangat mirip dengan Bubble Sort. Banyak yang mengatakan Bubble Sort sama dengan Exchange Sort. Pebedaan : dalam hal bagaimana membandingkan antar elemen-elemennya.
    Pegurutan berhenti di sini!. Exchange sort membandingkan suatu elemen dengan elemen-elemen lainnya dalam array tersebut, dan melakukan pertukaran elemen jika perlu. Jadi ada elemen yang selalu menjadi elemen pusat (pivot). Sedangkan Bubble sort akan membandingkan elemen pertama/terakhir dengan elemen sebelumnya/sesudahnya, kemudian elemen sebelum/sesudahnya itu akan menjadi pusat (pivot) untuk dibandingkan dengan elemen sebelumnya/sesudahnya lagi, begitu seterusnya.










































    SELECTION SORT
    Merupakan kombinasi antara sorting dan searching. Untuk setiap proses, akan dicari elemen-elemen yang belum diurutkan yang memiliki nilai terkecil atau terbesar akan dipertukarkan ke posisi yang tepat di dalam array. Misalnya untuk putaran pertama, akan dicari data dengan nilai terkecil dan data ini akan ditempatkan di indeks terkecil (data[0]), pada putaran kedua akan dicari data kedua terkecil, dan akan ditempatkan di indeks kedua (data[1]). Selama proses, pembandingan dan pengubahan hanya dilakukan pada indeks pembanding saja, pertukaran data secara fisik terjadi pada akhir proses.























































    INSERTION SORT
    Mirip dengan cara orang mengurutkan kartu, selembar demi selembar kartu diambil dan disisipkan (insert) ke tempat yang seharusnya. Pengurutan dimulai dari data ke-2 sampai dengan data terakhir, jika ditemukan data yang lebih kecil, maka akan ditempatkan (diinsert) diposisi yang seharusnya. Pada penyisipan elemen, maka elemen-elemen lain akan bergeser ke belakang.



















































    void insertion_sort(){
    int temp;
    for(int i=1;itemp && j>=0){
    data[j+1] = data[j];
    j--;
    }
    data[j+1] = temp;
    }
    }



    Binary Search
    Adalah teknik pencarian data dalam array dengan cara membagi array menjadi dua
    bagian setiap kali terjadi proses pengurutan.
    Prinsip pencarian biner adalah: Data diambil dari posisi 1 sampai posisi akhir N. Kemudian cari posisi data tengah dengan rumus (posisi awal + posisi akhir) / 2. Kemudian data yang dicari dibandingkan dengan data yang di tengah, apakah
    sama atau lebih kecil, atau lebih besar? Jika lebih besar, maka proses pencarian dicari dengan posisi awal adalah posisi
    tengah + 1. Jika lebih kecil, maka proses pencarian dicari dengan posisi akhir adalah posisi
    tengah – 1. Jika data sama, berarti ketemu.

    Sejarah dari Linked List

    Dikembangkan tahun 1955-1956 oleh Allen Newell, Cliff Shaw dan Herbert Simon di RAND Corporation sebagai struktur data utama untuk bahasa Information Processing Language (IPL). IPL dibuat untuk mengembangkan program artificial intelligence, seperti pembuatan Chess Solver. Victor Yngve di Massachusetts Institute of Technology (MIT) juga menggunakan linked list pada natural language processing dan machine transitions pada bahasa pemrograman COMMIT.


    Linked List

    Linked List adalah salah satu bentuk struktur data, berisi kumpulan data (node) yang tersusun secara sekuensial, saling sambung-menyambung, dinamis dan terbatas. Linked List sering disebut juga Senarai Berantai. Linked List saling terhubung dengan bantuan variabel pointer. Masing-masing data dalam Linked List disebut dengan node (simpul) yang menempati alokasi memori secara dinamis dan biasanya berupa struct yang terdiri dari beberapa field.


    Array VS Linked List









    Bentuk Node Single Linked List non Circular







    Pengertian:

    Single artinya field pointer-nya hanya satu buah saja dan satu arah serta pada akhir node, pointernya menunjuk NULL. Linked List artinya node-node tersebut saling terhubung satu sama lain. Setiap node pada linked list mempunyai field yang berisi pointer ke node berikutnya, dan juga memiliki field yang berisi data. Node terakhir akan menunjuk ke NULL yang akan digunakan sebagai kondisi berhenti pada saat pembacaan isi linked list.





    Pembuatan Single Linked List

    Deklarasi Node

    typedef struct TNode{
    int data;
    TNode *next;
    };

    Penjelasan:
    • Pembuatan struct bernama TNode yang berisi 2 field, yaitu field data bertipe integer dan field next yang bertipe pointer dari TNode
    • Setelah pembuatan struct, buat variabel head yang bertipe pointer dari TNode yang berguna sebagai kepala linked list.

    Pembuatan Node Baru
    Digunakan keyword new yang berarti mempersiapkan sebuah node baru berserta alokasi memorinya, kemudian node tersebut diisi data dan pointer nextnya ditunjuk ke NULL.

    TNode *baru;
    baru = new TNode;
    baru->data = databaru;
    baru->next = NULL;


    Cara lain alokasi pointer
    • Menggunakan alokasi memori secara manual
    • Menggunakan header stdlib.h atau malloc.h
    • Menggunakan fungsi:
    *malloc(int size);



    Single Linked List Menggunakan Head
    • Dibutuhkan satu buah variabel pointer: head
    • Head akan selalu menunjuk pada node pertama








    Deklarasi Pointer Penunjuk Kepala Single Linked List

    Manipulasi linked list tidak bisa dilakukan langsung ke node yang dituju, melainkan harus menggunakan suatu pointer penunjuk ke node pertama dalam linked list (dalam hal ini adalah head). Deklarasinya sebagai berikut:

    TNode *head;

    Fungsi Inisialisasi Single Linked List

    void init(){

    head = NULL;
    }
    Function untuk mengetahui kosong tidaknya Single
    Linked List
    Jika pointer head tidak menunjuk pada suatu node maka kosong

    int isEmpty(){
    if(head == NULL) return 1;
    else return 0;
    }

    Penambahan data di depan
    Penambahan node baru akan dikaitan di node paling depan, namun pada saat pertama kali (data masih kosong), maka penambahan data dilakukan dengan cara: node head ditunjukkan ke node baru tersebut. Pada prinsipnya adalah mengkaitkan node baru dengan head, kemudian head akan menunjuk pada data baru tersebut sehingga head akan tetap selalu menjadi data terdepan.

    void insertDepan(int databaru){
    TNode *baru;
    baru = new TNode;
    baru->data = databaru;
    baru->next = NULL;
    if(isEmpty()==1){
    head=baru;
    head->next = NULL;
    }
    else {
    baru->next = head;
    head = baru;
    }
    cout<<”Data masuk\n”; }


    Ilustrasi:
    1. List masih kosong (head=NULL)






    2. Masuk data baru, misalnya 5








    3. Datang data baru, misalnya 20 (penambahan di depan)











    Penambahan data di belakang
    Penambahan data dilakukan di belakang, namun pada saat pertama kali, node langsung ditunjuk oleh head. Penambahan di belakang lebih sulit karena kita membutuhkan pointer bantu untuk mengetahui node terbelakang, kemudian setelah itu, dikaitkan dengan node baru. Untuk mengetahui data terbelakang perlu digunakan perulangan.

    void insertBelakang (int databaru){
    TNode *baru,*bantu;
    baru = new TNode;
    baru->data = databaru;
    baru->next = NULL;
    if(isEmpty()==1){
    head=baru;
    head->next = NULL;
    }
    else {
    bantu=head;
    while(bantu->next!=NULL){
    bantu=bantu->next;
    }
    bantu->next = baru;
    }
    cout<<"Data masuk\n“; }


    Ilustrasi :
    1. List masih kosong (head=NULL)







    2. Masuk data baru, misalnya 5








    3. Datang data baru, misalnya 20 (penambahan di belakang)











    4. Datang data baru, misalnya 25 (penambahan di belakang)












    Bagaimana dengan penambahan di tengah?

    void tampil(){
    TNode *bantu;
    bantu = head;
    if(isEmpty()==0){
    while(bantu!=NULL){
    cout<data<<" "; bantu=bantu->next;
    }
    cout<<“\n”; } else cout<<“Masih kosong\n“; }











    Function di atas digunakan untuk menampilkan semua isi list, di mana linked list ditelusuri satu-persatu dari awal node sampai akhir node. Penelusuran ini dilakukan dengan menggunakan suatu pointer bantu, karena pada prinsipnya pointer head yang menjadi tanda awal list tidak boleh berubah/berganti posisi. Penelusuran dilakukan terus sampai node terakhir ditemukan menunjuk ke nilai NULL. Jika tidak NULL, maka node bantu akan berpindah ke node selanjutnya dan membaca isi datanya dengan menggunakan field next sehingga dapat saling berkait. Jika head masih NULL berarti data masih kosong!

    Function untuk menghapus data terdepan

    void hapusDepan (){
    TNode *hapus;
    int d;
    if (isEmpty()==0){
    if(head->next != NULL){
    hapus = head;
    d = hapus->data;
    head = head->next;
    delete hapus;
    } else {
    d = head->data;
    head = NULL;
    }
    cout<<“%d terhapus\n“,d; } else cout<<"Masih kosong\n"; }







    Function di atas akan menghapus data teratas (pertama) yang ditunjuk oleh head pada linked list. Penghapusan node tidak boleh dilakukan jika keadaan node sedang ditunjuk oleh pointer, maka harus dilakukan penggunakan suatu pointer lain yang digunakan untuk menunjuk node yang akan dihapus, misalnya pointer hapus dan barulah kemudian menghapus pointer hapus dengan menggunakan perintah delete. Sebelum data terdepan dihapus, head harus ditunjukkan ke node sesudahnya terlebih dahulu agar list tidak putus, sehingga node setelah head lama akan menjadi head baru (data terdepan yang baru). Jika head masih NULL maka berarti data masih kosong!


    Hapus Belakang

    void hapusBelakang(){
    TNode *hapus,*bantu;
    int d;
    if (isEmpty()==0){
    if(head->next != NULL){
    bantu = head;
    while(bantu->next->next!=NULL){
    bantu = bantu->next;
    }
    hapus = bantu->next;
    d = hapus->data;
    bantu->next = NULL;
    delete hapus;
    } else {
    d = head->data;
    head = NULL;
    }
    cout<<“%d terhapus\n“,d; } else cout<<“Masih kosong\n“; }


    Membutuhkan pointer bantu dan hapus. Pointer hapus digunakan untuk menunjuk node yang akan dihapus, dan pointer bantu digunakan untuk menunjuk node sebelum node yang dihapus yang kemudian selanjutnya akan menjadi node terakhir. Pointer bantu akan digunakan untuk menunjuk ke nilai NULL. Pointer bantu akan selalu bergerak sampai sebelum node yang akan dihapus, baru kemudian pointer hapus diletakkan setelah pointer bantu. Setelah itu pointer hapus akan dihapus, pointe bantu akan menunjuk ke NULL.















    Function untuk menghapus semua elemen Linked List
    void clear(){
    TNode *bantu,*hapus;
    bantu = head;
    while(bantu!=NULL){
    hapus = bantu;
    bantu = bantu->next;
    delete hapus;
    }
    head = NULL;
    }


    Single Linked List dengan HEAD & TAIL

    Dibutuhkan dua buah variabel pointer: head dan tail. Head akan selalu menunjuk pada node pertama, sedangkan tail akan selalu menunjuk pada node terakhir.






    Inisialisasi LinkedList

    TNode *head, *tail;

    Fungsi Inisialisasi LinkedList

    void init(){

    head = NULL;
    tail = NULL;

    }

    Function untuk mengetahui kosong tidaknya LinkedList

    int isEmpty(){
    if(tail == NULL) return 1;
    else return 0;
    }

    Pengkaitan node baru ke linked list di depan

    Penambahan data baru di depan akan selalu menjadi head.

    void insertDepan(int databaru){
    TNode *baru;
    baru = new TNode;
    baru->data = databaru;
    baru->next = NULL;
    if(isEmpty()==1){
    head=tail=baru;
    tail->next=NULL;
    }
    else {
    baru->next = head;
    head = baru;
    }
    cout<<”Data masuk\n”; }



    1. List masih kosong (head = tail = NULL)






    2. Masuk data baru, misalnya 5







    3. Datang data baru, misalnya 20













    Penambahan Data di belakang

    void tambahBelakang(int databaru){
    TNode *baru,*bantu;
    baru = new TNode;
    baru->data = databaru;
    baru->next = NULL;
    if(isEmpty()==1){
    head=baru;
    tail=baru;
    tail->next = NULL;
    }
    else {
    tail->next = baru;
    tail=baru;
    }
    cout<<"Data masuk\n“; }


    Ilustrasi :
    1. List masih kosong (head = tail = NULL)






    2. Masuk data baru, misalnya 5







    3. Datang data baru, misalnya 20








    Kelebihan dari Single Linked List dengan Head & Tail adalah pada penambahan data di belakang, hanya dibutuhkan tail yang mengikat node baru saja tanpa harus menggunakan perulangan pointer bantu.

    Function untuk menampilkan isi linked list:

    void tampil(){
    TNode *bantu;
    bantu = head;
    if(isEmpty()==0){
    while(bantu!=NULL){
    cout<<“%d\n”,bantu->data;
    bantu=bantu->next;
    }
    cout<<“\n”; } else cout<<“Masih kosong\n“; }







    Function untuk menghapus data di depan

    void hapusDepan(){
    TNode *hapus;
    int d;
    if (isEmpty()==0){
    if(head!=tail){
    hapus = head;
    d = hapus->data;
    head = head->next;
    delete hapus;
    } else {
    d = tail->data;
    head=tail=NULL;
    }
    cout<<“%d terhapus\n“,d; } else cout<<"Masih kosong\n“; }











    Function di atas akan menghapus data terdepan (pertama) yang ditunjuk oleh head pada linked list. Penghapusan node tidak boleh dilakukan jika keadaan node sedang ditunjuk oleh pointer, maka harus dilakukan penunjukkan terlebih dahulu dengan pointer hapus pada head, kemudian dilakukan pergeseran head ke node berikutnya sehingga data setelah head menjadi head baru, kemudian menghapus pointer hapus dengan menggunakan perintah delete. Jika tail masih NULL maka berarti list masih kosong!

    Function untuk menghapus data di belakang:

    void hapusBelakang(){
    TNode *bantu,*hapus;
    int d;
    if (isEmpty()==0){
    bantu = head;
    if(head!=tail){
    while(bantu->next!=tail){
    bantu = bantu->next;
    }
    hapus = tail;
    tail=bantu;
    d = hapus->data;
    delete hapus;
    tail->next = NULL;
    }else {
    d = tail->data;
    head=tail=NULL;
    }
    cout<<<" terhapus\n"; } else cout<<"Masih kosong\n"; }
















    Function di atas akan menghapus data terbelakang (terakhir) yang ditunjuk oleh tail pada linked list. Penghapusan node tidak boleh dilakukan jika keadaan node sedang ditunjuk oleh pointer, maka harus dilakukan penunjukkan terlebih dahulu dengan variabel hapus pada tail, kemudian dibutuhkan pointer bantu untuk membantu pergeseran dari head ke node berikutnya sampai sebelum tail, sehingga tail dapat ditunjukkan ke bantu tersebut, dan bantu tersebut akan menjadi tail yang baru. Setelah itu hapus pointer hapus dengan menggunakan perintah delete. Jika tail masih NULL maka berarti list masih kosong!

    Function untuk menghapus semua elemen LinkedList

    void clear(){
    TNode *bantu,*hapus;
    bantu = head;
    while(bantu!=NULL){
    hapus = bantu;
    bantu = bantu->next;
    delete hapus;
    }
    head = NULL;
    tail = NULL;
    }

    by : Vivi Frismantini (080010231)

    kelas : F081