Data Structure :: Singly Linked Lists

Data Structure :: Singly Linked Lists

What is a linked list?
A data structure that contains a head, tail and length property.

Linked lists consist of nodes, and each node has a value and a pointer to another node or null.

Everything is about node, and how to set .next to some value..!

class Node{
    constructor(val){
        this.val = val;
        this.next = null;
    }
}

class SinglyLinkedList{
    constructor(){
        this.length = 0;
        this.head = null;
        this.tail = null;
    }
    push(val){
        let newNode = new Node(val);
        if(!this.head){
            this.head = newNode;
            this.tail = this.head;
        } else {
            this.tail.next = newNode; // 먼저 현재 테일 다음위치에 newNode 지정하고
            this.tail = newNode; // 테일을 그 녀석으로 바꿈
        }
        this.length++;
        return this;
    }
    pop(){
        if(!this.head) return undefined;
        let current = this.head;
        let newTail = current;
        while(current.next){
            newTail = current;
            currnet = current.next;
        }
        this.tail = newTail;
        this.tail.next = null;
        this.legnth--;
        return current;
    } 
    // pop은 current, newTail 두개를 가지고 작동시킨다.
    shift(){
        if(!this.head) return undefined;
        let currentHead = this.head;
        this.head = currentHead.next;
        this.length--;
        return currentHead;
    }
    unshift(val){
        let newNode = new Node(val);
        if(!this.head) { 
            this.head = newNode;
            this.tail = this.head;
        } else {
            newNode.next = this.head;
            this.head = newNode;
        }
        this.length++;
        return this;
    }
    /* Get : Retrieving a node by it's position*/
    get(index){
        if(index < 0 || index >= this.length) return null;
        let counter = 0;
        let current = this.head;
        while(counter !== index){
            current = current.next;
            counter++;
        }
        return current;
    }
    /* Set : Changing the value of a node based on 
    it's position in the Linked List */
    set(index, val){
        let foundNode = this.get(index);
        if(foundNode) {
            foundNode.val = val;
            return true;
        }
        return false;
    }
    /* Insert : Adding a node to the Linked List
    at a specific position */
    insert(index, val){
        if(index < 0 || index > this.length) retrun false;
        if(index === this.length) return this.push(val);
        if(index === 0) return this.unshift(val);
        let newNode = new Node(val);
        let prev = this.get(index - 1);
        let temp = prev;
        prev.next = newNode;
        newNode.next = temp;
        this.length++;
        return true;
    }
    /* Remove : Removing a node from the Linked List at a 
    specific position */
    remove(index) {
        if(index < 0 || index > this.length) return undefiend;
        if(index === this.length - 1 ) return this.pop();
        if(index == 0) return this.shift();
        let previousNode = this.get(index-1);
        let removed = previousNode.next;
        previousNode.next = removed.next;
        this.length--;
        return removed;
    }
    /* Reverse : Reversing the Linked List */
    reverse(){
        let node = this.head;
        this.head = this.tail;
        this.tail = node;
        let next;
        let prev = null;
        for(let i = 0; i < this.length; i++) {
            next = node.next; 
            node.next = prev; // 여기가 제일 중요, 나머지는 변수 재설정 급 
            prev = node;
            node = next;
        }
        return this;
    }
}

Big O of Singly Linked List

Insertion at the begging or at the end O(1) : Take the current end, the tail, make a new node and just set the tail next to that new node // Same thing at the beginning, make a new node and its dot next to be the head, and then move the head.

Insertion general O(n) : Cause you have to get into that position

Removal, It depends O(1) or O(n) : From the beginning, its O(1), take the current head and set its dot next to be the next head, and take out the old head. // From the end, we need to find item right before the tail, and that involves iterating the entire list.

Searching O(n), Accessing O(n) : we need to check every single node, as the numbers growth, so does the number of operation there.