天天看點

資料挖掘apriori算法Java代碼實作

資料挖掘apriori算法Java代碼實作

package apriori;  

import java.util.*;  

import java.io.*;  

public class aprioti {  

    public static int k_item=3;//産生的頻繁項集數,但其實在我這裡不是真正的項集數,隻是疊代的次數,在[beer,ham][cola,diaper]這種情況下會産生頻繁4項集!!  

                               //隻要修改一下就可以,但是我覺得這樣也好是以就沒有修改  

    public static double min_support_count =2;//最小支援度計數值  

    public static string path="f:\\firstgit\\apriori\\";  

    public static list<itemset>allitemset = new arraylist<itemset>();  

    public static itemset originalitem = new itemset();  

    public static void main(string [] args)  

    {  

        aprioriprocess();  

    }  

    public static void aprioriprocess()  

        readitemfromtext(path,originalitem);//讀取硬碟上的資料集  

        itemset firstitemset =new itemset();  

        gen_first_item_set(firstitemset);//首先生成頻繁1項集  

        int k =k_item;  

        itemset forworditemset =firstitemset;  

        delete_blew_support_count(forworditemset);//去除低于最小支援度計數的項集  

        allitemset.add(firstitemset);//将所有的頻繁項集儲存起來  

        while(k--!=0)  

        {  

            itemset backworditemset =new itemset();  

            apriori_gen(forworditemset,backworditemset);//根據頻繁k-1項集生成頻繁k項集  

            delete_blew_support_count(backworditemset);//去除小于支援度計數的項集  

            allitemset.add(backworditemset);  

            forworditemset=backworditemset;//将指針指向頻繁k-1項集  

        }  

        printresult();//輸出結果  

    public static void printresult()  

        for(int i=0;i<allitemset.size();i++)  

            itemset itemset = allitemset.get(i);  

            for(treeset<string> everyitem : itemset.itemset)  

            {  

                system.out.println(everyitem.tostring());  

            }  

    /* 

     * 不可以一邊周遊一邊删除集合中的資料,這樣會讓你的集合周遊不完整或者越界! 

     */  

    public static void delete_blew_support_count(itemset itemset)  

        /* 

         * 在這裡可以用疊代器iterator也可以用size()的形式來, 

         * 其中用iterator會周遊的時候不可以删除元素 

         * 用size可以删除元素,但是最後的n(n是中途被删除的個數)個元素就沒有周遊到!!!! 

         */  

        arraylist<integer> deletesetnum= new arraylist<integer>();  

        for(int i=0;i<itemset.itemset.size();i++)  

            double suppoutcount=0;  

            treeset<string> item = itemset.itemset.get(i);  

            boolean ispinfan=false;  

            for(treeset<string> oriitem : originalitem.itemset)  

                if(contain(oriitem,item))  

                    suppoutcount++;  

                if(suppoutcount>=min_support_count)  

                {  

                    ispinfan=true;  

                    break;  

                }  

            if(!ispinfan)  

                deletesetnum.add(i);  

        for(int j=deletesetnum.size()-1;j>=0;j--)  

            //system.out.println(deletesetnum.get(j));  

            itemset.itemset.remove((int)deletesetnum.get(j));  

         * 下面這種做法由于remove 

         * 的時候會改變集合的大小,是以不可以從頭開始remove隻可以從後面remove 

         * 這樣就保證不會越界     

//      for(int  i :deletesetnum)  

//      {  

//          system.out.println(i);  

//          itemset.itemset.remove(i);  

//      }  

    //産生1項集  

    public static void gen_first_item_set(itemset firstitemset)  

        treeset<string> itemset = new treeset<string>();  

        for(treeset<string> per_ori_item : originalitem.itemset)  

            for(string item : per_ori_item)  

                itemset.add(item);  

        for(string word : itemset)  

            treeset<string> everyitemset = new treeset<string>();  

            everyitemset.add(word);  

            firstitemset.itemset.add(everyitemset);  

     * 根據k-1項頻繁産生頻繁k項項集 

    public static  void apriori_gen(itemset one_item,itemset second_item)  

        for(int i=0;i<one_item.itemset.size();i++)  

            for(int j=i+1;j<one_item.itemset.size();j++)  

                treeset<string> newitem=new treeset<string>();  

                for(string peritem: one_item.itemset.get(i))  

                    newitem.add(peritem);  

                for(string peritem: one_item.itemset.get(j))  

                //如果沒有非頻繁k-1項集,加入k項集  

                if(!has_infrequent_subset(newitem,one_item))  

                    if(!find_in_already_set(newitem,second_item))//并且項集沒有在之前出現  

                       second_item.itemset.add(newitem);  

    public static boolean find_in_already_set(treeset<string> newitem,itemset second_item)  

        for(int i=0;i<second_item.itemset.size();i++)  

            if(newitem.equals(second_item.itemset.get(i)))//記住,treeset也可以用equals,這個函數真是好用,不過有時候效率低  

                    return true;  

        return false;  

    public static  boolean has_infrequent_subset(treeset<string> newitem,itemset one_item1)//這裡寫錯了!  

        for(treeset<string> k_1_item : one_item1.itemset)  

            if(!contain(newitem,k_1_item))  

                return false;  

        return true;  

    public static boolean contain(treeset<string> big,treeset<string>small)  

        for(string smallword : small)  

            if(!big.contains(smallword))  

    public static  void readitemfromtext(string path,itemset originalitem)  

        file file =new file(path);  

        if(file.isdirectory())  

            string [] filelist = file.list();  

            for(int i =0;i<filelist.length;i++)  

                try {  

                    bufferedreader br = new bufferedreader(new filereader(new file(path+filelist[i])));  

                    string line =null;  

                    while((line = br.readline())!=null)  

                    {  

                        string [] lineword = line.split("[^\\s]+");  

                        treeset<string> itemset = new treeset<string>();  

                        for(string word : lineword)  

                        {  

                            itemset.add(word);  

                        }  

                        originalitem.itemset.add(itemset);  

                    }  

                } catch (exception e) {  

                    e.printstacktrace();  

}  

上面代碼中用到的itemset,由于不想老是寫那麼長的代碼,是以就将其封裝為一個類

資料挖掘apriori算法Java代碼實作

public class itemset {  

    public arraylist<treeset<string>> itemset = new arraylist<treeset<string>>();  

輸入的資料集如下:

cola egg ham

cola diaper beer

cola diaper beer ham

diaper beer

輸出結果如下:

[beer]

[cola]

[diaper]

[ham]

[beer, cola]

[beer, diaper]

[cola, diaper]

[cola, ham]

[beer, cola, diaper]

其實還有兩個地方沒有改正,不過對于入門的同學應該可以看看,求指正批評!!