addLast(value) {
    const newNode = new Node(value);

    if (this.first) { // check if first node exists (list not empty)
      newNode.previous = this.last;
      this.last.next = newNode;
      this.last = newNode;
    } else { // if list is empty, first & last will point to newNode.
      this.first = newNode;
      this.last = newNode;
    }

    this.size += 1;

    return newNode;
  }
Adds element to the end of the list (tail). Similar to Array.push
Using the element last reference instead of navigating through the list,
we can reduced from linear to a constant runtime.
Runtime: O(1)
@param {any} value node's value
@returns {Node} newly created node