node-fpgrowth
Advanced tools
Comparing version
@@ -17,4 +17,9 @@ /// <reference types="node" /> | ||
private _support; | ||
/** | ||
* The transactions from which you want to mine itemsets. | ||
*/ | ||
private _transactions; | ||
private _supports; | ||
/** | ||
* Output of the algorithm: The mined frequent itemsets. | ||
*/ | ||
private _itemsets; | ||
@@ -28,7 +33,2 @@ /** | ||
*/ | ||
/** | ||
* [constructor description] | ||
* @param {number} private_support [description] | ||
* @return {[type]} [description] | ||
*/ | ||
constructor(_support: number); | ||
@@ -46,5 +46,5 @@ /** | ||
/** | ||
* RECURSIVE CALL - Returns mined itemset from each conditional sub-FPTree of the given free until no FPTree can be created anymore. | ||
* RECURSIVE CALL - Returns mined itemset from each conditional sub-FPTree of the given FPtree. | ||
* | ||
* @param {FPTree<T>} tree The FPTree you want to mine | ||
* @param {FPTree<T>} tree The FPTree you want to mine. | ||
* @param {number} prefixSupport The support of the FPTree's current prefix. | ||
@@ -51,0 +51,0 @@ * @param {T[]} prefix The current prefix associated with the FPTree. |
@@ -24,10 +24,8 @@ "use strict"; | ||
*/ | ||
/** | ||
* [constructor description] | ||
* @param {number} private_support [description] | ||
* @return {[type]} [description] | ||
*/ | ||
function FPGrowth(_support /*, private _confidence: number*/) { | ||
var _this = _super.call(this) || this; | ||
_this._support = _support; /*, private _confidence: number*/ | ||
/** | ||
* Output of the algorithm: The mined frequent itemsets. | ||
*/ | ||
_this._itemsets = []; | ||
@@ -53,7 +51,9 @@ return _this; | ||
// First scan to determine the occurence of each unique item. | ||
this._supports = this._getDistinctItemsCount(this._transactions); | ||
var supports = this._getDistinctItemsCount(this._transactions); | ||
return new Promise(function (resolve, reject) { | ||
var time = process.hrtime(); | ||
// Building the FP-Tree... | ||
var tree = new fptree_1.FPTree(_this._supports, _this._support).fromTransactions(_this._transactions); | ||
var tree = new fptree_1.FPTree(supports, _this._support).fromTransactions(_this._transactions); | ||
// Running the algorithm on the main tree. | ||
// All the frequent itemsets are returned at the end of the execution. | ||
var frequentItemsets = _this._fpGrowth(tree, _this._transactions.length); | ||
@@ -72,5 +72,5 @@ var elapsedTime = process.hrtime(time); | ||
/** | ||
* RECURSIVE CALL - Returns mined itemset from each conditional sub-FPTree of the given free until no FPTree can be created anymore. | ||
* RECURSIVE CALL - Returns mined itemset from each conditional sub-FPTree of the given FPtree. | ||
* | ||
* @param {FPTree<T>} tree The FPTree you want to mine | ||
* @param {FPTree<T>} tree The FPTree you want to mine. | ||
* @param {number} prefixSupport The support of the FPTree's current prefix. | ||
@@ -87,8 +87,17 @@ * @param {T[]} prefix The current prefix associated with the FPTree. | ||
// TODO: if(singlePath) return this._handleSinglePath(singlePath, prefix); | ||
// For each header, ordered ascendingly by their support, determining the prefix paths. | ||
// of each each they represent. | ||
// These prefix paths represent new transactions to mine in a new FPTree. | ||
// If no prefix path can be found, the algorithm stops. | ||
return tree.headers.reduce(function (itemsets, item) { | ||
var support = Math.min(tree.supports[JSON.stringify(item)], prefixSupport); | ||
// Array copy. | ||
var currentPrefix = prefix.slice(0); | ||
currentPrefix.push(item); | ||
// Prefix is a mined itemset. | ||
itemsets.push(_this._getFrequentItemset(currentPrefix, support)); | ||
// Method below generates the prefix paths of the current item, as well as the support of | ||
// each item composing the prefix paths, and returns a new conditional FPTree if one can be created. | ||
var childTree = tree.getConditionalFPTree(item); | ||
// If a conditional tree can be mined... mine it recursively. | ||
if (childTree) | ||
@@ -95,0 +104,0 @@ return itemsets.concat(_this._fpGrowth(childTree, support, currentPrefix)); |
@@ -101,2 +101,3 @@ import { FPNode } from './fpnode'; | ||
* @param {FPNode<T>} node The node of which you want the prefix path. | ||
* @param {number} count The support of the stating node (which is node). | ||
* @param {Function} onPushingNewItem Callback function to keep track of items added to the prefix path. | ||
@@ -110,2 +111,3 @@ * @return {IPrefixPath<T>[]} The result you expect. | ||
* @param {FPNode<T>} node The node to start the prefix. | ||
* @param {number} count The support of the stating node (which is node). | ||
* @param {Function} onPushingNewItem Callback function to keep track of items added to the prefix path. | ||
@@ -112,0 +114,0 @@ * @return {T[]} The result you expect. |
@@ -61,4 +61,6 @@ "use strict"; | ||
}); | ||
// Pushing formatted transaction to the tree. | ||
_this._addTransaction(items); | ||
}); | ||
// Generating headers. | ||
this._headers = this._getHeaderList(); | ||
@@ -89,5 +91,6 @@ this._isInit = true; | ||
*/ | ||
// Adding each prefix path to the tree. | ||
// Pushing each prefix path to the tree. | ||
_this._addTransaction(items); | ||
}); | ||
// Generating headers. | ||
this._headers = this._getHeaderList(); | ||
@@ -206,2 +209,3 @@ this._isInit = true; | ||
* @param {FPNode<T>} node The node of which you want the prefix path. | ||
* @param {number} count The support of the stating node (which is node). | ||
* @param {Function} onPushingNewItem Callback function to keep track of items added to the prefix path. | ||
@@ -223,2 +227,3 @@ * @return {IPrefixPath<T>[]} The result you expect. | ||
* @param {FPNode<T>} node The node to start the prefix. | ||
* @param {number} count The support of the stating node (which is node). | ||
* @param {Function} onPushingNewItem Callback function to keep track of items added to the prefix path. | ||
@@ -225,0 +230,0 @@ * @return {T[]} The result you expect. |
{ | ||
"name": "node-fpgrowth", | ||
"version": "0.1.10", | ||
"version": "0.2.0", | ||
"description": "FPGrowth Algorithm implementation in TypeScript / JavaScript.", | ||
@@ -5,0 +5,0 @@ "main": "dist/fpgrowth.js", |
@@ -16,6 +16,2 @@ # Node-FPGrowth | ||
### Performances | ||
### Example of use | ||
@@ -22,0 +18,0 @@ |
@@ -22,5 +22,10 @@ import { EventEmitter } from 'events'; | ||
export class FPGrowth<T> extends EventEmitter implements IFPGrowthEvents<T> { | ||
/** | ||
* The transactions from which you want to mine itemsets. | ||
*/ | ||
private _transactions: T[][]; | ||
private _supports: ItemsCount; | ||
/** | ||
* Output of the algorithm: The mined frequent itemsets. | ||
*/ | ||
private _itemsets: Itemset<T>[] = []; | ||
@@ -35,8 +40,2 @@ | ||
*/ | ||
/** | ||
* [constructor description] | ||
* @param {number} private_support [description] | ||
* @return {[type]} [description] | ||
*/ | ||
constructor( private _support: number /*, private _confidence: number*/ ) { | ||
@@ -63,3 +62,3 @@ super(); | ||
// First scan to determine the occurence of each unique item. | ||
this._supports = this._getDistinctItemsCount(this._transactions); | ||
let supports: ItemsCount = this._getDistinctItemsCount(this._transactions); | ||
@@ -70,5 +69,8 @@ return new Promise<IFPGrowthResults<T>>( (resolve, reject) => { | ||
// Building the FP-Tree... | ||
let tree: FPTree<T> = new FPTree<T>(this._supports,this._support).fromTransactions(this._transactions); | ||
let tree: FPTree<T> = new FPTree<T>(supports,this._support).fromTransactions(this._transactions); | ||
// Running the algorithm on the main tree. | ||
// All the frequent itemsets are returned at the end of the execution. | ||
let frequentItemsets: Itemset<T>[] = this._fpGrowth(tree,this._transactions.length); | ||
let elapsedTime = process.hrtime(time); | ||
@@ -88,5 +90,5 @@ | ||
/** | ||
* RECURSIVE CALL - Returns mined itemset from each conditional sub-FPTree of the given free until no FPTree can be created anymore. | ||
* RECURSIVE CALL - Returns mined itemset from each conditional sub-FPTree of the given FPtree. | ||
* | ||
* @param {FPTree<T>} tree The FPTree you want to mine | ||
* @param {FPTree<T>} tree The FPTree you want to mine. | ||
* @param {number} prefixSupport The support of the FPTree's current prefix. | ||
@@ -102,11 +104,20 @@ * @param {T[]} prefix The current prefix associated with the FPTree. | ||
// For each header, ordered ascendingly by their support, determining the prefix paths. | ||
// of each each they represent. | ||
// These prefix paths represent new transactions to mine in a new FPTree. | ||
// If no prefix path can be found, the algorithm stops. | ||
return tree.headers.reduce<Itemset<T>[]>( (itemsets: Itemset<T>[], item: T) => { | ||
let support: number = Math.min(tree.supports[JSON.stringify(item)],prefixSupport); | ||
// Array copy. | ||
let currentPrefix: T[] = prefix.slice(0); | ||
currentPrefix.push(item); | ||
// Prefix is a mined itemset. | ||
itemsets.push(this._getFrequentItemset(currentPrefix,support)); | ||
// Method below generates the prefix paths of the current item, as well as the support of | ||
// each item composing the prefix paths, and returns a new conditional FPTree if one can be created. | ||
let childTree: FPTree<T> = tree.getConditionalFPTree(item); | ||
// If a conditional tree can be mined... mine it recursively. | ||
if(childTree) return itemsets.concat(this._fpGrowth(childTree,support,currentPrefix)); | ||
@@ -113,0 +124,0 @@ return itemsets; |
@@ -50,3 +50,3 @@ import { FPNode } from './fpnode'; | ||
*/ | ||
constructor( public readonly supports: ItemsCount, private _support: number,) { | ||
constructor( public readonly supports: ItemsCount, private _support: number ) { | ||
} | ||
@@ -67,3 +67,5 @@ | ||
let items: T[] = transaction | ||
// Pruning. | ||
.filter( (item: T) => this.supports[JSON.stringify(item)] >= this._support) | ||
// Sorting. | ||
.sort( (a: T, b: T) => { | ||
@@ -74,5 +76,7 @@ let res: number = this.supports[JSON.stringify(b)] - this.supports[JSON.stringify(a)]; | ||
}); | ||
// Pushing formatted transaction to the tree. | ||
this._addTransaction(items); | ||
}); | ||
// Generating headers. | ||
this._headers = this._getHeaderList(); | ||
@@ -106,6 +110,7 @@ | ||
// Adding each prefix path to the tree. | ||
// Pushing each prefix path to the tree. | ||
this._addTransaction(items); | ||
}); | ||
// Generating headers. | ||
this._headers = this._getHeaderList(); | ||
@@ -112,0 +117,0 @@ this._isInit = true; |
58983
3.46%1272
2.58%53
-7.02%