Test that it is possible to use objects and binary tree node values.

This commit is contained in:
Oleksii Trekhleb 2018-05-30 07:19:48 +03:00
parent 625217a9c2
commit 3ae9c40416
2 changed files with 71 additions and 4 deletions

View File

@ -1,11 +1,23 @@
import Comparator from '../../utils/comparator/Comparator';
export default class BinaryTreeNode { export default class BinaryTreeNode {
/**
* @param {*} value
* @param {BinaryTreeNode} parent
*/
constructor(value = null, parent = null) { constructor(value = null, parent = null) {
this.left = null; this.left = null;
this.right = null; this.right = null;
this.parent = parent; this.parent = parent;
this.value = value; this.value = value;
// This comparator is used to compare binary tree nodes with each other.
this.nodeComparator = new Comparator();
} }
/**
* @return {number}
*/
get leftHeight() { get leftHeight() {
if (!this.left) { if (!this.left) {
return 0; return 0;
@ -14,6 +26,9 @@ export default class BinaryTreeNode {
return this.left.height + 1; return this.left.height + 1;
} }
/**
* @return {number}
*/
get rightHeight() { get rightHeight() {
if (!this.right) { if (!this.right) {
return 0; return 0;
@ -22,14 +37,24 @@ export default class BinaryTreeNode {
return this.right.height + 1; return this.right.height + 1;
} }
/**
* @return {number}
*/
get height() { get height() {
return Math.max(this.leftHeight, this.rightHeight); return Math.max(this.leftHeight, this.rightHeight);
} }
/**
* @return {number}
*/
get balanceFactor() { get balanceFactor() {
return this.leftHeight - this.rightHeight; return this.leftHeight - this.rightHeight;
} }
/**
* @param {BinaryTreeNode} node
* @return {BinaryTreeNode}
*/
setLeft(node) { setLeft(node) {
// Reset parent for left node since it is going to be detached. // Reset parent for left node since it is going to be detached.
if (this.left) { if (this.left) {
@ -47,6 +72,10 @@ export default class BinaryTreeNode {
return this; return this;
} }
/**
* @param {BinaryTreeNode} node
* @return {BinaryTreeNode}
*/
setRight(node) { setRight(node) {
// Reset parent for right node since it is going to be detached. // Reset parent for right node since it is going to be detached.
if (this.right) { if (this.right) {
@ -64,13 +93,17 @@ export default class BinaryTreeNode {
return this; return this;
} }
/**
* @param {BinaryTreeNode} nodeToRemove
* @return {boolean}
*/
removeChild(nodeToRemove) { removeChild(nodeToRemove) {
if (this.left && this.left === nodeToRemove) { if (this.left && this.nodeComparator.equal(this.left, nodeToRemove)) {
this.left = null; this.left = null;
return true; return true;
} }
if (this.right && this.right === nodeToRemove) { if (this.right && this.nodeComparator.equal(this.right, nodeToRemove)) {
this.right = null; this.right = null;
return true; return true;
} }
@ -78,17 +111,22 @@ export default class BinaryTreeNode {
return false; return false;
} }
/**
* @param {BinaryTreeNode} nodeToReplace
* @param {BinaryTreeNode} replacementNode
* @return {boolean}
*/
replaceChild(nodeToReplace, replacementNode) { replaceChild(nodeToReplace, replacementNode) {
if (!nodeToReplace || !replacementNode) { if (!nodeToReplace || !replacementNode) {
return false; return false;
} }
if (this.left && this.left === nodeToReplace) { if (this.left && this.nodeComparator.equal(this.left, nodeToReplace)) {
this.left = replacementNode; this.left = replacementNode;
return true; return true;
} }
if (this.right && this.right === nodeToReplace) { if (this.right && this.nodeComparator.equal(this.right, nodeToReplace)) {
this.right = replacementNode; this.right = replacementNode;
return true; return true;
} }
@ -96,6 +134,9 @@ export default class BinaryTreeNode {
return false; return false;
} }
/**
* @return {*[]}
*/
traverseInOrder() { traverseInOrder() {
let traverse = []; let traverse = [];
@ -115,6 +156,9 @@ export default class BinaryTreeNode {
return traverse; return traverse;
} }
/**
* @return {string}
*/
toString() { toString() {
return this.traverseInOrder().toString(); return this.traverseInOrder().toString();
} }

View File

@ -173,4 +173,27 @@ describe('BinaryTreeNode', () => {
expect(root.left).toBeNull(); expect(root.left).toBeNull();
expect(root.right).toBeNull(); expect(root.right).toBeNull();
}); });
it('should be possible to create node with object as a value', () => {
const obj1 = { key: 'object_1', toString: () => 'object_1' };
const obj2 = { key: 'object_2' };
const node1 = new BinaryTreeNode(obj1);
const node2 = new BinaryTreeNode(obj2);
node1.setLeft(node2);
expect(node1.value).toEqual(obj1);
expect(node2.value).toEqual(obj2);
expect(node1.left.value).toEqual(obj2);
node1.removeChild(node2);
expect(node1.value).toEqual(obj1);
expect(node2.value).toEqual(obj2);
expect(node1.left).toBeNull();
expect(node1.toString()).toBe('object_1');
expect(node2.toString()).toBe('[object Object]');
});
}); });