使用 MongoDB 在 Python 中编写面向对象的决策树

使用 MongoDB 在 Python 中编写面向对象的决策树

Source: 约翰普莱纽斯

介绍

面向对象程序 (OOP) 受益于其模块化,因为可以隔离部分以进行故障排除。也可以调用函数在其他函数中使用,从而减少所需的编码时间。

决策树是一种流行的算法,因为与神经网络相比,它降低了计算成本。尽管由于参数固定,它们的适应性较差,但它们对于不易更改的数据结构很有用。

MongoDB 是一个安全的文档数据库,可以连接到 Python 以构建安全的、支持数据库的程序。它是一个 NoSQL 数据库,这意味着它以列表格式存储数据以实现多功能性。

在这个项目中,我们使用 Python 开发了一个面向对象的程序,该程序使用决策树来预测中风的风险,使用 MongoDB 进行数据库存储。

为了数据安全,任何敏感信息都将被审查。

第一步:获取数据。

我使用 Kaggle 找到了一个具有高票数和高可用性的数据集,以防止任何有关数据完整性的问题。我下载了 中风预测数据集 经过 费德索里亚诺 ,谁已将 30 个数据集上传到 Kaggle,所有数据集的可用性均为 10.0,请查看!该文件以逗号分隔值 (.csv) 格式提供。

步骤 2:配置 MongoDB 客户端。

要使用 MongoDB,您需要创建一个 帐户 .它是完全免费的,他们提供 订阅 如果需要。注册后,您将被定向到 MongoDB 仪表板的“项目”部分。点击“新建项目”。

MongoDB dashboard projects section.

命名您的项目(我命名为 0),然后按“下一步”。

Name your project

添加成员并为您的项目设置权限,方法是添加他们的电子邮件地址以向他们发送邀请。这样做时,您可以使用下拉框设置角色,以确保项目的安全性。点击“创建项目”。

Add members and set permissions.

您将被带到项目仪表板的“数据库部署”部分,并会提示您创建数据库。点击“建立数据库”。

Data

然后,您将部署一个免费的云数据库,它将使用共享服务器。单击共享服务器框上的“创建”。

Cloud database deployment options

MongoDB 将自动配置您的集群。您可以自定义云提供商、更改服务器、升级集群大小、探索备份选项并命名您的集群。我使用了默认设置。

Cluster configuration

设置集群的登录详细信息。或者,x.509 证书可用于无密码身份验证。完成后,登录方法将出现在表格中。

Security configuration

接下来,选择是要在本地连接还是通过云连接。我选择在本地连接以进行演示。单击“添加您当前的 IP 地址”以连接到集群,然后单击“完成并关闭”。

Connection configuration

出现提示时,单击“转到数据库”。

Congratulations prompt

您将返回“数据库部署”页面以查找新集群。点击“连接”。

Database Deployments

要连接到 Python 应用程序,请单击“连接您的应用程序”。

Application connection options

使用以下代码检查您的 Python 版本。

 从平台导入 python_version  
 python_version()

在 MongoDB 上选择您的版本并选择“包含完整的驱动程序代码示例”。将代码复制到剪贴板。

Connecting the Python application to the cluster

在与数据集相同的文件夹中创建一个空白的 Jupyter 笔记本。导入 pymongo,然后将 MongoDB 中的代码粘贴到下一行,更改“ ”(包括<>)作为您的密码。

 # MongoDB 连接。  
 # 导入 pymongo 以连接到 MongoDB。  
 导入pymongo # 使用 MongoDB 中的代码,将帐户连接到客户端。  
 客户端 = pymongo.MongoClient("mongodb+srv://user:<password> @cluster0.2z3xdjn.mongodb.net/?retryWrites=true&w=majority") # 尝试连接到客户端。  
 db = client.test

现在通过在下一行输入“db”并运行它来测试您的连接。在输出中,您应该会看到“connect=True”(如果有效)。

Testing the client connection

做得好!如果您已经做到了这一点,那么您已经成功配置了 MongoDB 客户端。

第 3 步:将数据集上传到 MongoDB。

使用以下代码片段加载笔画数据集,将其转换为字典格式,创建数据库并上传转换后的数据。如果要使用替代数据集,您只需更改文件名以匹配。

 # 上传数据到 MongoDB。  
 # Pandas 被导入以读取 (.csv) 文件。  
 将熊猫导入为 pd # 数据集是使用 pandas 的 read_csv 函数加载的。  
 df = pd.read_csv('healthcare-dataset-stroke-data.csv') # 数据集被转换为字典格式。  
 数据 = df.to_dict(orient = 'records') # 在客户端创建数据库。  
 db = 客户端['数据库'] # 转换后的数据被插入到MongoDB数据库中  
 db.stroke.insert_many(数据)

PyMongo 确认上传成功。

Successful upload comment

返回到 MongoDB 上的“数据库部署”,然后在您的集群上单击“浏览集合”。不出所料,数据传输成功。

Dataset uploaded to MongoDB

第 4 步:设计面向对象的程序。

将类定义为“模型”。

 # 该类已定义并托管了任务所需的所有功能。  
 班级型号:

通过添加整个类中使用的任何变量来配置类的“init”函数。数据集从 MongoDB 加载并转换为 Pandas 数据框。导入并定义决策树,固定随机种子以确保可重复性。数据集已预览。

要使用您自己的详细信息登录,请从前面描述的连接向导中复制代码并用它替换我的详细信息。

要使用替代模型,请将“DecisionTreeClassifier”更改为替代模型。

 # 数据集和模型的初始化。  
 def __init__(self):  
 # 导入必要的库  
 import pandas as pd # 用于数据操作。  
 from sklearn.tree import DecisionTreeClassifier # 用作分类算法。 # 用于 MongoDB 集成的 Pymongo 库。  
 import pymongo # 与 MongoDB 通信。  
 from pymongo.mongo_client import MongoClient # 登录 MongoDB。  
 from pymongo.server_api import ServerApi # 与 MongoDB 服务器通信。  
          
 # 使用 mongoDB 的用户名和密码登录客户端。  
 客户端 = pymongo.MongoClient("mongodb+srv://jayparekh:<password> @cluster0.m6t3kym.mongodb.net/?retryWrites=true&w=majority", server_api=ServerApi('1'))  
 # 创建数据库  
 db = 客户端['CMP6221']  
 # 在数据库中创建一个集合。  
 测试 = db.stroke  
 #将集合转换为 Pandas 数据框。  
 测试 = pd.DataFrame(list(test.find()))  
 # 定义转换后的数据框。  
 self.df = 测试  
 # 定义决策树设置随机状态的可重复性。  
 self.classifier = DecisionTreeClassifier(random_state=100)  
 # 显示数据集。  
 print('原始数据集:\n', self.df.head())

Dataset preview.

配置一个名为“corr”的函数,以使用数据框生成相关矩阵,从而深入了解数据。将矩阵绘制为热图以获得更好的可视化效果。

如果您的数据集被称为“df”以外的名称,请更改函数中的文件名。

 # 可视化数据。  
 def corr(自我):  
 from matplotlib import pyplot as plt # 可视化数据。  
 import seaborn as sns # 绘制可视化图。  
 # 使用 corr 函数计算数据集中的相关性,并定义它们以在热图中使用。  
 corrdata = self.df.corr()  
 # 绘制热图以显示数据集中名为相关热图的数据的相关性。  
 fig = plt.subplots (figsize = (10,10))  
 plt.title("相关热图")  
 sns.heatmap(corrdata)  
 plt.show()

配置一个名为“clean”的函数以删除空值并将字符串变量编码为二进制格式,以便决策树可以解释它们。

如果您的数据集被称为“df”以外的名称,请更改函数中的文件名。

如果您要在另一个数据集中对特征进行编码,则“ever_married”等特征将更改为您的特征,请根据需要复制脚本。

 # 数据清理,删除空值和编码字符串变量。  
 def 清洁(自我):  
 from sklearn import preprocessing # 用于标签编码。  
 self.df = self.df.dropna()  
 le = preprocessing.LabelEncoder()  
 self.df['ever_married'] = le.fit_transform(self.df['ever_married'])  
 self.df['work_type'] = le.fit_transform(self.df['work_type'])  
 self.df['吸烟状态'] = le.fit_transform(self.df['吸烟状态'])  
 self.df['Residence_type'] = le.fit_transform(self.df['Residence_type'])  
 self.df['gender'] = le.fit_transform(self.df['gender'])  
 print('清理的数据集:\n', self.df.head())

配置一个名为“split”的函数,将从查看相关热图中选择的必要特征数据与标签数据分开,然后使用“train-test split”将数据拆分为训练集和测试集。

使用“test_size”作为变量,以便用户可以在不修改脚本的情况下更改拆分的大小。

如果您的数据集被称为“df”以外的名称,请更改函数中的文件名。

如果要更改用于特征数据的变量,可以在“self.X”部分中选择它们。使用“self.y”设置标签变量。

 # train-test-split 以 70:30 的比例由变量 test_size 设置。由于未显示相关性,因此省略了居住状况和性别。  
 def 拆分(自我,test_size):  
 import numpy as np # 用于操作数组。  
 from sklearn.model_selection import train_test_split # 用于准备拟合数据。  
 self.X = np.array(self.df[['age', 'hypertension', 'heart_disease', 'ever_married', 'work_type', 'avg_glucose_level', 'bmi', 'Smoking_status']])  
 self.y = np.array(self.df['stroke'])  
 self.X_train,self.X_test,self.y_train,self.y_test = train_test_split(self.X,self.y,test_size = test_size,random_state = 42)

配置一个名为“fit”的函数,使用训练特征和标签数据训练决策树模型。

如果您配置的算法有另一个名称,请将“分类器”替换为该名称。

 # 使用训练数据拟合模型。  
 默认适合(自我):  
 self.model = self.classifier.fit(self.X_train, self.y_train)

配置一个名为“predict”的函数,以使用经过训练的模型使用测试数据来预测结果。

如果您配置的算法有另一个名称,请将“分类器”替换为该名称。

 # 使用测试数据测试的模型。  
 def 预测(自我):  
 self.predictions = self.classifier.predict(self.X_test)  
 返回自我预测

配置一个名为“cvscoring”的函数以使用 10 倍交叉验证对模型进行评分。

如果您配置的算法有另一个名称,请将“分类器”替换为该名称。

 # 原始模型的交叉验证。  
 def cvscoring(自我):  
 from sklearn.model_selection import cross_val_score # 用于模型的交叉验证。  
 from matplotlib import pyplot as plt # 可视化数据。  
 import seaborn as sns # 绘制可视化。  
 orig_cv_scores = cross_val_score(estimator = self.classifier, X = model_instance.X, y= model_instance.y, cv = 10)  
 fig = plt.subplots(1, figsize=(5, 5))  
 sns.boxplot(数据 = orig_cv_scores)  
 plt.title("初始交叉验证分数 DT")  
 plt.show()  
 print('\n 初始平均 CV 分数:', model_instance.model.score(model_instance.X_test, model_instance.y_test))

配置一个名为“initial_params”的函数来获取模型的参数。

如果您配置的算法有另一个名称,请将“分类器”替换为该名称。

 # pprint 获取初始模型的参数。  
 定义初始参数(自我):  
 from pprint import pprint # 评估模型参数。  
 print('\n 初始参数:')  
 pprint(self.classifier.get_params())

配置一个名为“tune”的函数来调整原始模型,对其进行 10 倍交叉验证,并返回新模型的改进百分比。

要更改调优中使用的参数,请修改 param_dist 表。

如果您配置的算法有另一个名称,请将“分类器”替换为该名称。

 # 模型调整。该模型通过各种合适的组合进行了调整,这些组合使用 RandomizedSearchCV 进行实施。  
 # max_depth 考虑在预测之前可以进行的分割数。  
 # max_features 确定考虑的特征数量。  
 # min_samples_leaf 定义了节点分裂所需的最小样本。  
 # 标准确定用于测量拆分纯度的函数。  
 def 曲调(自我):  
 from pprint import pprint # 评估模型参数  
 from sklearn.model_selection import RandomizedSearchCV # 调整模型。  
 import pandas as pd # 用于数据操作。  
 from matplotlib import pyplot as plt # 可视化数据。  
 import seaborn as sns # 绘制可视化。  
 from sklearn.metrics import accuracy_score # 计算准确率。  
 param_dist = {"max_depth": [5, 7, 10, 15, 无],  
 "max_features": [无, 2, 4, 6, 8, 10],  
 "min_samples_leaf": (1, 2, 4),  
 “标准”:[“基尼”,“熵”]}  
 self.tree_cv = RandomizedSearchCV(self.classifier, param_dist, cv=10)  
          
 # 调整后的模型适合数据。  
 self.tuned_tree = self.tree_cv.fit(model_instance.X_train, model_instance.y_train)  
          
 # 使用'.cv_results_'以表格形式获得交叉验证结果数组。  
 tune_results = self.tree_cv.cv_results_ # “DataFrame”函数用于将结果数组转换为定义为“Tuned_Results”的数据帧。  
 Tuned_Results = pd.DataFrame(tuned_results) # 绘制箱线图,显示获得的平均交叉验证分数。  
 fig = plt.subplots(1, figsize=(5, 5))  
 sns.boxplot(数据 = Tuned_Results,y = 'mean_test_score')  
 plt.title("调谐平均 CV 分数 DT")  
 plt.show()  
          
 # 显示调整后的模型参数。  
 print('\n 最优参数:')  
 打印(self.tree_cv.best_params_)  
          
 # 显示了调整模型的平均交叉验证分数。  
 print("\n 调整后的平均 CV 分数:")  
 打印(self.tree_cv.best_score_)  
          
 # 显示了相对于原始模型参数的百分比改进。  
 print("\n 使用 RandomizedSearchCV 的百分比改进")  
 print(((self.tree_cv.best_score_-accuracy_score(model_instance.y_test, model_instance.predictions))/accuracy_score(model_instance.y_test, model_instance.predictions))*100)

配置一个名为“confmatrix”的函数来评估调整后的模型并可视化其预测。

 # 一个混淆矩阵表示模型输出。  
 def confmatrix(自我):  
 from sklearn.metrics import chaos_matrix # 可视化结果。  
 import seaborn as sns # 绘制可视化。  
 from matplotlib import pyplot as plt # 可视化数据。  
 ConfMatrix = 混淆矩阵(model_instance.y_test,model_instance.predictions)  
 sns.heatmap(ConfMatrix,不=真)  
 plt.title("优化决策树混淆矩阵")

配置一个名为“classreport”的函数,获取调优模型的分类报告。

 # 调优模型的分类报告。  
 def 类报告(自我):  
 from sklearn.metrics import classification_report # 打印性能指标。  
 print('调整后的模型分类报告:\n', classification_report(model_instance.y_test,model_instance.predictions))

配置一个名为“treeviz”的函数来可视化决策树。

如果您配置的算法有另一个名称,请将“分类器”替换为该名称。

 # 可视化决策树。  
 def treeviz(自我):  
 from matplotlib import pyplot as plt # 可视化数据。  
 from sklearn import tree # 绘制决策树。  
 fig = plt.figure(figsize=(25,20))  
 plt.suptitle("决策树可视化")  
 _ = tree.plot_tree(self.classifier, feature_names=self.df.columns.values, class_names='stroke',filled=True)

第 5 步:设计 main 函数,执行模型。

每个函数都按所需的顺序调用,并在使用它们的地方添加变量。要更改训练-测试拆分,请将变量“0.3”更改为所需的测试数据大小,介于 0 和 1 之间。

 # main: 函数已定义。每个阶段调用函数来执行模型。  
 如果 __name__ == '__main__':  
 模型实例 = 模型()  
 model_instance.corr()  
 model_instance.clean()  
 model_instance.split(0.3)  
 model_instance.fit()  
 model_instance.predict()  
 model_instance.initial_params()  
 model_instance.cvscoring()  
 model_instance.tune()  
 model_instance.confmatrix()  
 model_instance.classreport()  
 model_instance.treeviz()

结果

 原始数据集:  
 _id id 性别 年龄 高血压 heart_disease \  
 0 630c2d66ccb4d1494b0bba11 9046 男 67.0 0 1  
 1 630c2d66ccb4d1494b0bba12 51676 女 61.0 0 0  
 2 630c2d66ccb4d1494b0bba13 31112 男 80.0 0 1  
 3 630c2d66ccb4d1494b0bba14 60182 女 49.0 0 0  
 4 630c2d66ccb4d1494b0bba15 1665 女 79.0 1 0  
  
 ever_married work_type Residence_type avg_glucose_level bmi \  
 0 是 民营 城市 228.69 36.6  
 1 是 个体户 农村 202.21 NaN  
 2 是 民营 农村 105.92 32.5  
 3 是 民营 城市 171.23 34.4  
 4 是 个体户 农村 174.12 24.0  
  
 吸烟状态中风  
 0 以前吸过 1  
 1 从不吸烟 1  
 2 从不吸烟 1  
 3 抽 1  
 4 从不吸烟 1

Correlation heatmap

 清理数据集:  
 _id id 性别 年龄 高血压 heart_disease \  
 0 630c2d66ccb4d1494b0bba11 9046 1 67.0 0 1  
 2 630c2d66ccb4d1494b0bba13 31112 1 80.0 0 1  
 3 630c2d66ccb4d1494b0bba14 60182 0 49.0 0 0  
 4 630c2d66ccb4d1494b0bba15 1665 0 79.0 1 0  
 5 630c2d66ccb4d1494b0bba16 56669 1 81.0 0 0  
  
 ever_married work_type Residence_type avg_glucose_level bmi \  
 0 1 2 1 228.69 36.6  
 2 1 2 0 105.92 32.5  
 3 1 2 1 171.23 34.4  
 4 1 3 0 174.12 24.0  
 5 1 2 1 186.21 29.0  
  
 吸烟状态中风  
 0 1 1  
 2 2 1  
 3 3 1  
 4 2 1  
 5 1 1  
  
 初始参数:  
 {'ccp_alpha': 0.0,  
 'class_weight':无,  
 “标准”:“基尼”,  
 “最大深度”:无,  
 'max_features':无,  
 'max_leaf_nodes':无,  
 'min_impurity_decrease': 0.0,  
 'min_samples_leaf': 1,  
 'min_samples_split': 2,  
 'min_weight_fraction_leaf':0.0,  
 “随机状态”:100,  
 “分离器”:“最佳”} 初始平均 CV 分数:0.9205702647657841

Initial cross validation score

 最佳参数:  
 {'min_samples_leaf':1,'max_features':4,'max_depth':5,'criterion':'gini'}  
  
 调整后的平均 CV 分数:  
 0.9540180690216286 使用 RandomizedSearchCV 的百分比改进  
 3.6333787366415136

Tuned cross validation score

 调整后的模型分类报告:  
 精确召回 f1 分数支持  
  
 0 0.97 0.95 0.96 1413  
 1 0.15 0.20 0.17 60  
  
 精度 0.92 1473  
 宏平均 0.56 0.58 0.56 1473  
 加权平均 0.93 0.92 0.93 1473

Tuned confusion matrix

Decision tree visualization

结论

总之,该模型的交叉验证分数增加了 3.63%(至 2 dp)。该模型使用了面向对象的编程,尽管大多数函数没有输入,例如,这会使更改数据集变得困难。一种改进的方法是使用一个名为“config”的文件来存储每个函数的参数,以便可以安全地控制程序。

参考

[

scikit-学习

“我们使用 scikit-learn 来支持前沿基础研究 [...]”

scikit-learn.org

](https://scikit-learn.org/stable/index.html)

[

MongoDB:开发者数据平台 | MongoDB

产品解决方案客户故事了解企业如何利用 MongoDB 白皮书和演示文稿……

www.mongodb.com

](https://www.mongodb.com/)

[

数字货币

为什么选择 NumPy?强大的 n 维数组。数值计算工具。可互操作。高性能。开源。

numpy.org

](https://numpy.org/)

[

熊猫

pandas 是一个快速、强大、灵活且易于使用的开源数据分析和操作工具,建立在...

pandas.pydata.org

](https://pandas.pydata.org/)

[

seaborn:统计数据可视化 - seaborn 0.11.2 文档

Seaborn 是一个基于 matplotlib 的 Python 数据可视化库。它为绘图提供了一个高级界面……

seaborn.pydata.org

](https://seaborn.pydata.org/)

[

pprint - 数据漂亮的打印机 - Python 3.10.6 文档

源代码:Lib/pprint.py 该模块提供了“漂亮打印”任意 Python 数据结构的能力。

docs.python.org

](https://docs.python.org/3/library/pprint.html)

版权声明:本文为博主原创文章,遵循 CC 4.0 BY-SA 版权协议,转载请附上原文出处链接和本声明

本文链接:https://www.qanswer.top/1754/56093016

posted @ 2022-08-30 16:57  哈哈哈来了啊啊啊  阅读(148)  评论(0编辑  收藏  举报