基于GPU的K-Means聚类算法
1?聚類分析及k-means算法
1.1?聚類分析技術(shù)
對于給定的數(shù)據(jù)集,按照一定的度量,把其中相似度大的歸為一類,這樣的過程稱為聚類(Clustering)。聚類分析的結(jié)果是一個個的數(shù)據(jù)或?qū)ο蟮募?#xff0c;稱之為簇(Cluster):同一個簇中的對象相似,而與其他簇中的對象則不相似。現(xiàn)在主流的聚類分析技術(shù)一般可以分為以下幾類:
??? (1)基于劃分的方法。對于給定的n個對象,提供數(shù)值k(k≤N),將對象劃分為k份,每一份滿足“簇”的定義。典型的基于劃分的算法有K-Means算法和K-Medoids算法。劃分方法需要在運算之前就確定K的值。
??? (2)基于層次的方法。層次方法創(chuàng)建給定數(shù)據(jù)對象集的層次分解。層次方法可分為:凝聚法,開始時每個對象為一類,合并相似項,直至所有對象被合并為一個類;分裂法,開始時將所有對象都歸類為一個類,逐次將每個類分裂為更小的類,直至所有對象的類滿足“簇”的概念,或滿足其他既定的收斂條件。典型的基于層次的算法有:BIRCH算法、ROCK(RObust Clusteringusing linKs)算法和Chameleon算法。
??? (3)基于密度的方法。基于距離的聚類算法更容易發(fā)現(xiàn)球形簇,但對于發(fā)現(xiàn)任意形狀的簇,則力不從心。基于密度的方法能解決這個問題:對于數(shù)據(jù)集中的每一個點,在給定的半徑鄰域內(nèi),假設(shè)包含M個點,如果M滿足既定的條件,則算法繼續(xù)。常用的基于密度的方法有:DBSCAN(Density-Based Spatial Clustering of Applications with Noise)、DENCLUE(DENsity-based CLUstEring)和OPTICS(Ordering Points to Identify the Clustering Structure)。
??? (4)基于網(wǎng)格的方法[1]。該方法將對象空間劃分為一定數(shù)量的單元,組成網(wǎng)格,并在此基礎(chǔ)上進行聚類。典型的例子有:STING(Statistical Information Grid)、WaveCluster。
1.2? ? K-Means算法
在眾多基于劃分方法的聚類算法中,K-Means算法是最著名和最常用的算法之一。K-Means算法以k為輸入?yún)?shù),將給定的n個對象,劃分為k個簇,使得簇內(nèi)的對象相似度高,而不同簇內(nèi)的對象的相似度低。
K-Means 算法的主要流程如下:
(1)在給定的n個對象中,隨機選取k個對象,作為每一個簇的初始均值(中心);
(2)對于其余的n-k個對象,分別計算與k個中心的距離,將對象指派到最接近的簇;
(3)更新每個簇的新均值,得出k個新的中心;
(4)根據(jù)k個新的中心,重復(fù)(2)(3)兩個步驟,直至準則函數(shù)收斂。
雖然K-Means算法實現(xiàn)起來比較簡單,但K-Means算法也存在以下問題:
(1)需要對全部N個數(shù)據(jù)進行多次遍歷,假設(shè)為 M 次;每次遍歷中,對每個數(shù)據(jù)都需要進行 k 次比較運算,則計算復(fù)雜度為O(N*M*k),同時還需要反復(fù)讀取原數(shù)據(jù),并將比較結(jié)果多次寫到存放分類信息的結(jié)果集中。雖然通常情況下,M<<N,且k<<N,但算法的計算復(fù)雜度依然偏高,執(zhí)行效率較低,并且對系統(tǒng)I/O的壓力也很大;
(2)K的大小需要在算法前確定,并且一般需要用戶指定。這就需要依靠用戶的經(jīng)驗,在運算前就明確,或大概明確現(xiàn)有的數(shù)據(jù)有多少個分類;
(3)對于異常點、離群點較敏感,一個異常點就可能影響整個算法的結(jié)果;
(4)初始簇中心的選取可能會對整個聚類結(jié)果產(chǎn)生很大的影響,甚至能產(chǎn)生截然不同的聚類結(jié)果。
因此,不少學(xué)者針對以上問題從不同方面提出了一些優(yōu)化的方案[2]。例如,文獻3中提出了一種使用K-D Tree來加速算法的執(zhí)行時間的方案[3]。另一種方案是將K-Means算法中的計算部分高度并行化,文獻4中提出利用OpenMP來優(yōu)化K-Means算法[4]。但這種方法不可避免地會產(chǎn)生大量的多線程通信代價。
目前,大多數(shù)桌面計算機都配置了可編程的圖形處理器(GPU,Graphic Processing Unit)。GPU是一種單指令流多數(shù)據(jù)流(SIMD)計算模式的處理器,在處理單元的數(shù)量上要遠遠超過CPU ,擁有數(shù)十個甚至上百個處理核心。盡管GPU的運行頻率低于CPU,但更多的執(zhí)行單元數(shù)量能夠使GPU在浮點運算能力上獲得大幅優(yōu)勢,同時期主流的GPU性能可以達到CPU性能的10倍左右。近年來,GPU性能的飛速發(fā)展,加上基于GPU的可編程性越來越簡單,使得基于GPU并行計算來優(yōu)化K-Means算法成為可行。
本文提出了一種基于GPU并行計算的K-Means算法的優(yōu)化方案,將傳統(tǒng)K-Means算法中計算密集部分采用并行化的方法在GPU上計算。下文將詳細介紹GPU并行計算的相關(guān)原理及基于GPU并行計算的K-Means算法。
2? ?? GPU通用計算編程模型
??? 圖形處理器技術(shù)的迅速發(fā)展帶來的并不只是速度的提高,還產(chǎn)生了很多全新的圖形硬件技術(shù),使GPU具有流處理、高密集并行運算、可編程流水線等特性,從而極大的拓展了GPU的處理能力和應(yīng)用范圍。正是由于GPU具有高效的并行性和靈活的可編程性等特點,越來越多的研究人員和商業(yè)組織開始利用GPU完成一些非圖形繪制方面的計算,并開創(chuàng)了一個新的研究領(lǐng)域:基于GPU的通用計算(GPGPU,General-Purpose computation on GPU),其主要研究內(nèi)容是如何利用GPU在圖形處理之外的其他領(lǐng)域進行更為廣泛的科學(xué)計算。
GPU通用計算通常采用CPU+GPU異構(gòu)模式[5],由CPU負責執(zhí)行復(fù)雜邏輯處理和事務(wù)處理等不適合數(shù)據(jù)并行的計算,由GPU負責計算密集型的大規(guī)模數(shù)據(jù)并行計算。這種利用GPU強大處理能力和高帶寬彌補CPU性能不足的計算方式在發(fā)掘計算機潛在性能,在成本和性價比方面有顯著的優(yōu)勢。在2007年NVIDIA推出CUDA(Compute Unified Device Architecture,統(tǒng)一計算設(shè)備架構(gòu))之前,GPU通用計算受硬件可編程性和開發(fā)方式的制約,開發(fā)難度較大。2007年以后,CUDA不斷發(fā)展的同時,其他的GPU通用計算標準也被相繼提出,如由Apple提出Khronos Group最終發(fā)布的OpenCL,AMD推出的Stream SDK,Microsoft則在其最新的Windows7系統(tǒng)中集成了Direct Compute以支持利用GPU進行通用計算,程序員利用這些語言可以比較輕松地把一些應(yīng)用程序移植到GPU上。
??????? CUDA編程模型[6]將CPU作為主機(Host),GPU作為設(shè)備(Device)。在一個系統(tǒng)中可以存在一個主機和若干個設(shè)備。CPU、GPU各自擁有相互獨立的存儲地址空間:主機端內(nèi)存和設(shè)備端顯存。CUDA對內(nèi)存的操作與一般的C程序基本相同,但是增加了一種新的pinned memory;操作顯存則需要調(diào)用CUDA API存儲器管理函數(shù)。一旦確定了程序中的并行部分,就可以考慮把這部分計算工作交給GPU。運行在GPU上的CUDA并行計算函數(shù)稱為kernel(內(nèi)核函數(shù))。一個完整的CUDA程序是由一系列的設(shè)備端kernel函數(shù)并行步驟和主機端的串行處理步驟共同組成的。這些處理步驟會按照程序中相應(yīng)語句的順序依次執(zhí)行,滿足順序一致性。
3? ?? 基于GPU的K-Means算法
??????? 從上文對K-Means算法主要流程的介紹中可以看到,K-Means算法的主要計算任務(wù)集中在第(2)、(3)這兩個步驟,即計算每個對象與K個簇的距離,并將每個對象分配到一個簇中以及更新每個簇的新中心。因此,基于GPU的K-Means算法主要從這兩方面來考慮如何進行并行優(yōu)化。
3.1? ? 數(shù)據(jù)對象分配
基于GPU的K-Means算法在進行數(shù)據(jù)對象分配這一步驟的時候有兩種策略。第一種策略是面向每個簇的中心,通過計算出該簇的中心與每個數(shù)據(jù)對象的距離,然后將每個數(shù)據(jù)對象歸并到距離簇中心最近的那個簇中。這種策略適應(yīng)于GPU的處理核心數(shù)量比較少的情況,此時,GPU中的每個處理核心可以對應(yīng)一個簇的中心,并且能夠連續(xù)的處理所有的數(shù)據(jù)對象。另一種策略是面向每個數(shù)據(jù)對象,每個數(shù)據(jù)對象計算與所有簇中心的距離,然后數(shù)據(jù)對象將會被分配到距離簇中心最近的那個簇當中。該策略適應(yīng)于GPU的處理核心比較大的情況,目前主流的GPU一般都有超過100個處理核心,因此第二種處理策略比較合適。圖1展示了上述兩種策略的不同思想。
?
圖1 數(shù)據(jù)分配過程不同策略對比圖
3.2? ? 更新K個簇的中心
新的簇中心是通過計算原有簇中所有數(shù)據(jù)對象的數(shù)學(xué)平均值得到的。K-Means算法中K個簇中心的位置也可以通過GPU來計算,CUDA中的每個線程負責一個簇中心,如圖2所示。
圖2 更新K個簇的中心
當數(shù)據(jù)對象分配結(jié)束之后,可以得到每個數(shù)據(jù)對象所屬的簇的下標。要重新計算每個簇的中心位置,一個直觀的想法就是讀取所有的數(shù)據(jù)對象,然后判斷哪些屬于一同個簇。但是,在GPU上如果大量線程都需要同時訪問共享內(nèi)存的話,勢必會因為等待訪問造成大量的延時,因此這里先將數(shù)據(jù)對象分配的結(jié)果從設(shè)備(GPU)傳送到主機(CPU),然后由主機來重新安排,并計算出每個簇包含數(shù)據(jù)對象的數(shù)量。之后,將處理過的數(shù)據(jù)再傳送給設(shè)備的共享內(nèi)存。通過這種途徑,CUDA中每個線程只需連續(xù)地讀取屬于該簇的數(shù)據(jù)對象的數(shù)據(jù)來計算平均值,從而不會發(fā)生多個線程對共享內(nèi)存競爭的情況。
3.3? ? 整體思想
基于GPU的K-Means算法的主要思想是將傳統(tǒng)的K-Means算法中的數(shù)據(jù)獨立,計算密集的部分從主機轉(zhuǎn)移到設(shè)備上處理,從而提高性能。更具體的說,數(shù)據(jù)對象的分配過程和K個簇中心的更新過程雖然要執(zhí)行很多次,但每次計算以及每次計算的數(shù)據(jù)之間都是相互獨立的,并不存在前后依賴的關(guān)系,因此可以將其分離成兩個單獨的內(nèi)核函數(shù),交給GPU的大量的處理核心來并行計算。
盡管GPU的SIMD的計算模式擅長并行計算,但是基于GPU的K-Means算法有三個重要的原則需要說明。第一,GPU設(shè)備的分支轉(zhuǎn)移控制和數(shù)據(jù)緩存機制都非常弱,因為大量的計算處理單元占用了GPU內(nèi)部的大部分空間。第二,GPU與GPU全局內(nèi)存之間的數(shù)據(jù)傳輸速率和CPU與CPU高速緩存之間的數(shù)據(jù)傳輸速率相比要慢很多,因此適當?shù)木€程塊和線程束大小才能體現(xiàn)出GPU的強大計算能力。第三,與傳統(tǒng)的K-Means算法相比,基于GPU的K-Means算法增加了在GPU全局內(nèi)存與CPU內(nèi)存之間傳輸數(shù)據(jù)的時間。因此要達到優(yōu)化算法性能的目的,必須合理地分配主機與設(shè)備的職責,合理地設(shè)計與實現(xiàn)數(shù)據(jù)存儲和并行計算的模式。
基于GPU的K-Means算法的主要流程圖如圖3所示。
圖3 基于GPU的K-Means算法流程圖
如圖3所示,在任務(wù)職責分配方面,主機部分主要負責隨機產(chǎn)生初始的K個簇的中心,對數(shù)據(jù)對象分配的結(jié)果進行預(yù)處理以及判斷聚類過程是否已經(jīng)收斂;而設(shè)備部分則主要負責數(shù)據(jù)獨立的密集型計算過程。在數(shù)據(jù)存儲方面,所有的數(shù)據(jù)對象以及簇中心的數(shù)據(jù)都需要在設(shè)備上以數(shù)組的形式存儲。在GPU設(shè)備上,核函數(shù)中所有線程所共享的內(nèi)存有三類:常量內(nèi)存,紋理內(nèi)存以及全局內(nèi)存。常量內(nèi)存和紋理內(nèi)存都是只讀的而且其有用的大小也很有限,所以對于算法中的數(shù)據(jù)是不合適的。另外,在GPU和顯存之間的傳輸帶寬要比在主機內(nèi)存和顯存之間傳輸數(shù)據(jù)的帶寬高得多,考慮到這一點,在基于GPU的K-Means算法中,在主機和設(shè)備之間傳輸?shù)拇刂行牡南聵藬?shù)據(jù)大小要盡量的小。這種基于CPU+GPU異構(gòu)模式雖然會產(chǎn)生額外的數(shù)據(jù)I/O的時間消耗,但是GPU的計算模型中,大量線程的并行能夠減少讀取內(nèi)存的延遲。
4? ?? 總結(jié)
??????? 本文闡述了傳統(tǒng)的K-Means聚類算法的具體過程以及其中的復(fù)雜性和效率問題,并提出將其中計算密集的處理部分分離到GPU上進行處理的優(yōu)化方案。隨著CUDA、OpenCL、Stream SDK等其他GPU通用計算標準的提出和發(fā)展,GPU的強大處理能力和高帶寬的特點將會越來越突顯。本文的主要研究目的在于提出將信息檢索和數(shù)據(jù)挖掘方面的部分經(jīng)典算法與GPU并行計算相結(jié)合的思想,使其通過并行處理在性能上達到高效的優(yōu)化。
總結(jié)
以上是生活随笔為你收集整理的基于GPU的K-Means聚类算法的全部內(nèi)容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: 龙卡全球支付信用卡好申请吗?这些条件必不
- 下一篇: 员工价值——如何体现自己价值,如何被自己