function(dataset, treeNode) {
		var superlabelsDataset = [];
		var mapSuperlabelToRestDataset = {};
		dataset.forEach(function(datum) { 
			var splitLabels = datum.output;	// [ [ 'Offer', 'Leased Car', 'Without leased car' ], [ 'Offer', 'Working Hours', '9 hours' ] ]
			var superlabels = {};           // the first parts of each of the splitLabels
			var mapSuperlabelToRest = {};   // each value is a list of continuations of the key. 
			for (var i in splitLabels) { 
				var splitLabel = splitLabels[i];//[ 'Offer', 'Leased Car', 'Without leased car' ]
				var superlabel = splitLabel[0];
				superlabels[superlabel] = true; //superlabels['Offer'] = true
				if (splitLabel.length>1) { 		// if it have more than one label (superlabel)
					if (!mapSuperlabelToRest[superlabel]) 
						mapSuperlabelToRest[superlabel] = [];
					mapSuperlabelToRest[superlabel].push(splitLabel.slice(1));//['Leased Car', 'Without leased car']
				}
			}

/*			Sample of mapSuperlabelToRest
			{ Offer: 
			[ [ 'Leased Car', 'Without leased car' ],
   			  [ 'Working Hours', '9 hours' ] ] }

			Sample of superlabelsDataset, initial dataset with superlabel instead of entire output
			'. [end]': 0.965080896043587 },
			output: [ 'Offer' ] } ]
*/
			superlabelsDataset.push({
				input: datum.input,
				output: Object.keys(superlabels)
			});		

			for (var superlabel in mapSuperlabelToRest) {
				if (!(superlabel in mapSuperlabelToRestDataset)) 
					mapSuperlabelToRestDataset[superlabel] = [];
				mapSuperlabelToRestDataset[superlabel].push({
					input: datum.input,
					output: mapSuperlabelToRest[superlabel]
				});
			}
		}, this);
		
/*		Sample of mapSuperlabelToRestDataset
		{ Offer: [ { input: [Object], output: [["Leased Car","Without leased car"],["Working Hours","9 hours"]] } ] }
*/

		// train the classifier only on superlabels
		treeNode.superlabelClassifier.trainBatch(superlabelsDataset);

		for (var superlabel in mapSuperlabelToRestDataset) {
			if (!(superlabel in treeNode.mapSuperlabelToBranch)) {
				treeNode.mapSuperlabelToBranch[superlabel] = {
					superlabelClassifier: this.newMultilabelClassifier(),
					mapSuperlabelToBranch: {}
				}
			}
/*			train the next level classifier for a give superlabel classifier superlabel (from loop)
			with the dataset from new structure mapSuperlabelToRestDataset (see above)
*/			this.trainBatchRecursive(mapSuperlabelToRestDataset[superlabel], treeNode.mapSuperlabelToBranch[superlabel]);
		}
	}
function(dataset, treeNode) {
		var superlabelsDataset = [];
		var mapSuperlabelToRestDataset = {};
		dataset.forEach(function(datum) { 
			var splitLabels = datum.output;	// [ [ 'Offer', 'Leased Car', 'Without leased car' ], [ 'Offer', 'Working Hours', '9 hours' ] ]
			var superlabels = {};           // the first parts of each of the splitLabels
			var mapSuperlabelToRest = {};   // each value is a list of continuations of the key. 
			for (var i in splitLabels) { 
				var splitLabel = splitLabels[i];//[ 'Offer', 'Leased Car', 'Without leased car' ]
				var superlabel = splitLabel[0];
				superlabels[superlabel] = true; //superlabels['Offer'] = true
				if (splitLabel.length>1) { 		// if it have more than one label (superlabel)
					if (!mapSuperlabelToRest[superlabel]) 
						mapSuperlabelToRest[superlabel] = [];
					mapSuperlabelToRest[superlabel].push(splitLabel.slice(1));//['Leased Car', 'Without leased car']
				}
			}

/*			Sample of mapSuperlabelToRest
			{ Offer: 
			[ [ 'Leased Car', 'Without leased car' ],
   			  [ 'Working Hours', '9 hours' ] ] }

			Sample of superlabelsDataset, initial dataset with superlabel instead of entire output
			'. [end]': 0.965080896043587 },
			output: [ 'Offer' ] } ]
*/
			superlabelsDataset.push({
				input: datum.input,
				output: Object.keys(superlabels)
			});		

			for (var superlabel in mapSuperlabelToRest) {
				if (!(superlabel in mapSuperlabelToRestDataset)) 
					mapSuperlabelToRestDataset[superlabel] = [];
				mapSuperlabelToRestDataset[superlabel].push({
					input: datum.input,
					output: mapSuperlabelToRest[superlabel]
				});
			}
		}, this);
		
/*		Sample of mapSuperlabelToRestDataset
		{ Offer: [ { input: [Object], output: [["Leased Car","Without leased car"],["Working Hours","9 hours"]] } ] }
*/

		// train the classifier only on superlabels
		treeNode.superlabelClassifier.trainBatch(superlabelsDataset);

		for (var superlabel in mapSuperlabelToRestDataset) {
			if (!(superlabel in treeNode.mapSuperlabelToBranch)) {
				treeNode.mapSuperlabelToBranch[superlabel] = {
					superlabelClassifier: this.newMultilabelClassifier(),
					mapSuperlabelToBranch: {}
				}
			}
/*			train the next level classifier for a give superlabel classifier superlabel (from loop)
			with the dataset from new structure mapSuperlabelToRestDataset (see above)
*/			this.trainBatchRecursive(mapSuperlabelToRestDataset[superlabel], treeNode.mapSuperlabelToBranch[superlabel]);
		}
	}
function ( dataset , treeNode ) { var superlabelsDataset = [ ] ; var mapSuperlabelToRestDataset = { } ; dataset . forEach ( function ( datum ) { var splitLabels = datum . output ; // [ [ 'Offer', 'Leased Car', 'Without leased car' ], [ 'Offer', 'Working Hours', '9 hours' ] ] var superlabels = { } ; // the first parts of each of the splitLabels var mapSuperlabelToRest = { } ; // each value is a list of continuations of the key.  for ( var i in splitLabels ) { var splitLabel = splitLabels [ i ] ; //[ 'Offer', 'Leased Car', 'Without leased car' ] var superlabel = splitLabel [ 0 ] ; superlabels [ superlabel ] = true ; //superlabels['Offer'] = true if ( splitLabel . length > 1 ) { // if it have more than one label (superlabel) if ( ! mapSuperlabelToRest [ superlabel ] ) mapSuperlabelToRest [ superlabel ] = [ ] ; mapSuperlabelToRest [ superlabel ] . push ( splitLabel . slice ( 1 ) ) ; //['Leased Car', 'Without leased car'] } } /*			Sample of mapSuperlabelToRest
			{ Offer: 
			[ [ 'Leased Car', 'Without leased car' ],
   			  [ 'Working Hours', '9 hours' ] ] }

			Sample of superlabelsDataset, initial dataset with superlabel instead of entire output
			'. [end]': 0.965080896043587 },
			output: [ 'Offer' ] } ]
*/ superlabelsDataset . push ( { input : datum . input , output : Object . keys ( superlabels ) } ) ; for ( var superlabel in mapSuperlabelToRest ) { if ( ! ( superlabel in mapSuperlabelToRestDataset ) ) mapSuperlabelToRestDataset [ superlabel ] = [ ] ; mapSuperlabelToRestDataset [ superlabel ] . push ( { input : datum . input , output : mapSuperlabelToRest [ superlabel ] } ) ; } } , this ) ; /*		Sample of mapSuperlabelToRestDataset
		{ Offer: [ { input: [Object], output: [["Leased Car","Without leased car"],["Working Hours","9 hours"]] } ] }
*/ // train the classifier only on superlabels treeNode . superlabelClassifier . trainBatch ( superlabelsDataset ) ; for ( var superlabel in mapSuperlabelToRestDataset ) { if ( ! ( superlabel in treeNode . mapSuperlabelToBranch ) ) { treeNode . mapSuperlabelToBranch [ superlabel ] = { superlabelClassifier : this . newMultilabelClassifier ( ) , mapSuperlabelToBranch : { } } } /*			train the next level classifier for a give superlabel classifier superlabel (from loop)
			with the dataset from new structure mapSuperlabelToRestDataset (see above)
*/ this . trainBatchRecursive ( mapSuperlabelToRestDataset [ superlabel ] , treeNode . mapSuperlabelToBranch [ superlabel ] ) ; } }
Recursive internal subroutine of trainBatch.
Recursive internal subroutine of trainBatch .