mirror of
https://github.com/TheAlgorithms/JavaScript.git
synced 2025-07-06 09:28:26 +08:00

* Auto-update DIRECTORY.md * Update and rename SingleCircularLinkedList.js.js to SinglyCircularLinkedList.js * Test Case creation for SinglyCircularLinkedList * Update SinglyCircularLinkedList.js * Update SinglyCircularLinkedList.test.js * Update SinglyCircularLinkedList.js Co-authored-by: github-actions <${GITHUB_ACTOR}@users.noreply.github.com>
158 lines
4.3 KiB
JavaScript
158 lines
4.3 KiB
JavaScript
// Methods - size, head, isEmpty, getElementAt, addAtFirst, add, clean, insertAt, remove, removeData, printData, get, clear
|
|
import { Node } from './SinglyLinkedList.js'
|
|
|
|
class SinglyCircularLinkedList {
|
|
constructor () {
|
|
this.headNode = null
|
|
this.length = 0
|
|
}
|
|
|
|
// Get size of the linkedList
|
|
size = () => this.length
|
|
// Get the headNode data
|
|
head = () => this.headNode?.data || null
|
|
// Check if the linkedList is empty
|
|
isEmpty = () => this.length === 0
|
|
|
|
// initiate the node and index
|
|
initiateNodeAndIndex () {
|
|
return { currentNode: this.headNode, currentIndex: 0 }
|
|
}
|
|
|
|
// get the data specific to an index
|
|
getElementAt (index) {
|
|
if (this.length !== 0 && index >= 0 && index <= this.length) {
|
|
let { currentNode } = this.initiateNodeAndIndex()
|
|
for (let i = 0; i < index && currentNode !== null; i++) {
|
|
currentNode = currentNode.next
|
|
}
|
|
return currentNode
|
|
}
|
|
return undefined
|
|
}
|
|
|
|
// Add the element in the first position
|
|
addAtFirst (data) {
|
|
const node = new Node(data)
|
|
node.next = this.headNode
|
|
this.headNode = node
|
|
this.length++
|
|
return this.length
|
|
}
|
|
|
|
// Add any data to the end of the linkedList
|
|
add (data) {
|
|
if (!this.headNode) { return this.addAtFirst(data) }
|
|
const node = new Node(data)
|
|
// Getting the last node
|
|
const currentNode = this.getElementAt(this.length - 1)
|
|
currentNode.next = node
|
|
node.next = this.headNode
|
|
this.length++
|
|
return this.length
|
|
}
|
|
|
|
// insert data at a specific position
|
|
insertAt (index, data) {
|
|
if (index === 0) return this.addAtFirst(data)
|
|
if (index === this.length) return this.add(data)
|
|
if (index < 0 || index > this.length) throw new RangeError(`Index is out of range max ${this.length}`)
|
|
const node = new Node(data)
|
|
const previousNode = this.getElementAt(index - 1)
|
|
node.next = previousNode.next
|
|
previousNode.next = node
|
|
this.length++
|
|
return this.length
|
|
}
|
|
|
|
// find the first index of the data
|
|
indexOf (data) {
|
|
let { currentNode } = this.initiateNodeAndIndex()
|
|
// initializing currentIndex as -1
|
|
let currentIndex = -1
|
|
while (currentNode) {
|
|
if (currentNode.data === data) {
|
|
return currentIndex + 1
|
|
}
|
|
currentIndex++
|
|
currentNode = currentNode.next
|
|
}
|
|
return -1
|
|
}
|
|
|
|
// remove the data from the end of the list
|
|
remove () {
|
|
if (this.isEmpty()) return null
|
|
const secondLastNode = this.getElementAt(this.length - 2)
|
|
const removedNode = secondLastNode.next
|
|
secondLastNode.next = this.headNode
|
|
this.length--
|
|
return removedNode.data || null
|
|
}
|
|
|
|
// remove the data from the first of the list
|
|
removeFirst () {
|
|
if (this.isEmpty()) return null
|
|
const removedNode = this.headNode
|
|
if (this.length === 1) {
|
|
this.clear()
|
|
return removedNode.data
|
|
}
|
|
const lastNode = this.getElementAt(this.length - 1)
|
|
this.headNode = this.headNode.next
|
|
lastNode.next = this.headNode
|
|
this.length--
|
|
return removedNode.data || null
|
|
}
|
|
|
|
// remove the data from the index
|
|
removeAt (index) {
|
|
if (this.isEmpty()) return null
|
|
if (index === 0) return this.removeFirst()
|
|
if (index === this.length) return this.remove()
|
|
if (index < 0 && index > this.length) return null
|
|
const previousNode = this.getElementAt(index - 1)
|
|
const currentNode = previousNode.next
|
|
previousNode.next = currentNode.next
|
|
this.length--
|
|
return currentNode.data || null
|
|
}
|
|
|
|
// remove if the data is present
|
|
removeData (data) {
|
|
if (this.isEmpty()) return null
|
|
const index = this.indexOf(data)
|
|
return this.removeAt(index)
|
|
}
|
|
|
|
// logs the data
|
|
printData (output = value => console.log(value)) {
|
|
let { currentIndex, currentNode } = this.initiateNodeAndIndex()
|
|
|
|
while (currentNode !== null && currentIndex < this.length) {
|
|
output(currentNode.data)
|
|
currentNode = currentNode.next
|
|
currentIndex++
|
|
}
|
|
}
|
|
|
|
// get the data from the linkedList
|
|
get () {
|
|
let { currentIndex, currentNode } = this.initiateNodeAndIndex()
|
|
const list = []
|
|
while (currentNode !== null && currentIndex < this.length) {
|
|
list.push(currentNode.data)
|
|
currentNode = currentNode.next
|
|
currentIndex++
|
|
}
|
|
return list
|
|
}
|
|
|
|
clear () {
|
|
this.headNode = null
|
|
this.length = 0
|
|
}
|
|
}
|
|
|
|
export { SinglyCircularLinkedList }
|