共用方式為


教學課程:使用語意連結探索 Synthea 數據集中的關聯性

本教學課程說明如何使用語意連結來偵測公用 Synthea 數據集中的關聯性。

當您使用新數據或在沒有現有數據模型的情況下運作時,自動探索關聯性會很有説明。 此關聯性偵測可協助您:

  • 瞭解高階的模型
  • 在探勘數據分析期間取得更多深入解析,
  • 驗證更新的數據或新的、傳入的數據,以及
  • 清除數據。

即使事先知道關聯性,搜尋關聯性也有助於進一步了解數據模型或識別數據質量問題。

在本教學課程中,您會從簡單的基準範例開始,其中您只實驗三個數據表,讓兩者之間的連線很容易遵循。 然後,您會以較大的數據表集顯示更複雜的範例。

在本教學課程中,您會了解如何:

  • 使用語意連結的 Python 連結庫 (SemPy) 元件,支援與 Power BI 整合,並協助自動化數據分析。 這些元件包括:
    • FabricDataFrame - 使用其他語意信息增強的 pandas 類似結構。
    • 將語意模型從 Fabric 工作區提取至筆記本的函式。
    • 自動化語意模型中關聯性探索和視覺效果的函式。
  • 針對具有多個數據表和相互相關性的語意模型關聯性探索程序進行疑難解答。

必要條件

  • 從左側瀏覽窗格中選取 [工作區 ],以尋找並選取您的工作區。 此工作區會變成您目前的工作區。

在筆記本中跟著

relationships_detection_tutorial.ipynb 筆記本會伴隨本教學課程。

若要開啟本教學課程隨附的筆記本,請遵循準備系統以進行數據科學教學課程中的指示,將筆記本匯入您的工作區。

如果您想要複製並貼上此頁面中的程式碼,您可以 建立新的筆記本

開始執行程序代碼之前,請務必將 Lakehouse 附加至筆記本

設定筆記本

在本節中,您會使用必要的模組和數據來設定筆記本環境。

  1. 使用%pip筆記本內的內嵌安裝功能從 PyPI 安裝SemPy

    %pip install semantic-link
    
  2. 執行稍後需要的必要 SemPy 模組匯入:

    import pandas as pd
    
    from sempy.samples import download_synthea
    from sempy.relationships import (
        find_relationships,
        list_relationship_violations,
        plot_relationship_metadata
    )
    
  3. 匯入 pandas 以強制執行可協助輸出格式設定的組態選項:

    import pandas as pd
    pd.set_option('display.max_colwidth', None)
    
  4. 提取範例數據。 在本教學課程中,您會使用 綜合醫療記錄的 Synthea 數據集(為了簡單起見,小版):

    download_synthea(which='small')
    

偵測 Synthea 數據表子集的關聯性

  1. 從較大的集合中選取三個數據表:

    • patients 指定病患資訊
    • encounters 指定有醫療接觸的患者(例如醫療預約、程式)
    • providers 指定哪些醫療提供者參加了病人

    數據表encounters會解析 和 providers 之間的patients多對多關聯性,可描述為關聯實體

    patients = pd.read_csv('synthea/csv/patients.csv')
    providers = pd.read_csv('synthea/csv/providers.csv')
    encounters = pd.read_csv('synthea/csv/encounters.csv')
    
  2. 使用 SemPy 函 find_relationships 式尋找資料表之間的關聯性:

    suggested_relationships = find_relationships([patients, providers, encounters])
    suggested_relationships
    
  3. 使用 SemPy 的 plot_relationship_metadata 函式,將 DataFrame 關聯性可視化為圖形。

    plot_relationship_metadata(suggested_relationships)
    

    顯示數據集中數據表之間關聯性的螢幕快照。

    函式會配置從左側到右側的關聯性階層,其對應至輸出中的 “from” 和 “to” 數據表。 換句話說,左側的獨立「from」數據表會使用其外鍵指向右側的「對」相依性數據表。 每個實體方塊都會顯示參與關聯性之「從」或「到」端的數據行。

    根據預設,關聯性會產生為 「m:1」 (而不是 “1:m”) 或 “1:1”。 「1:1」關聯性可以產生一或兩種方式,取決於對應值與所有值的比例是否只超過 coverage_threshold 一或兩個方向。 稍後在本教學課程中,您會討論 「m:m」關聯性較不頻繁的情況。

針對關聯性偵測問題進行疑難解答

基準範例會顯示全新 Synthea 數據上成功的關聯性偵測。 在實務上,數據很少清除,因此無法成功偵測。 當數據未清除時,有數種技術很有用。

本教學課程的本節說明語意模型包含臟數據時的關聯性偵測。

  1. 首先,操作原始 DataFrame 以取得「骯髒」的數據,並列印臟數據的大小。

    # create a dirty 'patients' dataframe by dropping some rows using head() and duplicating some rows using concat()
    patients_dirty = pd.concat([patients.head(1000), patients.head(50)], axis=0)
    
    # create a dirty 'providers' dataframe by dropping some rows using head()
    providers_dirty = providers.head(5000)
    
    # the dirty dataframes have fewer records than the clean ones
    print(len(patients_dirty))
    print(len(providers_dirty))
    
    
  2. 為了進行比較,原始數據表的列印大小:

    print(len(patients))
    print(len(providers))
    
  3. 使用 SemPy 函 find_relationships 式尋找資料表之間的關聯性:

    find_relationships([patients_dirty, providers_dirty, encounters])
    

    程式代碼的輸出顯示,由於您稍早引進來建立「骯髒」語意模型的錯誤,因此沒有偵測到關聯性。

使用驗證

驗證是針對關聯性偵測失敗進行疑難解答的最佳工具,因為:

  • 它清楚地報告為什麼特定關聯性未遵循外鍵規則,因此無法偵測到。
  • 它會使用大型語意模型快速執行,因為它只著重於宣告的關聯性,而且不會執行搜尋。

驗證可以使用任何 DataFrame 與 所 find_relationships產生數據行類似的數據行。 在下列程式代碼中 suggested_relationships ,DataFrame 會參考 patients 而不是 patients_dirty,但您可以使用字典將 DataFrame 別名:

dirty_tables = {
    "patients": patients_dirty,
    "providers" : providers_dirty,
    "encounters": encounters
}

errors = list_relationship_violations(dirty_tables, suggested_relationships)
errors

鬆散搜尋準則

在更模糊的案例中,您可以嘗試放寬搜尋準則。 這個方法會增加誤判的可能性。

  1. 設定 include_many_to_many=True 並評估它是否有説明:

    find_relationships(dirty_tables, include_many_to_many=True, coverage_threshold=1)
    

    結果顯示偵測到 的patients關聯性encounters,但有兩個問題:

    • 關聯性表示從 patientsencounters的方向,這是預期關聯性的反函數。 這是因為所有patients碰巧都由 (Coverage From是 1.0) 覆蓋encounters,而encounters只是部分覆蓋 patientsCoverage To= 0.85),因為患者數據列遺失。
    • 低基數 GENDER 數據行發生意外比對,這兩個數據表中的名稱和值都會比對,但這不是感興趣的 「m:1」 關聯性。 低基數是由 Unique Count FromUnique Count To 數據行表示。
  2. 請重新執行 find_relationships 以只尋找 「m:1」 關聯性,但具有較低的 coverage_threshold=0.5

    find_relationships(dirty_tables, include_many_to_many=False, coverage_threshold=0.5)
    

    結果會顯示從 encountersproviders的正確關聯性方向。 不過,不會偵測到從 encounterspatients 的關聯性,因為 不是因為 patients 不唯一的,因此不能位於 「m:1」 關聯性的 「One」 端。

  3. include_many_to_many=True鬆散和 coverage_threshold=0.5

    find_relationships(dirty_tables, include_many_to_many=True, coverage_threshold=0.5)
    

    現在兩個感興趣的關聯性都可見,但有更多的噪音:

    • 上的 GENDER 低基數比對存在。
    • 出現 ORGANIZATION 較高的基數 「m:m」 比對,因此很明顯 ORGANIZATION ,這很可能是兩個數據表的數據行反正規化。

比對數據行名稱

根據預設,SemPy 會視為只比對顯示名稱相似度的屬性,並利用資料庫設計工具通常以相同方式命名相關數據行的事實。 此行為有助於避免經常發生低基數整數索引鍵的假交關聯性。 例如,如果有 1,2,3,...,10 產品類別和 1,2,3,...,10 訂單狀態代碼,當只查看值對應而不考慮數據行名稱時,它們會彼此混淆。 假象關聯性不應該是類似 GUID 的索引鍵的問題。

SemPy 會查看資料行名稱和數據表名稱之間的相似度。 比對是近似且不區分大小寫。 它會忽略最常遇到的 「decorator」 子字串,例如 「id」、“code”、“name”、“key”、“pk”、“fk”。 因此,最常見的比對案例如下:

  • 實體 'foo' 中稱為 'column' 的屬性會比對實體 'bar' 中稱為 'column' 的屬性(也稱為 'COLUMN' 或 'Column')。
  • 實體 'foo' 中名為 'column' 的屬性與 'bar' 中稱為 'column_id' 的屬性相符。
  • 實體 'foo' 中名為 'bar' 的屬性與 'bar' 中稱為 'code' 的屬性相符。

藉由先比對數據行名稱,偵測會更快執行。

  1. 符合資料列名稱:

    • 若要瞭解要進一步評估哪些數據行,請使用 verbose=2 選項 (verbose=1 僅列出正在處理的實體)。
    • 參數 name_similarity_threshold 會決定數據行的比較方式。 閾值 1 表示您只對 100% 相符感興趣。
    find_relationships(dirty_tables, verbose=2, name_similarity_threshold=1.0);
    

    以 100% 相似度執行無法解釋名稱之間的小差異。 在您的範例中,數據表具有具有 “s” 後綴的複數形式,這不會完全相符。 這是使用預設 name_similarity_threshold=0.8的妥善處理。

  2. 使用預設值 name_similarity_threshold=0.8重新執行 :

    find_relationships(dirty_tables, verbose=2, name_similarity_threshold=0.8);
    

    請注意,複數格式 patients 的標識符現在會與單數 patient 比較,而不會將太多其他假想比較新增至運行時間。

  3. 使用預設值 name_similarity_threshold=0重新執行 :

    find_relationships(dirty_tables, verbose=2, name_similarity_threshold=0);
    

    變更 name_similarity_threshold 為 0 是另一個極端值,表示您想要比較所有數據行。 這很少必要,而且會導致運行時間增加,以及需要檢閱的虛假相符專案。 觀察詳細信息輸出中的比較數目。

疑難解答秘訣摘要

  1. 從 「m:1」 關聯性完全相符開始 (也就是預設值 include_many_to_many=Falsecoverage_threshold=1.0)。 這通常是您想要的。
  2. 對較小的數據表子集使用窄焦點。
  3. 使用驗證來偵測數據質量問題。
  4. 如果您要瞭解哪些資料列被視爲關聯性, 請使用 verbose=2 。 這可能會導致大量的輸出。
  5. 請注意搜尋自變數的取捨。 include_many_to_many=Truecoverage_threshold<1.0 可能會產生可能更難分析且需要篩選的假關係。

偵測完整 Synthea 數據集上的關聯性

簡單的基準範例是一個方便的學習和疑難解答工具。 實際上,您可以從語意模型開始,例如完整的 Synthea 數據集,其中包含更多數據表。 探索完整的 合成器 數據集,如下所示。

  1. synthea/csv 目錄讀取所有檔案:

    all_tables = {
        "allergies": pd.read_csv('synthea/csv/allergies.csv'),
        "careplans": pd.read_csv('synthea/csv/careplans.csv'),
        "conditions": pd.read_csv('synthea/csv/conditions.csv'),
        "devices": pd.read_csv('synthea/csv/devices.csv'),
        "encounters": pd.read_csv('synthea/csv/encounters.csv'),
        "imaging_studies": pd.read_csv('synthea/csv/imaging_studies.csv'),
        "immunizations": pd.read_csv('synthea/csv/immunizations.csv'),
        "medications": pd.read_csv('synthea/csv/medications.csv'),
        "observations": pd.read_csv('synthea/csv/observations.csv'),
        "organizations": pd.read_csv('synthea/csv/organizations.csv'),
        "patients": pd.read_csv('synthea/csv/patients.csv'),
        "payer_transitions": pd.read_csv('synthea/csv/payer_transitions.csv'),
        "payers": pd.read_csv('synthea/csv/payers.csv'),
        "procedures": pd.read_csv('synthea/csv/procedures.csv'),
        "providers": pd.read_csv('synthea/csv/providers.csv'),
        "supplies": pd.read_csv('synthea/csv/supplies.csv'),
    }
    
  2. 使用 SemPy 函 find_relationships 式尋找資料表之間的關聯性:

    suggested_relationships = find_relationships(all_tables)
    suggested_relationships
    
  3. 可視化關聯性:

    plot_relationship_metadata(suggested_relationships)
    

    數據表之間關聯性的螢幕快照。

  4. 計算使用 探索 include_many_to_many=True到多少新的 「m:m」 關聯性。 這些關聯性除了先前顯示的 「m:1」 關聯性之外;因此,您必須篩選 multiplicity

    suggested_relationships = find_relationships(all_tables, coverage_threshold=1.0, include_many_to_many=True) 
    suggested_relationships[suggested_relationships['Multiplicity']=='m:m']
    
  5. 您可以依各種數據行排序關聯性數據,以深入瞭解其本質。 例如,您可以選擇依和 Row Count To排序輸出Row Count From,以協助識別最大的數據表。

    suggested_relationships.sort_values(['Row Count From', 'Row Count To'], ascending=False)
    

    在不同的語意模型中,也許請務必將焦點放在 Null Null Count From 數目或 Coverage To

    此分析可協助您瞭解是否有任何關聯性可能無效,而且如果您需要從候選專案清單中移除關聯性。

查看語意連結 /SemPy 的其他教學課程: