這是描述預(yù)測客戶流失的端到端藍(lán)圖的系列文章的第三部分。在前幾期文章中,我們已經(jīng)討論了機(jī)器學(xué)習(xí)系統(tǒng)的一些挑戰(zhàn),這些挑戰(zhàn)直到您投入生產(chǎn)時才會出現(xiàn):在 第一期付款 中,我們介紹了我們的用例,并描述了一個加速的數(shù)據(jù)聯(lián)合管道;在 第二期 中,我們展示了高級分析如何適應(yīng)機(jī)器學(xué)習(xí)生命周期的其余部分。
在第三期文章中,我們將介紹應(yīng)用程序的分析和聯(lián)合組件,并解釋如何充分利用 Apache Spark 和 RAPIDS Apache 加速器 Spark 的一些最佳實(shí)踐。
架構(gòu)( Architecture )評審

圖 1 :我們的藍(lán)圖架構(gòu)的高級概述。
回想一下,我們的 blueprint 應(yīng)用程序(圖 1 )包括一個聯(lián)邦工作負(fù)載和一對分析工作負(fù)載。
聯(lián)合工作負(fù)載 生成了一個關(guān)于每個客戶的非規(guī)范化寬數(shù)據(jù)表,這些數(shù)據(jù)來自于五個與客戶賬戶不同方面相關(guān)的規(guī)范化觀察表的數(shù)據(jù)匯總。
第一次分析工作量 為每個特性生成一個機(jī)器可讀的值分布和域的摘要報告。
第二次分析工作量 生成一系列關(guān)于客戶結(jié)果的說明性業(yè)務(wù)報告 我們的第一期 包含有關(guān)聯(lián)合工作負(fù)載的其他詳細(xì)信息, 我們的第二期 包含有關(guān)分析工作負(fù)載的其他詳細(xì)信息。
我們將這三個工作負(fù)載作為一個具有多個階段的 Spark 應(yīng)用程序來實(shí)現(xiàn):
應(yīng)用程序?qū)?HDFS 中多個表(存儲為拼花文件)的原始數(shù)據(jù)聯(lián)合到一個寬表中。
因?yàn)閷挶肀仍紨?shù)據(jù)小得多,所以應(yīng)用程序然后通過合并到較少的分區(qū)并將數(shù)值轉(zhuǎn)換為適合 ML 模型訓(xùn)練的類型來重新格式化寬輸出。此階段的輸出是 ML 模型訓(xùn)練的源數(shù)據(jù)。
然后,應(yīng)用程序針對合并和轉(zhuǎn)換的寬表運(yùn)行分析工作負(fù)載,首先生成機(jī)器可讀的摘要報告,然后生成匯總和數(shù)據(jù)立方體報告的集合。
性能注意事項(xiàng)
并行執(zhí)行
50 多年來,提高并行執(zhí)行的適用性一直是計算機(jī)系統(tǒng)高性能最重要的考慮因素之一 ( 我們有點(diǎn)武斷地選擇在 1967 年確定 托馬蘇洛算法 的開發(fā),它為無處不在的超標(biāo)量處理奠定了基礎(chǔ),因?yàn)樵谶@一點(diǎn)上,對并行性的關(guān)注變得實(shí)用而不僅僅是理論上的。)在分析員、數(shù)據(jù)科學(xué)家、數(shù)據(jù)和 ML 工程師以及應(yīng)用程序開發(fā)人員的日常工作中,對并行性的關(guān)注通常表現(xiàn)為以下幾種方式之一;我們現(xiàn)在來看看。
向外擴(kuò)展時,在集群上執(zhí)行工作
如果您使用的是橫向擴(kuò)展框架,請盡可能在集群上而不是在單個節(jié)點(diǎn)上執(zhí)行工作。在 Spark 的情況下,這意味著在執(zhí)行器上執(zhí)行 Spark 作業(yè)中的代碼,而不是在驅(qū)動程序上執(zhí)行串行代碼。 一般來說,在驅(qū)動程序中使用 Spark 的 API 而不是宿主語言代碼將使您獲得大部分的成功,但是您需要確保所使用的 Spark API 實(shí)際上是在執(zhí)行器上并行執(zhí)行的。
操作集合,而不是元素;在列上,而不是行上
開發(fā)并行性和提高性能的一般最佳實(shí)踐是使用一次對集合執(zhí)行操作的專用庫,而不是一次對元素執(zhí)行操作。在 Spark 的情況下,這意味著使用數(shù)據(jù)幀和列操作,而不是迭代 rdd 分區(qū)中的記錄;在 Python 數(shù)據(jù)生態(tài)系統(tǒng)和 RAPIDS 。 ai 中,這意味著使用在單個庫調(diào)用中對整個數(shù)組和矩陣進(jìn)行操作的 矢量化操作 ,而不是在 Python 中使用顯式循環(huán)。最關(guān)鍵的是,這兩種方法也適用于 GPU 加速。
分?jǐn)?I / O 和數(shù)據(jù)加載的成本
I / O 和數(shù)據(jù)加載成本很高,因此在盡可能多的并行操作中分?jǐn)偹鼈兊某杀臼怯幸饬x的。 我們可以通過直接降低數(shù)據(jù)傳輸成本和在數(shù)據(jù)加載后盡可能多地處理數(shù)據(jù)來提高性能。在 Spark 中,這意味著使用列格式,在從穩(wěn)定存儲導(dǎo)入時只過濾一次關(guān)系,并在 I / O 或無序操作之間執(zhí)行盡可能多的工作。
通過抽象提高性能
一般來說,提高分析師和開發(fā)人員在應(yīng)用程序、查詢和報表中使用的抽象級別,可以讓運(yùn)行時和框架找到開發(fā)人員沒有(或無法)預(yù)料到的并行執(zhí)行機(jī)會。
使用 Spark 的數(shù)據(jù)幀
例如,在 Spark 中使用數(shù)據(jù)幀并主要針對高級數(shù)據(jù)幀 API 進(jìn)行開發(fā)有許多好處,包括執(zhí)行速度更快、查詢的語義保持優(yōu)化、對存儲和 I / O 的需求減少,以及相對于使用基于 RDD 的代碼顯著改善了內(nèi)存占用。但除了這些好處之外,還有一個更深層次的優(yōu)勢:因?yàn)閿?shù)據(jù)幀接口是高級的,而且 Spark 允許插件改變查詢優(yōu)化器的行為,所以 RAPIDS Apache 加速器 Spark 有可能用在 GPU 上運(yùn)行的等效但實(shí)際上更快的操作替換某些數(shù)據(jù)幀操作。
透明加速 Spark 查詢
用插件替換 Spark 的查詢規(guī)劃器的一些功能是抽象能力的一個特別引人注目的例子:在能夠在 GPU 上運(yùn)行 Spark 查詢之前幾年編寫的應(yīng)用程序仍然可以通過使用 Spark 3 。 1 和 RAPIDS 加速器來利用 GPU 加速。
保持清晰的抽象
盡管使用新的運(yùn)行時加速未修改的應(yīng)用程序的潛力是針對高級抽象進(jìn)行開發(fā)的一個主要優(yōu)勢,但實(shí)際上,對于開發(fā)團(tuán)隊(duì)來說,維護(hù)清晰的抽象很少比按時交付工作項(xiàng)目更重要。由于多種原因,抽象背后的細(xì)節(jié)常常會泄漏到產(chǎn)品代碼中;雖然這可能會引入技術(shù)債務(wù)并產(chǎn)生無數(shù)工程后果,但它也會限制高級運(yùn)行時的適用性,以優(yōu)化干凈地使用抽象的程序。
考慮適合 GPU 加速的操作
為了從 Spark 中獲得最大的收益,在圍繞 Spark 的數(shù)據(jù)幀抽象的應(yīng)用程序中償還技術(shù)債務(wù)(例如,通過將部分查詢實(shí)現(xiàn)為 RDD 操作)是有意義的。 不過,為了充分利用先進(jìn)的基礎(chǔ)設(shè)施,在不破壞抽象的情況下考慮執(zhí)行環(huán)境的細(xì)節(jié)通常是有意義的。 為了從 NVIDIA GPU 和 RAPIDS Apache 加速器 Spark 獲得盡可能好的性能,首先要確保您的代碼不會圍繞抽象工作,然后考慮或多或少適合 GPU 執(zhí)行的類型和操作,這樣您就可以確保盡可能多的應(yīng)用程序在 GPU 上運(yùn)行。下面我們將看到一些這樣的例子。
類型和操作
并不是每一個操作都能被 GPU 加速。當(dāng)有疑問時,運(yùn)行作業(yè)時將 spark.rapids.sql.explain 設(shè)置為 NOT_ON_GPU 并檢查記錄到標(biāo)準(zhǔn)輸出的解釋總是有意義的。在本節(jié)中,我們將指出一些常見的陷阱,包括需要配置支持的十進(jìn)制算法和操作。
小心十進(jìn)制算術(shù)
十進(jìn)制計算機(jī)算法支持高達(dá)給定精度限制的精確運(yùn)算,可以避免和檢測溢出,并像人類在執(zhí)行鉛筆和紙張計算時那樣舍入數(shù)字。盡管十進(jìn)制算法是許多數(shù)據(jù)處理系統(tǒng)(尤其是金融數(shù)據(jù))的重要組成部分,但它對分析系統(tǒng)提出了特殊的挑戰(zhàn)。為了避免溢出,十進(jìn)制運(yùn)算的結(jié)果必須擴(kuò)大到包括所有可能的結(jié)果;在結(jié)果比系統(tǒng)特定限制更寬的情況下,系統(tǒng)必須檢測溢出。在 cpu 上使用 Spark 的情況下,這涉及將操作委托給 Java 標(biāo)準(zhǔn)庫中的 BigDecimal 類 ,并且精度限制為 38 位十進(jìn)制數(shù)字或 128 位。 Apache 的 RAPIDS 加速器 Spark 目前可以加速計算多達(dá) 18 位或 64 位的十進(jìn)制值。
我們已經(jīng)評估了客戶流失藍(lán)圖的兩種配置:一種使用浮點(diǎn)值表示貨幣金額(如我們在 第一期 中所描述的那樣),另一種使用十進(jìn)制值表示貨幣金額(這是我們當(dāng)前報告的性能數(shù)字所針對的配置)。由于其語義和健壯性,十進(jìn)制算法比浮點(diǎn)算法成本更高,但只要所涉及的所有十進(jìn)制類型都在 64 位以內(nèi),就可以通過 RAPIDS 加速器插件來加速。
配置 RAPIDS 加速器以啟用更多操作
RAPIDS 加速器對于在 GPU 上執(zhí)行 MIG ht 表現(xiàn)出較差性能或返回與基于 CPU 的加速器略有不同的結(jié)果的操作持保守態(tài)度。因此,一些可以加速的操作在默認(rèn)情況下可能不會加速,許多實(shí)際應(yīng)用程序需要使這些操作能夠看到最佳性能。我們在 我們的第一期 中看到了這種現(xiàn)象的一個例子,其中我們必須通過將 true 設(shè)置為 true ,在 Spark 配置中顯式啟用浮點(diǎn)聚合操作。類似地,當(dāng)我們將工作負(fù)載配置為使用十進(jìn)制算法時,我們需要通過將 spark.rapids.sql.decimalType.enabled 設(shè)置為 true 來啟用十進(jìn)制加速。
插件文檔 列出了配置支持或不支持的操作,以及在默認(rèn)情況下啟用或禁用某些操作的原因。除了浮點(diǎn)聚合和十進(jìn)制支持之外,生產(chǎn) Spark 工作負(fù)載極有可能受益于以下幾類操作:
鑄造作業(yè) ,特別是從字符串到日期或數(shù)字類型,或從浮點(diǎn)類型到十進(jìn)制類型。
某些 Unicode 字符不支持字符串大小寫(例如“ SELECT UPPER(name) FROM EMPLOYEES ”),更改大小寫也會更改字符寬度(以字節(jié)為單位),但許多應(yīng)用程序不使用此類字符[或者通過將 Spark 。 RAPIDS 。 sql 。 compatibleops 。 enabled 設(shè)置為 true 來啟用它們和其他幾個。
從 CSV 文件中讀取特定類型;雖然插件( Spark 。 RAPIDS 。 sql 。 format 。 CSV 。 enabled )中當(dāng)前默認(rèn)啟用了讀取 CSV 文件,但讀取某些類型的無效值(尤其是數(shù)字類型、日期和小數(shù))在 GPU 和 CPU 上會有不同的行為,因此需要單獨(dú)啟用每個類型的讀取。
加快從 CSV 文件接收數(shù)據(jù)
CSV 閱讀需要額外的注意:它是昂貴的,加速它可以提高許多工作的性能。然而,由于在 RAPIDS 加速器下讀取 CSV 的行為可能與在 cpu 上執(zhí)行時的 Spark 行為不同,并且由于實(shí)際 CSV 文件質(zhì)量的巨大動態(tài)范圍,因此驗(yàn)證在 GPU 上讀取 CSV 文件的結(jié)果尤為重要。一個快速但有價值的健全性檢查是確保在 GPU 上讀取 CSV 文件返回的空值數(shù)與在 CPU 上讀取相同的文件返回的空值數(shù)相同。當(dāng)然,如果可能的話,使用像 Parquet 或 ORC 這樣的自文檔結(jié)構(gòu)化輸入格式而不是 CSV 有很多好處。
避免查詢優(yōu)化的意外后果
RAPIDS 加速器將 物理查詢計劃 轉(zhuǎn)換為將某些操作符委派給 GPU 。 但是,在 Spark 生成物理計劃時,它已經(jīng)對邏輯計劃執(zhí)行了幾個轉(zhuǎn)換,這可能涉及重新排序操作。 因此,開發(fā)人員或分析人員聲明的接近查詢或數(shù)據(jù)幀操作末尾的操作可能會從查詢計劃的葉移向根。

圖 2 : 一種執(zhí)行數(shù)據(jù)幀查詢的描述,該查詢連接兩個數(shù)據(jù)幀,然后過濾結(jié)果。 如果謂詞具有足夠的選擇性,則大多數(shù)輸出元組將被丟棄。

圖 3 : 執(zhí)行數(shù)據(jù)幀查詢的描述,在連接結(jié)果之前過濾兩個輸入關(guān)系。 如果可以對每個輸入關(guān)系獨(dú)立地計算謂詞,那么此查詢執(zhí)行將產(chǎn)生與圖 2 中的查詢執(zhí)行相同的結(jié)果,效率將大大提高。
一般來說,這種轉(zhuǎn)換可以提高性能。 例如,考慮一個查詢,該查詢連接兩個數(shù)據(jù)幀,然后過濾結(jié)果: 如果可能的話,在執(zhí)行連接之前執(zhí)行過濾器通常會更有效。 這樣做將減少連接的基數(shù),消除最終不必要的比較,減少內(nèi)存壓力,甚至可能減少連接中需要考慮的數(shù)據(jù)幀分區(qū)的數(shù)量。 然而,這種優(yōu)化可能會產(chǎn)生違反直覺的后果: 如果向查詢計劃的根移動的操作僅在 CPU 上受支持,或者如果它生成的值的類型在 GPU 上不受支持,則主動查詢重新排序可能會對 GPU 的性能產(chǎn)生負(fù)面影響。 當(dāng)這種情況發(fā)生時,在 CPU 上執(zhí)行的查詢計劃的百分比可能比嚴(yán)格需要的要大。 您通??梢越鉀Q這個問題,并通過將查詢劃分為兩個分別執(zhí)行的部分來提高性能,從而強(qiáng)制在查詢計劃的葉子附近僅 CPU 的操作僅在原始查詢的可加速部分在 GPU 上運(yùn)行之后執(zhí)行。
結(jié)論
在第三期文章中,我們詳細(xì)介紹了如何充分利用 Apache Spark 和 Apache RAPIDS 加速器 Spark 。 大多數(shù)團(tuán)隊(duì)都會通過干凈地使用 Spark 的數(shù)據(jù)幀抽象來實(shí)現(xiàn)最大的好處。 但是,一些應(yīng)用程序可能會受益于細(xì)微的調(diào)整,特別是考慮 RAPIDS 加速器的執(zhí)行模型并避免不受支持的操作的保留語義的代碼更改。 未來幾期文章將討論數(shù)據(jù)科學(xué)發(fā)現(xiàn)工作流和機(jī)器學(xué)習(xí)生命周期的其余部分。
關(guān)于作者
William Benton在NVIDIA數(shù)據(jù)科學(xué)產(chǎn)品小組工作,他熱衷于使機(jī)器學(xué)習(xí)從業(yè)人員可以輕松地從先進(jìn)的基礎(chǔ)架構(gòu)中受益,并使組織可以管理機(jī)器學(xué)習(xí)系統(tǒng)。 在擔(dān)任過以前的職務(wù)時,他定義了與數(shù)據(jù)科學(xué)和機(jī)器學(xué)習(xí)有關(guān)的產(chǎn)品戰(zhàn)略和專業(yè)服務(wù)產(chǎn)品,領(lǐng)導(dǎo)了數(shù)據(jù)科學(xué)家和工程師團(tuán)隊(duì),并為與數(shù)據(jù),機(jī)器學(xué)習(xí)和分布式系統(tǒng)有關(guān)的開源社區(qū)做出了貢獻(xiàn)。
審核編輯:郭婷
-
加速器
+關(guān)注
關(guān)注
2文章
833瀏覽量
39613 -
NVIDIA
+關(guān)注
關(guān)注
14文章
5442瀏覽量
108498 -
機(jī)器學(xué)習(xí)
+關(guān)注
關(guān)注
66文章
8530瀏覽量
135970
發(fā)布評論請先 登錄
NVIDIA黃仁勛向SpaceX馬斯克交付DGX Spark
NVIDIA DGX Spark新一代AI超級計算機(jī)正式交付
MediaTek攜手NVIDIA開啟個人AI算力新紀(jì)元
NVIDIA DGX Spark桌面AI計算機(jī)開啟預(yù)訂

NVIDIA RAPIDS 25.06版本新增多項(xiàng)功能
使用NVIDIA GPU加速Apache Spark中Parquet數(shù)據(jù)掃描

Nginx和Apache的差異
使用NVIDIA Triton和TensorRT-LLM部署TTS應(yīng)用的最佳實(shí)踐

NVIDIA發(fā)布AI優(yōu)先DGX個人計算系統(tǒng)
NVIDIA加速的Apache Spark助力企業(yè)節(jié)省大量成本

NVIDIA GTC2025 亮點(diǎn) NVIDIA推出 DGX Spark個人AI計算機(jī)

NVIDIA 宣布推出 DGX Spark 個人 AI 計算機(jī)

華為云 FlexusX 實(shí)例下的 Kafka 集群部署實(shí)踐與性能優(yōu)化

RAPIDS cuDF將pandas提速近150倍

評論