Example #1
0
        void RecurseMining(List <DFSLevelItem> levelItems, int support, int minLength, int maxLength, MineResults mineResult)
        {
            // Simple pattern cut-off: if the pattern is not long enough, or too long
            for (int i = levelItems.Count - 1; i >= 0; i--)
            {
                if (levelItems[i].Head.Count >= maxLength)
                {
                    levelItems.RemoveAt(i);
                    continue;
                }

                if (levelItems[i].Head.Count + levelItems[i].Tail.Count < minLength)
                {
                    levelItems.RemoveAt(i);
                    continue;
                }
            }

            if (levelItems.Count == 0)
            {
                return;
            }

            Dictionary <int, int> lookAheadPrune = new Dictionary <int, int>();

            for (int levelItemsLoop = 0; levelItemsLoop < levelItems.Count; levelItemsLoop++)
            {
                IntList      tail = levelItems[levelItemsLoop].Tail;
                ItemsetBasic head = levelItems[levelItemsLoop].Head;

                List <FastSparseBitArray> bitArrays = new List <FastSparseBitArray>(tail.Count);
                for (int loopTail = 0; loopTail < tail.Count; loopTail++)
                {
                    int i = tail[loopTail];

                    FastSparseBitArray bitArray = null;

                    if (_dualComp != null)
                    {
                        ISimpleItemset dualItemset = _dualComp.GetItemset(head.GetLastItem(), i);
                        if (dualItemset == null)
                        {
                            tail.RemoveAt(loopTail);
                            loopTail--;
                            continue;
                        }

                        bitArray = dualItemset.GetTransactions();
                    }
                    else
                    {
                        bitArray = FastSparseBitArrayPool.Instance.Allocate();
                        _ds.BuildBitVector(head.GetLastItem(), i, bitArray);
                    }

                    if (head.Count > 1)
                    {
                        bitArray = bitArray.And(head.GetTransactions());
                    }

                    bitArray.frequency = bitArray.CountElements();
                    if (bitArray.frequency >= support)
                    {
                        bitArrays.Add(bitArray);

                        // Prune look-ahead
                        if (bitArray.frequency == head.support)
                        {
                            int lookAheadSupport;
                            if (lookAheadPrune.TryGetValue(i, out lookAheadSupport) == false)
                            {
                                lookAheadPrune.Add(i, bitArray.frequency);
                            }
                            else
                            {
                                lookAheadPrune[i] = Math.Max(lookAheadSupport, bitArray.frequency);
                            }
                        }
                    }
                    else
                    {
                        // Don't release bit vectors from O2 matrix, or there is no
                        // O2 matrix
                        if ((head.Count > 1) || (_dualComp == null))
                        {
                            FastSparseBitArrayPool.Instance.Release(bitArray);
                        }

                        tail.RemoveAt(loopTail);
                        loopTail--;
                    }
                }

                levelItems[levelItemsLoop].TailBitArrays = bitArrays;
            }

            for (int levelItemsLoop = 0; levelItemsLoop < levelItems.Count; levelItemsLoop++)
            {
                ItemsetBasic head = levelItems[levelItemsLoop].Head;
                List <FastSparseBitArray> bitArrays = levelItems[levelItemsLoop].TailBitArrays;

                int lookAheadSupport;
                if (lookAheadPrune.TryGetValue(head.GetLastItem(), out lookAheadSupport) == true)
                {
                    if (lookAheadSupport == head.support)
                    {
                        if (head.Count > 2)
                        {
                            for (int j = 0; j < bitArrays.Count; j++)
                            {
                                FastSparseBitArrayPool.Instance.Release(bitArrays[j]);
                            }
                        }
                        continue;
                    }
                }

                IntList tail = levelItems[levelItemsLoop].Tail;

                List <DFSLevelItem> newLevelItems = new List <DFSLevelItem>();
                for (int loopTail = 0; loopTail < tail.Count; loopTail++)
                {
                    int i = tail[loopTail];

                    IntList newTail = (IntList)tail.Clone();
                    newTail.RemoveAt(loopTail);

                    ItemsetBasic newHead = new ItemsetBasic(head);
                    newHead.AddItem(i);
                    FastSparseBitArray bitArray = bitArrays[loopTail];
                    newHead.SetTransactions(bitArray);
                    newHead.support = bitArray.frequency;

                    if (newHead.Count >= minLength)
                    {
                        mineResult.Add(newHead);
                    }

                    newLevelItems.Add(new DFSLevelItem(newHead, newTail));
                }

                RecurseMining(newLevelItems, support, minLength, maxLength, mineResult);

                // Release IntList
                for (int j = 0; j < newLevelItems.Count; j++)
                {
                    IntListPool.Instance.Release(newLevelItems[j].Tail);
                }

                // Release FastSparseBitArray
                if (head.Count > 2)
                {
                    for (int j = 0; j < bitArrays.Count; j++)
                    {
                        FastSparseBitArrayPool.Instance.Release(bitArrays[j]);
                    }
                }
            }
        }
Example #2
0
        void RecurseMining(ItemsetBasic head, IntList tail, int support, int minLength, int maxLength, MineResults mineResult)
        {
            if (head.Count >= maxLength)
            {
                return;
            }

            if (head.Count + tail.Count < minLength)
            {
                return;
            }

            List <FastSparseBitArray> bitArrays = new List <FastSparseBitArray>(tail.Count);

            for (int loopTail = 0; loopTail < tail.Count; loopTail++)
            {
                int i = tail[loopTail];

                if (head.Count == 0)
                {
                    IntList newTail = (IntList)tail.Clone(); // new IntList(tail);
                    newTail.RemoveAt(loopTail);
                    ItemsetBasic newHead = new ItemsetBasic(tail.Count);
                    newHead.AddItem(i);
                    RecurseMining(newHead, newTail, support, minLength, maxLength, mineResult);

                    IntListPool.Instance.Release(newTail);
                }
                else
                {
                    FastSparseBitArray bitArray = null;

                    if (_dualComp != null)
                    {
                        ISimpleItemset dualItemset = _dualComp.GetItemset(head.GetLastItem(), i);
                        if (dualItemset == null)
                        {
                            tail.RemoveAt(loopTail);
                            loopTail--;
                            continue;
                        }

                        bitArray = dualItemset.GetTransactions();
                    }
                    else
                    {
                        bitArray = FastSparseBitArrayPool.Instance.Allocate();
                        _ds.BuildBitVector(head.GetLastItem(), i, bitArray);
                    }

                    if (head.Count > 1)
                    {
                        bitArray = bitArray.And(head.GetTransactions());
                    }

                    bitArray.frequency = bitArray.CountElements();
                    if (bitArray.frequency >= support)
                    {
                        bitArrays.Add(bitArray);
                    }
                    else
                    {
                        // Don't release bit vectors from O2 matrix, or there is no
                        // O2 matrix
                        if ((head.Count > 1) || (_dualComp == null))
                        {
                            FastSparseBitArrayPool.Instance.Release(bitArray);
                        }

                        tail.RemoveAt(loopTail);
                        loopTail--;
                    }
                }
            }

            if (head.Count > 0)
            {
                for (int loopTail = 0; loopTail < tail.Count; loopTail++)
                {
                    int i = tail[loopTail];

                    IntList newTail = (IntList)tail.Clone(); // new IntList(tail);
                    newTail.RemoveAt(loopTail);

                    // Create 'head' restore point
                    FastSparseBitArray restoreBitArray = head.GetTransactions();
                    int restoreSupport = head.support;

                    head.AddItem(i);
                    FastSparseBitArray bitArray = bitArrays[loopTail];
                    head.SetTransactions(bitArray);
                    head.support = bitArray.frequency;
                    RecurseMining(head, newTail, support, minLength, maxLength, mineResult);

                    IntListPool.Instance.Release(newTail);

                    if (head.Count >= minLength)
                    {
                        mineResult.Add(head);
                    }

                    head.SetTransactions(null);
                    if (head.Count > 2)
                    {
                        FastSparseBitArrayPool.Instance.Release(bitArray);
                    }

                    // Restore 'head'
                    head.RemoveLastItem();
                    head.SetTransactions(restoreBitArray);
                    head.support = restoreSupport;
                }
            }
        }