京公网安备 11010802034615号
经营许可证编号:京B2-20210330
Python机器学习之Logistic回归
大数据时代,数据犹如一座巨大的金矿,等待我们去发掘。而机器学习和数据挖掘的相关技术,无疑就是你挖矿探宝的必备利器!工欲善其事,必先利其器。很多初涉该领域的人,最先困惑的一个问题就是,我该选择哪种“工具”来进行数据挖掘和机器学习。我这里的工具主要指的是“语言、系统和平台”。尽管之于机器学习而言,语言和平台从来都不算是核心问题,但是选择一个你所熟悉的语言和环境确实可以令你事半功倍。

现在你的选择可谓相当广泛,例如Matlab、R和Weka都可以用来进行数据挖掘和机器学习方面的实践。其中,Matlab是众所周知的商业软件,而R和Weka都是免费软件。R是应用于统计和数据分析的首屈一指的计算机语言和平台,如果你是拥有数学或统计学相关专业背景的人,那么使用R来进行数据挖掘就是一个相当不错的选择。我前面有很多介绍利用R语言进行数据挖掘的文章可供参考:
在R中使用支持向量机(SVM)进行数据挖掘
机器学习中的EM算法详解及R语言实例
Weka的全名是怀卡托智能分析环境(Waikato Environment for Knowledge Analysis),是一款免费的,非商业化的,基于Java环境下开源的机器学习(machine learning)以及数据挖掘(data mining)软件。2005年8月,在第11届ACM SIGKDD国际会议上,怀卡托大学的Weka小组荣获了数据挖掘和知识探索领域的最高服务奖,Weka系统得到了广泛的认可,被誉为数据挖掘和机器学习 历史上的里程碑,是现今最完备的数据挖掘工具之一。如果你是一个忠实的Java拥护者,那么使用Weka来进行数据挖掘就非常明智。
如果你对R和Weka(或Java)都不是很熟悉,那么我今天将向你推荐和介绍另外一个进行机器学习和数据挖掘的利器——Python。Python是当前非常流行的计算机编程语言,相对C、C++来说,Python的门槛极低,可以很轻松的上手和掌握。More importantly,Python用于为数众多,而且相当完善的软件包、工具箱来实现功能上的扩展。这一点与R语言来说非常相似(R的扩展包也可以多到超乎你的想象)。
在Python中进行机器学习所需要的软件包主要是Scikit-Learn。Scikit-learn的基本功能主要被分为六个部分,分类,回归,聚类,数据降维,模型选择,数据预处理。
作为一个范例,我们今天将演示在Python (版本是3.5.1)中基于Scikit-Learn所提供的函数来实现Logistic Regression。从名字来看,Logistic 回归 应该属于一种回归方法(事实上,它也确实可以被用来进行回归分析),但实际中,它更多的是被用来作为一种“分类器”(Classifier)。而且,机器学习中,分类技术相比于回归技术而言也确实是一个更大阵营。
在下面这个示例中,我们会更多的使用仅属于Scikit-Learn中的函数来完成任务。
下面这个例子中的数据源于1936年统计学领域的一代宗师费希尔发表的一篇重要论文。彼时他收集了三种鸢尾花(分别标记为setosa、versicolor和virginica)的花萼和花瓣数据。包括花萼的长度和宽度,以及花瓣的长度和宽度。我们将根据这四个特征(中的两个)来建立Logistic Regression模型从而实现对三种鸢尾花的分类判别任务。
首先我们引入一些必要的头文件,然后读入数据(注意我们仅仅使用前两个特征)
[python] view plain copy 在CODE上查看代码片派生到我的代码片
import numpy as npy
from sklearn import linear_model, datasets
from sklearn.cross_validation import train_test_split
from sklearn.feature_extraction import DictVectorizer
from sklearn.metrics import accuracy_score, classification_report
iris = datasets.load_iris()
X = iris.data[:, :2] # we only take the first two features.
Y = iris.target
作为演示,我们来提取其中的前5行数据(包括特征和标签),输出如下。前面我们提到数据中共包含三种鸢尾花(分别标记为setosa、versicolor和virginica),所以这里的标签 使用的是0,1和2三个数字来分别表示对应的鸢尾花品种,显然前面5行都属于标签为0的鸢尾花。而且一共有150个样本数据。
[python] view plain copy 在CODE上查看代码片派生到我的代码片
>>> for n in range(5):
print(X[n], Y[5])
[ 5.1 3.5] 0
[ 4.9 3. ] 0
[ 4.7 3.2] 0
[ 4.6 3.1] 0
[ 5. 3.6] 0
>>> len(X)
150
现在我们利用train_test_split函数来对原始数据集进行分类采样,取其中20%作为测试数据集,取其中80%作为训练数据集。
[python] view plain copy
X_train, X_test, y_train, y_test = train_test_split(X, Y, test_size=0.2, random_state=42)
然后,我们便可以利用LogisticRegression函数来训练一个分类器
[python] view plain copy 在CODE上查看代码片派生到我的代码片
logreg = linear_model.LogisticRegression(C=1e5, , solver='lbfgs', multi_class='multinomial')
logreg.fit(X_train, y_train)
请留意Scikit-Learn文档中,对于参数solver和multi_class的说明。其中solver的可选值有4个:‘newton-cg’, ‘lbfgs’, ‘liblinear’, ‘sag’。
For small datasets, ‘liblinear’ is a good choice, whereas ‘sag’ is
faster for large ones.
For multiclass problems, only ‘newton-cg’ and ‘lbfgs’ handle
multinomial loss; ‘sag’ and ‘liblinear’ are limited toone-versus-rest schemes.
参数multi_class的可选值有2个:‘ovr’, ‘multinomial’。多分类问题既可以使用‘ovr’,也可以使用 ‘multinomial’。但是如果你的选项是 ‘ovr’,那么相当于对每个标签都执行一个二分类处理。Else the loss minimised is the multinomial loss fit acrossthe entire probability distribution. 选项 ‘multinomial’ 则仅适用于将参数solver置为‘lbfgs’时的情况。
然后再利用已经得到的分类器来对测试数据集进行预测
[python] view plain copy 在CODE上查看代码片派生到我的代码片
prediction = logreg.predict(X_test)
print("accuracy score: ")
print(accuracy_score(y_test, prediction))
print(classification_report(y_test, prediction))
预测结果如下,可见总体准确率都在90%以上,分类器执行的还是相当不错的!
[python] view plain copy 在CODE上查看代码片派生到我的代码片
accuracy score:
0.9
precision recall f1-score support
0 1.00 1.00 1.00 10
1 0.88 0.78 0.82 9
2 0.83 0.91 0.87 11
avg / total 0.90 0.90 0.90 30
In detail, 我们还可以利用predict_proba()函数和predict()函数来逐条检视一下Logistic Regression的分类判别结果,请看下面的示例代码:
[python] view plain copy 在CODE上查看代码片派生到我的代码片
logreg_proba = logreg.predict_proba(X_test)
logreg_pred = logreg.predict(X_test)
for index in range (5):
print(logreg_proba[index])
print("Predict label:", logreg_pred[index])
print("Correct label:", y_test[index])
我们仅仅输出了前五个测试用例的分类结果,可见这五个样本的预测结果中前四个都是正确的。
[python] view plain copy 在CODE上查看代码片派生到我的代码片
[ 8.86511110e-26 5.64775369e-01 4.35224631e-01]
Predict label: 1
Correct label: 1
[ 9.99999942e-01 3.78533501e-08 2.02808786e-08]
Predict label: 0
Correct label: 0
[ 9.92889585e-70 8.98623548e-02 9.10137645e-01]
Predict label: 2
Correct label: 2
[ 4.40394856e-21 5.97659713e-01 4.02340287e-01]
Predict label: 1
Correct label: 1
[ 5.68223824e-43 2.90652338e-01 7.09347662e-01]
Predict label: 2
Correct label: 1
当然,Logistic Regression的原理网上已有太多资料进行解释,因此本文的重点显然并不在于此。但是如果你对该算法的原理比较熟悉,自己实现其中的某些函数也是完全可以的。下面的代码就演示了笔者自行实现的predict_proba()函数和predict()函数,如果你对此感兴趣也不妨试试看。
[python] view plain copy 在CODE上查看代码片派生到我的代码片
class MyLogisticRegression:
def __init__(self, weights, constants, labels):
self.weights = weights
self.constants = constants
self.labels = labels
def predict_proba(self,X):
proba_list = []
len_label = len(self.labels)
for n in X: #.toarray():
pb = []
count = 0
for i in range(len_label):
value = npy.exp(npy.dot(n, self.weights[i]) + self.constants[i])
count = count + value
pb.append(value)
proba_list.append([x/count for x in pb])
return npy.asarray(proba_list)
def predict(self,X):
proba_list = self.predict_proba(X)
predicts = []
for n in proba_list.tolist():
i = n.index(max(n))
predicts.append(self.labels[i])
return npy.asarray(predicts)
与之前的执行类似,但是这次换成我们自己编写的函数
[python] view plain copy 在CODE上查看代码片派生到我的代码片
# Print the result based on my functions
print('\n')
my_logreg = MyLogisticRegression(logreg.coef_, logreg.intercept_, logreg.classes_)
my_logreg_proba = my_logreg.predict_proba(X_test)
my_logreg_pred = my_logreg.predict(X_test)
for index in range (5):
print(my_logreg_proba[index])
print("Predict label:",logreg_pred[index])
print("Correct label:", y_test[index])
最后让我们来对比一下执行结果,可见我们自己实现的函数与直接调用Scikit-Learn中函数所得之结果是完全相同的。
[python] view plain copy 在CODE上查看代码片派生到我的代码片
[ 8.86511110e-26 5.64775369e-01 4.35224631e-01]
Predict label: 1
Correct label: 1
[ 9.99999942e-01 3.78533501e-08 2.02808786e-08]
Predict label: 0
Correct label: 0
[ 9.92889585e-70 8.98623548e-02 9.10137645e-01]
Predict label: 2
Correct label: 2
[ 4.40394856e-21 5.97659713e-01 4.02340287e-01]
Predict label: 1
Correct label: 1
[ 5.68223824e-43 2.90652338e-01 7.09347662e-01]
Predict label: 2
Correct label: 1
最后需要补充说明的内容是,在我们自己编写的函数中存在这一句
[python] view plain copy 在CODE上查看代码片派生到我的代码片
for n in X: #.toarray():
请注意我们注释掉的内容,在本篇文章中,我们所使用的数据集属于是标准数据集,并不需要我们做Feature extraction。但是在另外一些时候,例如进行自然语言处理时,我们往往要将特征字典转换成一个大的稀疏矩阵,这时我们再编写上面的函数时就要使用下面这句来将稀疏矩阵逐行还原
[python] view plain copy 在CODE上查看代码片派生到我的代码片
for n in X.toarray():
数据分析咨询请扫描二维码
若不方便扫码,搜微信号:CDAshujufenxi
在神经网络模型搭建中,“最后一层是否添加激活函数”是新手常困惑的关键问题——有人照搬中间层的ReLU激活,导致回归任务输出异 ...
2025-12-05在机器学习落地过程中,“模型准确率高但不可解释”“面对数据噪声就失效”是两大核心痛点——金融风控模型若无法解释决策依据, ...
2025-12-05在CDA(Certified Data Analyst)数据分析师的能力模型中,“指标计算”是基础技能,而“指标体系搭建”则是区分新手与资深分析 ...
2025-12-05在回归分析的结果解读中,R方(决定系数)是衡量模型拟合效果的核心指标——它代表因变量的变异中能被自变量解释的比例,取值通 ...
2025-12-04在城市规划、物流配送、文旅分析等场景中,经纬度热力图是解读空间数据的核心工具——它能将零散的GPS坐标(如外卖订单地址、景 ...
2025-12-04在CDA(Certified Data Analyst)数据分析师的指标体系中,“通用指标”与“场景指标”并非相互割裂的两个部分,而是支撑业务分 ...
2025-12-04每到“双十一”,电商平台的销售额会迎来爆发式增长;每逢冬季,北方的天然气消耗量会显著上升;每月的10号左右,工资发放会带动 ...
2025-12-03随着数字化转型的深入,企业面临的数据量呈指数级增长——电商的用户行为日志、物联网的传感器数据、社交平台的图文视频等,这些 ...
2025-12-03在CDA(Certified Data Analyst)数据分析师的工作体系中,“指标”是贯穿始终的核心载体——从“销售额环比增长15%”的业务结论 ...
2025-12-03在神经网络训练中,损失函数的数值变化常被视为模型训练效果的“核心仪表盘”——初学者盯着屏幕上不断下降的损失值满心欢喜,却 ...
2025-12-02在CDA(Certified Data Analyst)数据分析师的日常工作中,“用部分数据推断整体情况”是高频需求——从10万条订单样本中判断全 ...
2025-12-02在数据预处理的纲量统一环节,标准化是消除量纲影响的核心手段——它将不同量级的特征(如“用户年龄”“消费金额”)转化为同一 ...
2025-12-02在数据驱动决策成为企业核心竞争力的今天,A/B测试已从“可选优化工具”升级为“必选验证体系”。它通过控制变量法构建“平行实 ...
2025-12-01在时间序列预测任务中,LSTM(长短期记忆网络)凭借对时序依赖关系的捕捉能力成为主流模型。但很多开发者在实操中会遇到困惑:用 ...
2025-12-01引言:数据时代的“透视镜”与“掘金者” 在数字经济浪潮下,数据已成为企业决策的核心资产,而CDA数据分析师正是挖掘数据价值的 ...
2025-12-01数据分析师的日常,常始于一堆“毫无章法”的数据点:电商后台导出的零散订单记录、APP埋点收集的无序用户行为日志、传感器实时 ...
2025-11-28在MySQL数据库运维中,“query end”是查询执行生命周期的收尾阶段,理论上耗时极短——主要完成结果集封装、资源释放、事务状态 ...
2025-11-28在CDA(Certified Data Analyst)数据分析师的工具包中,透视分析方法是处理表结构数据的“瑞士军刀”——无需复杂代码,仅通过 ...
2025-11-28在统计分析中,数据的分布形态是决定“用什么方法分析、信什么结果”的底层逻辑——它如同数据的“性格”,直接影响着描述统计的 ...
2025-11-27在电商订单查询、用户信息导出等业务场景中,技术人员常面临一个选择:是一次性查询500条数据,还是分5次每次查询100条?这个问 ...
2025-11-27