JSFiddle - React, Tailwind, and code Playground

by asdf

HTML

<!-- You have genealogical (family) tree. Each node is a person, children of a node are children of a person. Assume names of all of the people are unique. Given two names determine who is the nearest common ancestor (for both of them). For example,
                      Mike
                   /      |     \
              Dory       Ann    John
            /    |        |        \
   Tiffany       Ron     Ted        Lucy

for Tiffany and Ron answer will be Dory
for Ron and John answers will be Mike -->

JavaScript

function getNode(val, children) {
	var node = {
  	value: val, 
    children: children || []
  }; 
	return node;
}
var tif = getNode('Tiffany');
var ron = getNode('Ron');
var ted = getNode('Ted');
var luc = getNode('Lucy');
var dor = getNode('Dory', [tif, ron]);
var ann = getNode('Ann', [ted]);
var joh = getNode('John', [luc]);
var mik = getNode('Mike', [dor, ann, joh]);

function getAncestor2(p1, p2, node, result) {  
	// res = 0 - nothing found
  // res = 1 - p1 found
  // res = 2 - p2 found
  // res = 3 - p1 and p2 found, i.e. 1+2=3
  var res = 0;
  for (var i=0; i<node.children.length; i++) {
    res += getAncestor2(p1, p2, node.children[i], result);
    // optimization - quit early if we found both names already
    //if (res == 3) {
    //  if (!result.commonParent) {
    //    result.commonParent = node.value;
    //  }
    //  return res;
    //}
  }
  if (p1 === node.value) {
    res += 1;
  }
  if (p2 === node.value) {
		res += 2;
  }
  if (res == 3 && !result.commonParent) {
    result.commonParent = node.value;
  }
  return res;
}

var result = {
   commonParent: null
};
getAncestor2('Tiffany', 'Ron', mik, result);
console.log(result.commonParent);
result.commonParent = null;
getAncestor2('John', 'Ron', mik, result);
console.log(result.commonParent);
result.commonParent = null;
getAncestor2('Ann', 'Ted', mik, result);
console.log(result.commonParent);
console.log('------');

function contains(val, node) {
	if (node.value === val) {
  	return true;
  }
  for (var i=0; i<node.children.length; i++) {
  	if (contains(val, node.children[i])) {
    	return true;
    }
  }
	return false;
}

function getAncestor(p1, p2, node) {
	var anc, temp;
  if (contains(p1, node) && contains(p2, node)) {
  	anc = node.value;
    for (var i=0; i<node.children.length; i++) {
      temp = getAncestor(p1, p2, node.children[i]);
      if (temp) {
      	anc = temp;
      }
    }
  }
  return anc;
}
console.log(getAncestor('Tiffany', 'Ron',...