mirror of
https://github.com/TheAlgorithms/JavaScript.git
synced 2025-07-05 16:26:47 +08:00
chore: convert functions to an ES2015 classes (#1656)
* chore: convert functions to an ES2015 classes * remove unnecessary functions
This commit is contained in:
@ -24,8 +24,8 @@ const RailwayTimeConversion = (timeString) => {
|
|||||||
const [hour, minute, secondWithShift] = timeString.split(':')
|
const [hour, minute, secondWithShift] = timeString.split(':')
|
||||||
// split second and shift value.
|
// split second and shift value.
|
||||||
const [second, shift] = [
|
const [second, shift] = [
|
||||||
secondWithShift.substr(0, 2),
|
secondWithShift.substring(0, 2),
|
||||||
secondWithShift.substr(2)
|
secondWithShift.substring(2)
|
||||||
]
|
]
|
||||||
// convert shifted time to not-shift time(Railway time) by using the above explanation.
|
// convert shifted time to not-shift time(Railway time) by using the above explanation.
|
||||||
if (shift === 'PM') {
|
if (shift === 'PM') {
|
||||||
|
@ -7,11 +7,9 @@
|
|||||||
|
|
||||||
const Reverse = (arr) => {
|
const Reverse = (arr) => {
|
||||||
// limit specifies the amount of Reverse actions
|
// limit specifies the amount of Reverse actions
|
||||||
for (let i = 0, j = arr.length - 1; i < arr.length / 2; i++, j--) {
|
for (let i = 0, j = arr.length - 1; i < arr.length / 2; i++, j--)
|
||||||
const temp = arr[i]
|
[arr[i], arr[j]] = [arr[j], arr[i]]
|
||||||
arr[i] = arr[j]
|
|
||||||
arr[j] = temp
|
|
||||||
}
|
|
||||||
return arr
|
return arr
|
||||||
}
|
}
|
||||||
export { Reverse }
|
export { Reverse }
|
||||||
|
@ -8,8 +8,8 @@
|
|||||||
// Functions: push, pop, peek, view, length
|
// Functions: push, pop, peek, view, length
|
||||||
|
|
||||||
// Creates a stack constructor
|
// Creates a stack constructor
|
||||||
const Stack = (function () {
|
class Stack {
|
||||||
function Stack() {
|
constructor() {
|
||||||
// The top of the Stack
|
// The top of the Stack
|
||||||
this.top = 0
|
this.top = 0
|
||||||
// The array representation of the stack
|
// The array representation of the stack
|
||||||
@ -17,13 +17,13 @@ const Stack = (function () {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// Adds a value onto the end of the stack
|
// Adds a value onto the end of the stack
|
||||||
Stack.prototype.push = function (value) {
|
push(value) {
|
||||||
this.stack[this.top] = value
|
this.stack[this.top] = value
|
||||||
this.top++
|
this.top++
|
||||||
}
|
}
|
||||||
|
|
||||||
// Removes and returns the value at the end of the stack
|
// Removes and returns the value at the end of the stack
|
||||||
Stack.prototype.pop = function () {
|
pop() {
|
||||||
if (this.top === 0) {
|
if (this.top === 0) {
|
||||||
return 'Stack is Empty'
|
return 'Stack is Empty'
|
||||||
}
|
}
|
||||||
@ -35,23 +35,21 @@ const Stack = (function () {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// Returns the size of the stack
|
// Returns the size of the stack
|
||||||
Stack.prototype.size = function () {
|
size() {
|
||||||
return this.top
|
return this.top
|
||||||
}
|
}
|
||||||
|
|
||||||
// Returns the value at the end of the stack
|
// Returns the value at the end of the stack
|
||||||
Stack.prototype.peek = function () {
|
peek() {
|
||||||
return this.stack[this.top - 1]
|
return this.stack[this.top - 1]
|
||||||
}
|
}
|
||||||
|
|
||||||
// To see all the elements in the stack
|
// To see all the elements in the stack
|
||||||
Stack.prototype.view = function (output = (value) => console.log(value)) {
|
view(output = (value) => console.log(value)) {
|
||||||
for (let i = 0; i < this.top; i++) {
|
for (let i = 0; i < this.top; i++) {
|
||||||
output(this.stack[i])
|
output(this.stack[i])
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
}
|
||||||
return Stack
|
|
||||||
})()
|
|
||||||
|
|
||||||
export { Stack }
|
export { Stack }
|
||||||
|
@ -31,8 +31,8 @@ let utils
|
|||||||
* @argument comp - A function used by AVL Tree For Comparison
|
* @argument comp - A function used by AVL Tree For Comparison
|
||||||
* If no argument is sent it uses utils.comparator
|
* If no argument is sent it uses utils.comparator
|
||||||
*/
|
*/
|
||||||
const AVLTree = (function () {
|
class AVLTree {
|
||||||
function _avl(comp) {
|
constructor(comp) {
|
||||||
/** @public comparator function */
|
/** @public comparator function */
|
||||||
this._comp = undefined
|
this._comp = undefined
|
||||||
this._comp = comp !== undefined ? comp : utils.comparator()
|
this._comp = comp !== undefined ? comp : utils.comparator()
|
||||||
@ -43,162 +43,6 @@ const AVLTree = (function () {
|
|||||||
this.size = 0
|
this.size = 0
|
||||||
}
|
}
|
||||||
|
|
||||||
// creates new Node Object
|
|
||||||
const Node = function (val) {
|
|
||||||
this._val = val
|
|
||||||
this._left = null
|
|
||||||
this._right = null
|
|
||||||
this._height = 1
|
|
||||||
}
|
|
||||||
|
|
||||||
// get height of a node
|
|
||||||
const getHeight = function (node) {
|
|
||||||
if (node == null) {
|
|
||||||
return 0
|
|
||||||
}
|
|
||||||
return node._height
|
|
||||||
}
|
|
||||||
|
|
||||||
// height difference or balance factor of a node
|
|
||||||
const getHeightDifference = function (node) {
|
|
||||||
return node == null ? 0 : getHeight(node._left) - getHeight(node._right)
|
|
||||||
}
|
|
||||||
|
|
||||||
// update height of a node based on children's heights
|
|
||||||
const updateHeight = function (node) {
|
|
||||||
if (node == null) {
|
|
||||||
return
|
|
||||||
}
|
|
||||||
node._height = Math.max(getHeight(node._left), getHeight(node._right)) + 1
|
|
||||||
}
|
|
||||||
|
|
||||||
// Helper: To check if the balanceFactor is valid
|
|
||||||
const isValidBalanceFactor = (balanceFactor) =>
|
|
||||||
[0, 1, -1].includes(balanceFactor)
|
|
||||||
|
|
||||||
// rotations of AVL Tree
|
|
||||||
const leftRotate = function (node) {
|
|
||||||
const temp = node._right
|
|
||||||
node._right = temp._left
|
|
||||||
temp._left = node
|
|
||||||
updateHeight(node)
|
|
||||||
updateHeight(temp)
|
|
||||||
return temp
|
|
||||||
}
|
|
||||||
const rightRotate = function (node) {
|
|
||||||
const temp = node._left
|
|
||||||
node._left = temp._right
|
|
||||||
temp._right = node
|
|
||||||
updateHeight(node)
|
|
||||||
updateHeight(temp)
|
|
||||||
return temp
|
|
||||||
}
|
|
||||||
|
|
||||||
// check if tree is balanced else balance it for insertion
|
|
||||||
const insertBalance = function (node, _val, balanceFactor, tree) {
|
|
||||||
if (balanceFactor > 1 && tree._comp(_val, node._left._val) < 0) {
|
|
||||||
return rightRotate(node) // Left Left Case
|
|
||||||
}
|
|
||||||
if (balanceFactor < 1 && tree._comp(_val, node._right._val) > 0) {
|
|
||||||
return leftRotate(node) // Right Right Case
|
|
||||||
}
|
|
||||||
if (balanceFactor > 1 && tree._comp(_val, node._left._val) > 0) {
|
|
||||||
node._left = leftRotate(node._left) // Left Right Case
|
|
||||||
return rightRotate(node)
|
|
||||||
}
|
|
||||||
node._right = rightRotate(node._right)
|
|
||||||
return leftRotate(node)
|
|
||||||
}
|
|
||||||
|
|
||||||
// check if tree is balanced after deletion
|
|
||||||
const delBalance = function (node) {
|
|
||||||
const balanceFactor1 = getHeightDifference(node)
|
|
||||||
if (isValidBalanceFactor(balanceFactor1)) {
|
|
||||||
return node
|
|
||||||
}
|
|
||||||
if (balanceFactor1 > 1) {
|
|
||||||
if (getHeightDifference(node._left) >= 0) {
|
|
||||||
return rightRotate(node) // Left Left
|
|
||||||
}
|
|
||||||
node._left = leftRotate(node._left)
|
|
||||||
return rightRotate(node) // Left Right
|
|
||||||
}
|
|
||||||
if (getHeightDifference(node._right) > 0) {
|
|
||||||
node._right = rightRotate(node._right)
|
|
||||||
return leftRotate(node) // Right Left
|
|
||||||
}
|
|
||||||
return leftRotate(node) // Right Right
|
|
||||||
}
|
|
||||||
|
|
||||||
// implement avl tree insertion
|
|
||||||
const insert = function (root, val, tree) {
|
|
||||||
if (root == null) {
|
|
||||||
tree.size++
|
|
||||||
return new Node(val)
|
|
||||||
}
|
|
||||||
if (tree._comp(root._val, val) < 0) {
|
|
||||||
root._right = insert(root._right, val, tree)
|
|
||||||
} else if (tree._comp(root._val, val) > 0) {
|
|
||||||
root._left = insert(root._left, val, tree)
|
|
||||||
} else {
|
|
||||||
return root
|
|
||||||
}
|
|
||||||
updateHeight(root)
|
|
||||||
const balanceFactor = getHeightDifference(root)
|
|
||||||
return isValidBalanceFactor(balanceFactor)
|
|
||||||
? root
|
|
||||||
: insertBalance(root, val, balanceFactor, tree)
|
|
||||||
}
|
|
||||||
|
|
||||||
// delete am element
|
|
||||||
const deleteElement = function (root, _val, tree) {
|
|
||||||
if (root == null) {
|
|
||||||
return root
|
|
||||||
}
|
|
||||||
if (tree._comp(root._val, _val) === 0) {
|
|
||||||
// key found case
|
|
||||||
if (root._left === null && root._right === null) {
|
|
||||||
root = null
|
|
||||||
tree.size--
|
|
||||||
} else if (root._left === null) {
|
|
||||||
root = root._right
|
|
||||||
tree.size--
|
|
||||||
} else if (root._right === null) {
|
|
||||||
root = root._left
|
|
||||||
tree.size--
|
|
||||||
} else {
|
|
||||||
let temp = root._right
|
|
||||||
while (temp._left != null) {
|
|
||||||
temp = temp._left
|
|
||||||
}
|
|
||||||
root._val = temp._val
|
|
||||||
root._right = deleteElement(root._right, temp._val, tree)
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
if (tree._comp(root._val, _val) < 0) {
|
|
||||||
root._right = deleteElement(root._right, _val, tree)
|
|
||||||
} else {
|
|
||||||
root._left = deleteElement(root._left, _val, tree)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
updateHeight(root)
|
|
||||||
root = delBalance(root)
|
|
||||||
return root
|
|
||||||
}
|
|
||||||
// search tree for a element
|
|
||||||
const searchAVLTree = function (root, val, tree) {
|
|
||||||
if (root == null) {
|
|
||||||
return null
|
|
||||||
}
|
|
||||||
if (tree._comp(root._val, val) === 0) {
|
|
||||||
return root
|
|
||||||
}
|
|
||||||
if (tree._comp(root._val, val) < 0) {
|
|
||||||
return searchAVLTree(root._right, val, tree)
|
|
||||||
}
|
|
||||||
return searchAVLTree(root._left, val, tree)
|
|
||||||
}
|
|
||||||
|
|
||||||
/* Public Functions */
|
/* Public Functions */
|
||||||
/**
|
/**
|
||||||
* For Adding Elements to AVL Tree
|
* For Adding Elements to AVL Tree
|
||||||
@ -207,20 +51,22 @@ const AVLTree = (function () {
|
|||||||
* if a element exists it return false
|
* if a element exists it return false
|
||||||
* @returns {Boolean} element added or not
|
* @returns {Boolean} element added or not
|
||||||
*/
|
*/
|
||||||
_avl.prototype.add = function (_val) {
|
add(_val) {
|
||||||
const prevSize = this.size
|
const prevSize = this.size
|
||||||
this.root = insert(this.root, _val, this)
|
this.root = insert(this.root, _val, this)
|
||||||
return this.size !== prevSize
|
return this.size !== prevSize
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* TO check is a particular element exists or not
|
* TO check is a particular element exists or not
|
||||||
* @param {any} _val
|
* @param {any} _val
|
||||||
* @returns {Boolean} exists or not
|
* @returns {Boolean} exists or not
|
||||||
*/
|
*/
|
||||||
_avl.prototype.find = function (_val) {
|
find(_val) {
|
||||||
const temp = searchAVLTree(this.root, _val, this)
|
const temp = searchAVLTree(this.root, _val, this)
|
||||||
return temp != null
|
return temp != null
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
*
|
*
|
||||||
* @param {any} _val
|
* @param {any} _val
|
||||||
@ -228,13 +74,170 @@ const AVLTree = (function () {
|
|||||||
* in that case it return false
|
* in that case it return false
|
||||||
* @returns {Boolean} if element was found and deleted
|
* @returns {Boolean} if element was found and deleted
|
||||||
*/
|
*/
|
||||||
_avl.prototype.remove = function (_val) {
|
remove(_val) {
|
||||||
const prevSize = this.size
|
const prevSize = this.size
|
||||||
this.root = deleteElement(this.root, _val, this)
|
this.root = deleteElement(this.root, _val, this)
|
||||||
return prevSize !== this.size
|
return prevSize !== this.size
|
||||||
}
|
}
|
||||||
return _avl
|
}
|
||||||
})()
|
|
||||||
|
// creates new Node Object
|
||||||
|
class Node {
|
||||||
|
constructor(val) {
|
||||||
|
this._val = val
|
||||||
|
this._left = null
|
||||||
|
this._right = null
|
||||||
|
this._height = 1
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// get height of a node
|
||||||
|
const getHeight = function (node) {
|
||||||
|
if (node == null) {
|
||||||
|
return 0
|
||||||
|
}
|
||||||
|
return node._height
|
||||||
|
}
|
||||||
|
|
||||||
|
// height difference or balance factor of a node
|
||||||
|
const getHeightDifference = function (node) {
|
||||||
|
return node == null ? 0 : getHeight(node._left) - getHeight(node._right)
|
||||||
|
}
|
||||||
|
|
||||||
|
// update height of a node based on children's heights
|
||||||
|
const updateHeight = function (node) {
|
||||||
|
if (node == null) {
|
||||||
|
return
|
||||||
|
}
|
||||||
|
node._height = Math.max(getHeight(node._left), getHeight(node._right)) + 1
|
||||||
|
}
|
||||||
|
|
||||||
|
// Helper: To check if the balanceFactor is valid
|
||||||
|
const isValidBalanceFactor = (balanceFactor) =>
|
||||||
|
[0, 1, -1].includes(balanceFactor)
|
||||||
|
|
||||||
|
// rotations of AVL Tree
|
||||||
|
const leftRotate = function (node) {
|
||||||
|
const temp = node._right
|
||||||
|
node._right = temp._left
|
||||||
|
temp._left = node
|
||||||
|
updateHeight(node)
|
||||||
|
updateHeight(temp)
|
||||||
|
return temp
|
||||||
|
}
|
||||||
|
const rightRotate = function (node) {
|
||||||
|
const temp = node._left
|
||||||
|
node._left = temp._right
|
||||||
|
temp._right = node
|
||||||
|
updateHeight(node)
|
||||||
|
updateHeight(temp)
|
||||||
|
return temp
|
||||||
|
}
|
||||||
|
|
||||||
|
// check if tree is balanced else balance it for insertion
|
||||||
|
const insertBalance = function (node, _val, balanceFactor, tree) {
|
||||||
|
if (balanceFactor > 1 && tree._comp(_val, node._left._val) < 0) {
|
||||||
|
return rightRotate(node) // Left Left Case
|
||||||
|
}
|
||||||
|
if (balanceFactor < 1 && tree._comp(_val, node._right._val) > 0) {
|
||||||
|
return leftRotate(node) // Right Right Case
|
||||||
|
}
|
||||||
|
if (balanceFactor > 1 && tree._comp(_val, node._left._val) > 0) {
|
||||||
|
node._left = leftRotate(node._left) // Left Right Case
|
||||||
|
return rightRotate(node)
|
||||||
|
}
|
||||||
|
node._right = rightRotate(node._right)
|
||||||
|
return leftRotate(node)
|
||||||
|
}
|
||||||
|
|
||||||
|
// check if tree is balanced after deletion
|
||||||
|
const delBalance = function (node) {
|
||||||
|
const balanceFactor1 = getHeightDifference(node)
|
||||||
|
if (isValidBalanceFactor(balanceFactor1)) {
|
||||||
|
return node
|
||||||
|
}
|
||||||
|
if (balanceFactor1 > 1) {
|
||||||
|
if (getHeightDifference(node._left) >= 0) {
|
||||||
|
return rightRotate(node) // Left Left
|
||||||
|
}
|
||||||
|
node._left = leftRotate(node._left)
|
||||||
|
return rightRotate(node) // Left Right
|
||||||
|
}
|
||||||
|
if (getHeightDifference(node._right) > 0) {
|
||||||
|
node._right = rightRotate(node._right)
|
||||||
|
return leftRotate(node) // Right Left
|
||||||
|
}
|
||||||
|
return leftRotate(node) // Right Right
|
||||||
|
}
|
||||||
|
|
||||||
|
// implement avl tree insertion
|
||||||
|
const insert = function (root, val, tree) {
|
||||||
|
if (root == null) {
|
||||||
|
tree.size++
|
||||||
|
return new Node(val)
|
||||||
|
}
|
||||||
|
if (tree._comp(root._val, val) < 0) {
|
||||||
|
root._right = insert(root._right, val, tree)
|
||||||
|
} else if (tree._comp(root._val, val) > 0) {
|
||||||
|
root._left = insert(root._left, val, tree)
|
||||||
|
} else {
|
||||||
|
return root
|
||||||
|
}
|
||||||
|
updateHeight(root)
|
||||||
|
const balanceFactor = getHeightDifference(root)
|
||||||
|
return isValidBalanceFactor(balanceFactor)
|
||||||
|
? root
|
||||||
|
: insertBalance(root, val, balanceFactor, tree)
|
||||||
|
}
|
||||||
|
|
||||||
|
// delete am element
|
||||||
|
const deleteElement = function (root, _val, tree) {
|
||||||
|
if (root == null) {
|
||||||
|
return root
|
||||||
|
}
|
||||||
|
if (tree._comp(root._val, _val) === 0) {
|
||||||
|
// key found case
|
||||||
|
if (root._left === null && root._right === null) {
|
||||||
|
root = null
|
||||||
|
tree.size--
|
||||||
|
} else if (root._left === null) {
|
||||||
|
root = root._right
|
||||||
|
tree.size--
|
||||||
|
} else if (root._right === null) {
|
||||||
|
root = root._left
|
||||||
|
tree.size--
|
||||||
|
} else {
|
||||||
|
let temp = root._right
|
||||||
|
while (temp._left != null) {
|
||||||
|
temp = temp._left
|
||||||
|
}
|
||||||
|
root._val = temp._val
|
||||||
|
root._right = deleteElement(root._right, temp._val, tree)
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
if (tree._comp(root._val, _val) < 0) {
|
||||||
|
root._right = deleteElement(root._right, _val, tree)
|
||||||
|
} else {
|
||||||
|
root._left = deleteElement(root._left, _val, tree)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
updateHeight(root)
|
||||||
|
root = delBalance(root)
|
||||||
|
return root
|
||||||
|
}
|
||||||
|
// search tree for a element
|
||||||
|
const searchAVLTree = function (root, val, tree) {
|
||||||
|
if (root == null) {
|
||||||
|
return null
|
||||||
|
}
|
||||||
|
if (tree._comp(root._val, val) === 0) {
|
||||||
|
return root
|
||||||
|
}
|
||||||
|
if (tree._comp(root._val, val) < 0) {
|
||||||
|
return searchAVLTree(root._right, val, tree)
|
||||||
|
}
|
||||||
|
return searchAVLTree(root._left, val, tree)
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* A Code for Testing the AVLTree
|
* A Code for Testing the AVLTree
|
||||||
|
@ -13,77 +13,79 @@
|
|||||||
// class Node
|
// class Node
|
||||||
const Node = (function Node() {
|
const Node = (function Node() {
|
||||||
// Node in the tree
|
// Node in the tree
|
||||||
function Node(val) {
|
class Node {
|
||||||
this.value = val
|
constructor(val) {
|
||||||
this.left = null
|
this.value = val
|
||||||
this.right = null
|
this.left = null
|
||||||
}
|
this.right = null
|
||||||
|
|
||||||
// Search the tree for a value
|
|
||||||
Node.prototype.search = function (val) {
|
|
||||||
if (this.value === val) {
|
|
||||||
return this
|
|
||||||
} else if (val < this.value && this.left !== null) {
|
|
||||||
return this.left.search(val)
|
|
||||||
} else if (val > this.value && this.right !== null) {
|
|
||||||
return this.right.search(val)
|
|
||||||
}
|
}
|
||||||
return null
|
|
||||||
}
|
|
||||||
|
|
||||||
// Visit a node
|
// Search the tree for a value
|
||||||
Node.prototype.visit = function (output = (value) => console.log(value)) {
|
search(val) {
|
||||||
// Recursively go left
|
if (this.value === val) {
|
||||||
if (this.left !== null) {
|
return this
|
||||||
this.left.visit()
|
} else if (val < this.value && this.left !== null) {
|
||||||
}
|
return this.left.search(val)
|
||||||
// Print out value
|
} else if (val > this.value && this.right !== null) {
|
||||||
output(this.value)
|
return this.right.search(val)
|
||||||
// Recursively go right
|
|
||||||
if (this.right !== null) {
|
|
||||||
this.right.visit()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
// Add a node
|
|
||||||
Node.prototype.addNode = function (n) {
|
|
||||||
if (n.value < this.value) {
|
|
||||||
if (this.left === null) {
|
|
||||||
this.left = n
|
|
||||||
} else {
|
|
||||||
this.left.addNode(n)
|
|
||||||
}
|
}
|
||||||
} else if (n.value > this.value) {
|
return null
|
||||||
if (this.right === null) {
|
}
|
||||||
this.right = n
|
|
||||||
} else {
|
// Visit a node
|
||||||
this.right.addNode(n)
|
visit(output = (value) => console.log(value)) {
|
||||||
|
// Recursively go left
|
||||||
|
if (this.left !== null) {
|
||||||
|
this.left.visit()
|
||||||
|
}
|
||||||
|
// Print out value
|
||||||
|
output(this.value)
|
||||||
|
// Recursively go right
|
||||||
|
if (this.right !== null) {
|
||||||
|
this.right.visit()
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
|
||||||
|
|
||||||
// remove a node
|
// Add a node
|
||||||
Node.prototype.removeNode = function (val) {
|
addNode(n) {
|
||||||
if (val === this.value) {
|
if (n.value < this.value) {
|
||||||
if (!this.left && !this.right) {
|
if (this.left === null) {
|
||||||
return null
|
this.left = n
|
||||||
} else {
|
|
||||||
if (this.left) {
|
|
||||||
const leftMax = maxVal(this.left)
|
|
||||||
this.value = leftMax
|
|
||||||
this.left = this.left.removeNode(leftMax)
|
|
||||||
} else {
|
} else {
|
||||||
const rightMin = minVal(this.right)
|
this.left.addNode(n)
|
||||||
this.value = rightMin
|
}
|
||||||
this.right = this.right.removeNode(rightMin)
|
} else if (n.value > this.value) {
|
||||||
|
if (this.right === null) {
|
||||||
|
this.right = n
|
||||||
|
} else {
|
||||||
|
this.right.addNode(n)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
} else if (val < this.value) {
|
|
||||||
this.left = this.left && this.left.removeNode(val)
|
|
||||||
} else if (val > this.value) {
|
|
||||||
this.right = this.right && this.right.removeNode(val)
|
|
||||||
}
|
}
|
||||||
return this
|
|
||||||
|
// remove a node
|
||||||
|
removeNode(val) {
|
||||||
|
if (val === this.value) {
|
||||||
|
if (!this.left && !this.right) {
|
||||||
|
return null
|
||||||
|
} else {
|
||||||
|
if (this.left) {
|
||||||
|
const leftMax = maxVal(this.left)
|
||||||
|
this.value = leftMax
|
||||||
|
this.left = this.left.removeNode(leftMax)
|
||||||
|
} else {
|
||||||
|
const rightMin = minVal(this.right)
|
||||||
|
this.value = rightMin
|
||||||
|
this.right = this.right.removeNode(rightMin)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
} else if (val < this.value) {
|
||||||
|
this.left = this.left && this.left.removeNode(val)
|
||||||
|
} else if (val > this.value) {
|
||||||
|
this.right = this.right && this.right.removeNode(val)
|
||||||
|
}
|
||||||
|
return this
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// find maximum value in the tree
|
// find maximum value in the tree
|
||||||
@ -107,44 +109,46 @@ const Node = (function Node() {
|
|||||||
|
|
||||||
// class Tree
|
// class Tree
|
||||||
const Tree = (function () {
|
const Tree = (function () {
|
||||||
function Tree() {
|
class Tree {
|
||||||
// Just store the root
|
constructor() {
|
||||||
this.root = null
|
// Just store the root
|
||||||
}
|
this.root = null
|
||||||
|
|
||||||
// Inorder traversal
|
|
||||||
Tree.prototype.traverse = function () {
|
|
||||||
if (!this.root) {
|
|
||||||
// No nodes are there in the tree till now
|
|
||||||
return
|
|
||||||
}
|
}
|
||||||
this.root.visit()
|
|
||||||
}
|
|
||||||
|
|
||||||
// Start by searching the root
|
// Inorder traversal
|
||||||
Tree.prototype.search = function (val) {
|
traverse() {
|
||||||
const found = this.root.search(val)
|
if (!this.root) {
|
||||||
if (found !== null) {
|
// No nodes are there in the tree till now
|
||||||
return found.value
|
return
|
||||||
|
}
|
||||||
|
this.root.visit()
|
||||||
}
|
}
|
||||||
// not found
|
|
||||||
return null
|
|
||||||
}
|
|
||||||
|
|
||||||
// Add a new value to the tree
|
// Start by searching the root
|
||||||
Tree.prototype.addValue = function (val) {
|
search(val) {
|
||||||
const n = new Node(val)
|
const found = this.root.search(val)
|
||||||
if (this.root === null) {
|
if (found !== null) {
|
||||||
this.root = n
|
return found.value
|
||||||
} else {
|
}
|
||||||
this.root.addNode(n)
|
// not found
|
||||||
|
return null
|
||||||
}
|
}
|
||||||
}
|
|
||||||
|
|
||||||
// remove a value from the tree
|
// Add a new value to the tree
|
||||||
Tree.prototype.removeValue = function (val) {
|
addValue(val) {
|
||||||
// remove something if root exists
|
const n = new Node(val)
|
||||||
this.root = this.root && this.root.removeNode(val)
|
if (this.root === null) {
|
||||||
|
this.root = n
|
||||||
|
} else {
|
||||||
|
this.root.addNode(n)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// remove a value from the tree
|
||||||
|
removeValue(val) {
|
||||||
|
// remove something if root exists
|
||||||
|
this.root = this.root && this.root.removeNode(val)
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// returns the constructor
|
// returns the constructor
|
||||||
|
@ -1,129 +1,132 @@
|
|||||||
const TrieNode = function TrieNode(key, parent) {
|
class TrieNode {
|
||||||
this.key = key
|
constructor(key, parent) {
|
||||||
this.count = 0
|
this.key = key
|
||||||
this.children = Object.create(null)
|
this.count = 0
|
||||||
if (parent === undefined) {
|
this.children = Object.create(null)
|
||||||
this.parent = null
|
if (parent === undefined) {
|
||||||
} else {
|
this.parent = null
|
||||||
this.parent = parent
|
} else {
|
||||||
}
|
this.parent = parent
|
||||||
}
|
|
||||||
|
|
||||||
function Trie() {
|
|
||||||
// create only root with null key and parent
|
|
||||||
this.root = new TrieNode(null, null)
|
|
||||||
}
|
|
||||||
|
|
||||||
// Recursively finds the occurrence of all words in a given node
|
|
||||||
Trie.findAllWords = function (root, word, output) {
|
|
||||||
if (root === null) return
|
|
||||||
if (root.count > 0) {
|
|
||||||
if (typeof output === 'object') {
|
|
||||||
output.push({ word, count: root.count })
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
let key
|
|
||||||
for (key in root.children) {
|
|
||||||
word += key
|
|
||||||
this.findAllWords(root.children[key], word, output)
|
|
||||||
word = word.slice(0, -1)
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
Trie.prototype.insert = function (word) {
|
class Trie {
|
||||||
if (typeof word !== 'string') return
|
constructor() {
|
||||||
if (word === '') {
|
// create only root with null key and parent
|
||||||
this.root.count += 1
|
this.root = new TrieNode(null, null)
|
||||||
return
|
|
||||||
}
|
}
|
||||||
let node = this.root
|
|
||||||
const len = word.length
|
// Recursively finds the occurrence of all words in a given node
|
||||||
let i
|
static findAllWords(root, word, output) {
|
||||||
for (i = 0; i < len; i++) {
|
if (root === null) return
|
||||||
if (node.children[word.charAt(i)] === undefined) {
|
if (root.count > 0) {
|
||||||
node.children[word.charAt(i)] = new TrieNode(word.charAt(i), node)
|
if (typeof output === 'object') {
|
||||||
|
output.push({ word, count: root.count })
|
||||||
|
}
|
||||||
|
}
|
||||||
|
let key
|
||||||
|
for (key in root.children) {
|
||||||
|
word += key
|
||||||
|
this.findAllWords(root.children[key], word, output)
|
||||||
|
word = word.slice(0, -1)
|
||||||
}
|
}
|
||||||
node = node.children[word.charAt(i)]
|
|
||||||
}
|
|
||||||
node.count += 1
|
|
||||||
}
|
|
||||||
|
|
||||||
Trie.prototype.findPrefix = function (word) {
|
|
||||||
if (typeof word !== 'string') return null
|
|
||||||
let node = this.root
|
|
||||||
const len = word.length
|
|
||||||
let i
|
|
||||||
// After end of this loop node will be at desired prefix
|
|
||||||
for (i = 0; i < len; i++) {
|
|
||||||
if (node.children[word.charAt(i)] === undefined) return null // No such prefix exists
|
|
||||||
node = node.children[word.charAt(i)]
|
|
||||||
}
|
|
||||||
return node
|
|
||||||
}
|
|
||||||
|
|
||||||
Trie.prototype.remove = function (word, count) {
|
|
||||||
if (typeof word !== 'string') return
|
|
||||||
if (typeof count !== 'number') count = 1
|
|
||||||
else if (count <= 0) return
|
|
||||||
|
|
||||||
// for empty string just delete count of root
|
|
||||||
if (word === '') {
|
|
||||||
if (this.root.count >= count) this.root.count -= count
|
|
||||||
else this.root.count = 0
|
|
||||||
return
|
|
||||||
}
|
}
|
||||||
|
|
||||||
let child = this.root
|
insert(word) {
|
||||||
const len = word.length
|
if (typeof word !== 'string') return
|
||||||
let i, key
|
if (word === '') {
|
||||||
// child: node which is to be deleted
|
this.root.count += 1
|
||||||
for (i = 0; i < len; i++) {
|
return
|
||||||
key = word.charAt(i)
|
}
|
||||||
if (child.children[key] === undefined) return
|
let node = this.root
|
||||||
child = child.children[key]
|
const len = word.length
|
||||||
|
let i
|
||||||
|
for (i = 0; i < len; i++) {
|
||||||
|
if (node.children[word.charAt(i)] === undefined) {
|
||||||
|
node.children[word.charAt(i)] = new TrieNode(word.charAt(i), node)
|
||||||
|
}
|
||||||
|
node = node.children[word.charAt(i)]
|
||||||
|
}
|
||||||
|
node.count += 1
|
||||||
}
|
}
|
||||||
|
|
||||||
// Delete no of occurrences specified
|
findPrefix(word) {
|
||||||
if (child.count >= count) child.count -= count
|
if (typeof word !== 'string') return null
|
||||||
else child.count = 0
|
let node = this.root
|
||||||
|
const len = word.length
|
||||||
// If some occurrences are left we don't delete it or else
|
let i
|
||||||
// if the object forms some other objects prefix we don't delete it
|
// After end of this loop node will be at desired prefix
|
||||||
// For checking an empty object
|
for (i = 0; i < len; i++) {
|
||||||
// https://stackoverflow.com/questions/679915/how-do-i-test-for-an-empty-javascript-object
|
if (node.children[word.charAt(i)] === undefined) return null // No such prefix exists
|
||||||
if (
|
node = node.children[word.charAt(i)]
|
||||||
child.count <= 0 &&
|
}
|
||||||
Object.keys(child.children).length &&
|
return node
|
||||||
child.children.constructor === Object
|
|
||||||
) {
|
|
||||||
child.parent.children[child.key] = undefined
|
|
||||||
}
|
}
|
||||||
}
|
|
||||||
|
|
||||||
Trie.prototype.findAllWords = function (prefix) {
|
remove(word, count) {
|
||||||
const output = []
|
if (typeof word !== 'string') return
|
||||||
// find the node with provided prefix
|
if (typeof count !== 'number') count = 1
|
||||||
const node = this.findPrefix(prefix)
|
else if (count <= 0) return
|
||||||
// No such prefix exists
|
|
||||||
if (node === null) return output
|
|
||||||
Trie.findAllWords(node, prefix, output)
|
|
||||||
return output
|
|
||||||
}
|
|
||||||
|
|
||||||
Trie.prototype.contains = function (word) {
|
// for empty string just delete count of root
|
||||||
// find the node with given prefix
|
if (word === '') {
|
||||||
const node = this.findPrefix(word)
|
if (this.root.count >= count) this.root.count -= count
|
||||||
// No such word exists
|
else this.root.count = 0
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
return node !== null && node.count !== 0
|
let child = this.root
|
||||||
}
|
const len = word.length
|
||||||
|
let i, key
|
||||||
|
// child: node which is to be deleted
|
||||||
|
for (i = 0; i < len; i++) {
|
||||||
|
key = word.charAt(i)
|
||||||
|
if (child.children[key] === undefined) return
|
||||||
|
child = child.children[key]
|
||||||
|
}
|
||||||
|
|
||||||
Trie.prototype.findOccurrences = function (word) {
|
// Delete no of occurrences specified
|
||||||
// find the node with given prefix
|
if (child.count >= count) child.count -= count
|
||||||
const node = this.findPrefix(word)
|
else child.count = 0
|
||||||
// No such word exists
|
|
||||||
if (node === null) return 0
|
// If some occurrences are left we don't delete it or else
|
||||||
return node.count
|
// if the object forms some other objects prefix we don't delete it
|
||||||
|
// For checking an empty object
|
||||||
|
// https://stackoverflow.com/questions/679915/how-do-i-test-for-an-empty-javascript-object
|
||||||
|
if (
|
||||||
|
child.count <= 0 &&
|
||||||
|
Object.keys(child.children).length &&
|
||||||
|
child.children.constructor === Object
|
||||||
|
) {
|
||||||
|
child.parent.children[child.key] = undefined
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
findAllWords(prefix) {
|
||||||
|
const output = []
|
||||||
|
// find the node with provided prefix
|
||||||
|
const node = this.findPrefix(prefix)
|
||||||
|
// No such prefix exists
|
||||||
|
if (node === null) return output
|
||||||
|
Trie.findAllWords(node, prefix, output)
|
||||||
|
return output
|
||||||
|
}
|
||||||
|
|
||||||
|
contains(word) {
|
||||||
|
// find the node with given prefix
|
||||||
|
const node = this.findPrefix(word)
|
||||||
|
// No such word exists
|
||||||
|
return node !== null && node.count !== 0
|
||||||
|
}
|
||||||
|
|
||||||
|
findOccurrences(word) {
|
||||||
|
// find the node with given prefix
|
||||||
|
const node = this.findPrefix(word)
|
||||||
|
// No such word exists
|
||||||
|
if (node === null) return 0
|
||||||
|
return node.count
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
export { Trie }
|
export { Trie }
|
||||||
|
@ -4,7 +4,7 @@ determine the total number of the subset with sum
|
|||||||
equal to the given sum.
|
equal to the given sum.
|
||||||
*/
|
*/
|
||||||
/*
|
/*
|
||||||
Given solution is O(n*sum) Time complexity and O(sum) Space complexity
|
Given solution is O(n*sum) Time complexity and O(sum) Space complexity
|
||||||
*/
|
*/
|
||||||
function NumberOfSubsetSum(array, sum) {
|
function NumberOfSubsetSum(array, sum) {
|
||||||
const dp = [] // create an dp array where dp[i] denote number of subset with sum equal to i
|
const dp = [] // create an dp array where dp[i] denote number of subset with sum equal to i
|
||||||
|
@ -1,6 +1,6 @@
|
|||||||
// https://projecteuler.net/problem=4
|
// https://projecteuler.net/problem=4
|
||||||
/* A palindromic number reads the same both ways. The largest palindrome made from the product of two 2-digit numbers is 9009 = 91 × 99.
|
/* A palindromic number reads the same both ways. The largest palindrome made from the product of two 2-digit numbers is 9009 = 91 × 99.
|
||||||
Find the largest palindrome made from the product of two 3-digit numbers.
|
Find the largest palindrome made from the product of two 3-digit numbers.
|
||||||
*/
|
*/
|
||||||
export const largestPalindromic = (digits) => {
|
export const largestPalindromic = (digits) => {
|
||||||
let i
|
let i
|
||||||
|
Reference in New Issue
Block a user