数学建模社区-数学中国
标题:
Logistic回归--实例
[打印本页]
作者:
2744557306
时间:
2023-11-30 17:30
标题:
Logistic回归--实例
2023-11-30 17:26 上传
下载附件
(79.88 KB)
"""
; Z0 |4 R- m' p3 Z' m! L
函数说明:梯度上升算法测试函数
0 u( d; V! }5 |) D7 u+ C
- U6 B: T/ W6 v- L# c& G0 L
求函数f(x) = -x^2 + 4x的极大值
( D9 e `. V- L- L0 [$ x3 r& c2 m( V
, K6 j! n" F3 y- X
Parameters:
( D2 p" D; [# r
无
' |) E! S3 E* V. C9 ^
Returns:
1 Y4 L4 I6 a/ E% Y* o
无
G1 S8 q* B& i4 @
"""
: c& J) _9 ]+ ]" g, s; L3 Z9 {
def Gradient_Ascent_test():
/ E# R+ X4 g, Q
def f_prime(x_old): #f(x)的导数
6 H9 p& d- M, d7 k$ v7 H
return -2 * x_old + 4
. X' |6 E1 J3 \. h. b, r1 H4 Z
x_old = -1 #初始值,给一个小于x_new的值
9 T Z1 b" ?/ C4 C& n( J
x_new = 0 #梯度上升算法初始值,即从(0,0)开始
* q! S" V3 R' y$ U
alpha = 0.01 #步长,也就是学习速率,控制更新的幅度
8 ^( v! r$ z K# E3 N* n0 X( D' }
presision = 0.00000001 #精度,也就是更新阈值
4 x' o! j: @+ s% t) i; J7 h' t
while abs(x_new - x_old) > presision:
( |( q! C- @8 L2 z% Q7 A" a' H
x_old = x_new
& q/ X) m" V' f) s) q
x_new = x_old + alpha * f_prime(x_old) #上面提到的公式
+ b# m7 d5 ^% d4 e9 Y
print(x_new) #打印最终求解的极值近似值
8 W3 ^* n/ w- P _7 V- i
: [2 p0 Q3 s- Y$ ?& f+ a0 U& l
if __name__ == '__main__':
1 Y; ]* }8 x# u4 |& O
Gradient_Ascent_test()
0 V& y5 b4 U: T7 m
复制代码
运行实例:
1.999999515279857
2 u5 ~* M1 ^" G1 U! }8 J
复制代码
案例
数据集下载:
https://github.com/Jack-Cherish/Machine-Learning/blob/master/Logistic/testSet.txt
-0.017612 14.053064 0
5 ` v; s Y" a1 [
-1.395634 4.662541 1
% z; p) ~# A" V* \# @9 C; W0 \" A
-0.752157 6.538620 0
1 d/ K' ^/ `* S+ W, M9 E
-1.322371 7.152853 0
- }. Q+ u* u* {
0.423363 11.054677 0
8 N3 V0 B8 K: q: C
0.406704 7.067335 1
% E1 h; H* l% k( W/ Q& |
0.667394 12.741452 0
; ^- Z- y* F( m, t( j+ _
-2.460150 6.866805 1
) B9 _8 @4 M$ P
0.569411 9.548755 0
/ G! z( J3 X( _* G: q ?
-0.026632 10.427743 0
) E7 c8 C$ m5 b) T0 k# S
复制代码
这个数据有两维特征,因此可以将数据在一个二维平面上展示出来。我们可以将第一列数据(X1)看作x轴上的值,第二列数据(X2)看作y轴上的值。而最后一列数据即为分类标签。根据标签的不同,对这些点进行分类。
import matplotlib.pyplot as plt
; u- O/ _4 A& I0 m" M
import numpy as np
9 c$ D, l8 K6 @; J# F E( w
! {( K; P6 [$ F9 L
"""
" M& r+ B5 S6 M, |/ f! e6 ^0 Y: Q
函数说明:加载数据
5 q. I) S7 ^3 b/ _* @! m6 d3 U6 J# W C
% [0 F$ `. ~; ]9 h
Parameters:
' H W* i! s+ ^6 W: o1 s7 ^& A3 r
无
* V P8 h* J5 p6 G' l- e* F7 ?
Returns:
2 R! Y( O# F; Y8 F8 x6 ^
dataMat - 数据列表
2 q4 J. r. m& ^ q/ U* ~
labelMat - 标签列表
; L7 @9 J" o+ d( j4 x, g$ U9 ~
"""
! |! _2 ?" u; }+ o1 ]
def loadDataSet():
G* p7 X9 k$ A. u6 n
dataMat = [] #创建数据列表
9 V% S/ N9 p ?5 ? j) U# l
labelMat = [] #创建标签列表
n7 J, f9 `8 ]( n/ p; X
fr = open('testSet.txt') #打开文件
8 X+ I( j* ` m- ^4 |; J; l8 \9 _
for line in fr.readlines(): #逐行读取
+ [0 @% T3 e% z: M! C6 r) P* z( c6 r
lineArr = line.strip().split() #去回车,放入列表
& v: y) J, y6 l3 B
dataMat.append([1.0, float(lineArr[0]), float(lineArr[1])]) #添加数据
& Q6 I8 \0 k" j& j* H2 J
labelMat.append(int(lineArr[2])) #添加标签
# M% G3 \9 }+ n# R( Z5 |
fr.close() #关闭文件
8 J/ w( ~( I# o, d( X) H: c+ C& k$ ?
return dataMat, labelMat #返回
# |9 \6 \. F( }6 @; G8 W3 v/ ]- n
% [ J- S* l" ^: m
"""
6 s: l4 `! ]/ }% V" w
函数说明:绘制数据集
$ e7 [8 B) |0 [' J( J
' a4 D9 G' _* R4 [& w: N9 _, i& D
Parameters:
/ V. j# P- F, z' `3 G3 C
无
6 d% `6 L l/ k8 X
Returns:
4 F. l+ G, ]3 Z6 K3 K/ S& _
无
2 D6 p( D4 @; o2 u& f$ w
"""
$ w# w+ r1 P9 G; v
def plotDataSet():
( C" g5 \# H' x* u8 ]1 O% @
dataMat, labelMat = loadDataSet() #加载数据集
3 {1 v9 H5 W" K
dataArr = np.array(dataMat) #转换成numpy的array数组
& N4 H' `) A" Z/ u2 f
n = np.shape(dataMat)[0] #数据个数
! F. M& x2 _$ c9 h" {, M
xcord1 = []; ycord1 = [] #正样本
" p& R1 w3 ?8 B, k8 z+ k7 |2 Z+ v
xcord2 = []; ycord2 = [] #负样本
8 W! Y' G) i5 q/ S# c6 e' [' X
for i in range(n): #根据数据集标签进行分类
$ \' @0 [, N1 l& w& d
if int(labelMat[i]) == 1:
( M# ?0 X9 X, d# o) N% G1 }
xcord1.append(dataArr[i,1]); ycord1.append(dataArr[i,2]) #1为正样本
3 g5 J$ N* A% P ]- O4 n( f
else:
9 E0 }9 L, _- h& v, d Q" y
xcord2.append(dataArr[i,1]); ycord2.append(dataArr[i,2]) #0为负样本
$ I; j- Q* L8 W! O1 `8 s
fig = plt.figure()
* S' O: o ^" w8 Y
ax = fig.add_subplot(111) #添加subplot
& @: L. \5 O* s. N( ^4 C
ax.scatter(xcord1, ycord1, s = 20, c = 'red', marker = 's',alpha=.5)#绘制正样本
3 s7 h3 m/ N' Z( i' o" l6 J
ax.scatter(xcord2, ycord2, s = 20, c = 'green',alpha=.5) #绘制负样本
$ U, q+ j$ B- i/ C) U# ^, P
plt.title('DataSet') #绘制title
0 X2 v" U/ f$ T: c
plt.xlabel('x'); plt.ylabel('y') #绘制label
8 ~3 n" @2 m e8 ~
plt.show() #显示
" d5 D. @; p6 u8 \$ i
4 B" M+ h) k# w1 E" E) t! L
if __name__ == '__main__':
* @& ?- M/ p6 B" R, \
plotDataSet()
' n8 J/ f, o; G$ Q6 L: z
复制代码
2023-11-30 17:29 上传
下载附件
(43.58 KB)
& q0 U; x$ k6 _- j# b+ v
从上图可以看出数据的分布情况。假设Sigmoid函数的输入记为z,那么z=w0x0 + w1x1 + w2x2,即可将数据分割开。其中,x0为全是1的向量,x1为数据集的第一列数据,x2为数据集的第二列数据。另z=0,则0=w0 + w1x1 + w2x2。横坐标为x1,纵坐标为x2。这个方程未知的参数为w0,w1,w2,也就是我们需要求的回归系数(最优参数)。
import numpy as np
( ?2 }0 C6 N# B5 `8 H
; X5 i( b( U: p1 N! _9 e
"""
$ N' M# P8 B6 \4 T% u. _: w
函数说明:加载数据
5 F6 l z1 D" h- S$ X( l
* s$ ^" l2 r* _
Parameters:
1 U$ d: g3 Y" F" g5 O
无
3 {( C. \1 `; Z2 O8 Y
Returns:
6 U& ^8 G- I$ H& o! R) L- ~
dataMat - 数据列表
3 L. I1 n d, r% U1 ]2 x0 G
labelMat - 标签列表
0 }; {. T% L/ e
"""
2 }8 v2 l% E/ C( l# j r9 C2 ~( m
def loadDataSet():
8 m, p5 @6 g2 p
dataMat = [] #创建数据列表
" t( C3 z5 j) Z6 q3 ]% k; D9 U
labelMat = [] #创建标签列表
# O; X0 n+ V3 g7 H7 [
fr = open('testSet.txt') #打开文件
3 ?( S6 Q( O) i e( Y
for line in fr.readlines(): #逐行读取
. `% k3 q6 V2 w) O L
lineArr = line.strip().split() #去回车,放入列表
4 U8 @1 ^% A7 l8 |& ^
dataMat.append([1.0, float(lineArr[0]), float(lineArr[1])]) #添加数据
; w; z3 M; M' y5 u: `( N/ W% {
labelMat.append(int(lineArr[2])) #添加标签
3 x% M8 W; {7 Z/ K; F$ G
fr.close() #关闭文件
# {+ \: R D+ r6 s4 k! Q6 c: j
return dataMat, labelMat #返回
5 n7 u7 I# s! O' c
4 W% \" Q+ S) t- B- o3 d$ V9 T) _
"""
& {. M5 c3 i5 m# T
函数说明:sigmoid函数
* Q# I, }7 ]# Y% P4 M3 N4 s
/ r: ]) Q- F! b. R4 G$ Y# \% Q, B
Parameters:
* `0 x: I I; @. x
inX - 数据
& @" z% n# X$ l2 _' J
Returns:
5 c+ ?3 G: G% N7 a2 x( i0 n
sigmoid函数
. q& k4 t: \, \2 s$ L
"""
8 C# b- t/ U& _8 Q* W
def sigmoid(inX):
6 H1 c1 ~* x% t. [, t) H
return 1.0 / (1 + np.exp(-inX))
, J6 U h/ R5 B- n. B& A6 _( |) Z7 E
# X- }% B. C$ w2 ?9 u
! z* L8 l7 s) ^( ~, X. J) O
"""
# G' N( u4 X" {8 h9 f2 T, O
函数说明:梯度上升算法
4 g( I$ X# D0 j" w* F y7 h
3 {: d2 c6 ~1 c! L: B; T/ l
Parameters:
S4 ~7 G& R5 j$ c, u
dataMatIn - 数据集
3 Q% v: g. V/ {7 }# u- n$ @
classLabels - 数据标签
& {% s/ c4 [% |/ w8 _
Returns:
9 u+ V& K* I& z. l6 L( w; y* x
weights.getA() - 求得的权重数组(最优参数)
; w9 R6 q7 c, K$ h1 R" I
"""
9 n; ?9 s9 U5 m! u7 e( _
def gradAscent(dataMatIn, classLabels):
& F, U: } C' y) t% W; M
dataMatrix = np.mat(dataMatIn) #转换成numpy的mat
1 [7 b% C( a) w
labelMat = np.mat(classLabels).transpose() #转换成numpy的mat,并进行转置
7 h) Q6 {7 S- [. R! q0 a- ?. d: a/ b
m, n = np.shape(dataMatrix) #返回dataMatrix的大小。m为行数,n为列数。
+ W3 ^7 g7 m9 [! k; w r
alpha = 0.001 #移动步长,也就是学习速率,控制更新的幅度。
- f) o2 C3 ^, G3 k4 n! G8 L
maxCycles = 500 #最大迭代次数
* ]! z. O' D& k5 M3 F* g
weights = np.ones((n,1))
' ]" i9 W; Z3 X: D+ {1 z
for k in range(maxCycles):
1 \" Y; s7 C. ^) K
h = sigmoid(dataMatrix * weights) #梯度上升矢量化公式
+ [9 x9 u) o1 Z/ c
error = labelMat - h
3 q7 g6 B! k1 e& k
weights = weights + alpha * dataMatrix.transpose() * error
" [1 a( v+ S4 N! {2 E+ ]9 |6 n
return weights.getA() #将矩阵转换为数组,返回权重数组
( M3 d4 H) k8 n" I$ ~, G
4 m! O0 o) z, S* X9 s0 {
if __name__ == '__main__':
# `% P, `6 q2 T
dataMat, labelMat = loadDataSet()
0 H2 [ W% h5 f0 g
print(gradAscent(dataMat, labelMat))
0 v3 N- h/ c$ d" X
复制代码
运行结果
[[ 4.12414349]
; ?) W: f+ x" f
[ 0.48007329]
: r, v8 U) Z" M1 V
[-0.6168482 ]]
" R6 K! n, x4 p: C6 j( @
复制代码
9 o5 {- m- v. ]7 d3 q( `, j
欢迎光临 数学建模社区-数学中国 (http://www.madio.net/)
Powered by Discuz! X2.5