机器学习--逻辑回归

机器学习–逻辑回归


一、认知革命:从线性回归到逻辑回归

1.1 本质差异对比

维度线性回归逻辑回归
输出类型连续值概率值 (0-1)
目标函数最小二乘法极大似然估计
数学表达式 y = w T x + b y=w^Tx+b y=wTx+b p = 1 1 + e − ( w T x + b ) p=\frac{1}{1+e^{-(w^Tx+b)}} p=1+e(wTx+b)1
应用场景房价预测信用评分、疾病诊断

1.2 Sigmoid函数的数学推导

# Sigmoid函数特性验证
def sigmoid(z):return 1 / (1 + np.exp(-z))print("输入10时概率:", sigmoid(10))  # 输出0.99995
print("输入-10时概率:", sigmoid(-10)) # 输出0.000045

1.3 逻辑回归

逻辑回归需要提前设定一个阈值p,用来控制分类界限,

二、判断客户是否患病

其中提供了众多参数如:

  • age:年龄。
  • sex:性别。
  • cp:胸痛类型。
  • trestbps:休息时血压。

去判断是否患病,这就变成了一个分类问题

或者去判断一个人是否考试通过

image-20250217141526316

image-20250217141511499

三、损失函数

线性回归

对于线性回归的损失函数
L ( w , b ) = 1 N ∑ ( x , y ) ∈ D L o s s ( h ( x ) , y ) = 1 N ∑ ( x , y ) ∈ D L o s s ( y ′ , y ) L(w,b)=\frac{1}{N}\sum_{(x,y)\in D}Loss(h(x),y)=\frac{1}{N}\sum_{(x,y)\in D}Loss(y^{\prime},y) L(w,b)=N1(x,y)DLoss(h(x),y)=N1(x,y)DLoss(y,y)

e ˉ = 1 n ∑ i = 1 n ( w x i − y i ) 2 \bar{e}=\frac{1}{n}\sum_{i=1}^n(wx_i-y_i)^2 eˉ=n1i=1n(wxiyi)2

e ˉ = 1 n ∑ i = 1 n x i 2 w 2 − 2 1 n ∑ i = 1 n x i y i w + 1 n ∑ i = 1 n y i 2 \bar{e}=\frac{1}{n}\sum_{i=1}^nx_i^2w^2-2\frac{1}{n}\sum_{i=1}^nx_iy_iw+\frac{1}{n}\sum_{i=1}^ny_i^2 eˉ=n1i=1nxi2w22n1i=1nxiyiw+n1i=1nyi2

e ˉ = a w 2 + b w + c \bar{e}=aw^2+bw+c eˉ=aw2+bw+c

这可以把e当作一个二次函数,可以求最小值,其对于w的梯度可以最为梯度下降中的步长,但是对于逻辑回归,采用此方法可能无法到达最底端。

image-20250217145624371

逻辑回归

{ y = 1 , L o s s ( h ( x ) , y ) = − log ⁡ ( h ( x ) ) y = 0 , L o s s ( h ( x ) , y ) = − log ⁡ ( 1 − h ( x ) ) \begin{cases}y=1,Loss(h(x),y)=-\log(h(x))\\y=0,Loss(h(x),y)=-\log(1-h(x))&\end{cases} {y=1,Loss(h(x),y)=log(h(x))y=0,Loss(h(x),y)=log(1h(x))

image-20250217145926005

  • 如果真值是1,假设函数预测概率接近于0,损失值是巨大的。
  • 如果真值是0,假设函数预测概率接近于1,损失值是巨大的。

如果将两种情况归为一类,即可获得以下算式:
l o s s = y ∗ l o g ( h ( x ) ) + ( 1 − y ) ∗ l o g ( 1 − h ( x ) ) loss=y^{*}\mathrm{log}(h(x))+(1-y)^{*}\mathrm{log}(1-h(x)) loss=ylog(h(x))+(1y)log(1h(x))
我们设定损失函数为:
L ( w , b ) = − 1 N ∑ ( x , y ) ∈ D [ y ∗ l o g ( h ( x ) ) + ( 1 − y ) ∗ l o g ( 1 − h ( x ) ) ] L(w,b)=-\frac{1}{N}\sum_{(x,y)\in D}[y^*\mathrm{log}(h(x))+(1-y)^*\mathrm{log}(1-h(x))] L(w,b)=N1(x,y)D[ylog(h(x))+(1y)log(1h(x))]

四、梯度下降

梯度 = h ′ ( x ) = ∂ ∂ w L ( w , b ) = ∂ ∂ w { − 1 N ∑ ( x , y ) ∈ D [ y ∗ log ⁡ ( h ( x ) ) + ( 1 − y ) ∗ log ⁡ ( 1 − h ( x ) ) ] } \text{梯度}=h^{\prime}(x)=\frac{\partial}{\partial w}L(w,b)=\frac{\partial}{\partial w}\left\{-\frac{1}{N}\sum_{(x,y)\in D}[y*\log(h(x))+(1-y)*\log(1-h(x))]\right\} 梯度=h(x)=wL(w,b)=w N1(x,y)D[ylog(h(x))+(1y)log(1h(x))]

步骤1:明确损失函数形式(交叉熵损失)

L ( w , b ) = − 1 N ∑ i = 1 N [ y ( i ) log ⁡ ( h ( i ) ) + ( 1 − y ( i ) ) log ⁡ ( 1 − h ( i ) ) ] L(w,b) = -\frac{1}{N}\sum_{i=1}^N \left[ y^{(i)} \log(h^{(i)}) + (1-y^{(i)})\log(1-h^{(i)}) \right] L(w,b)=N1i=1N[y(i)log(h(i))+(1y(i))log(1h(i))]

步骤2:拆解单样本损失分量(以第i个样本为例)

单样本损失 = − [ y log ⁡ ( h ) + ( 1 − y ) log ⁡ ( 1 − h ) ] \text{单样本损失} = -\left[ y \log(h) + (1-y)\log(1-h) \right] 单样本损失=[ylog(h)+(1y)log(1h)]

步骤3:对参数w求导的核心运算

∂ ∂ w 单样本损失 = ∂ ∂ h ( − [ y log ⁡ ( h ) + ( 1 − y ) log ⁡ ( 1 − h ) ] ) ⋅ ∂ h ∂ w \frac{\partial}{\partial w} \text{单样本损失} = \frac{\partial}{\partial h}\left(-\left[y\log(h)+(1-y)\log(1-h)\right]\right) \cdot \frac{\partial h}{\partial w} w单样本损失=h([ylog(h)+(1y)log(1h)])wh

分项求导运算结果:

a项导: ∂ ∂ h [ − y log ⁡ ( h ) ] = − y h b项导: ∂ ∂ h [ − ( 1 − y ) log ⁡ ( 1 − h ) ] = 1 − y 1 − h \begin{aligned} &\text{a项导}:\frac{\partial}{\partial h}[-y \log(h)] = -\frac{y}{h} \\ &\text{b项导}:\frac{\partial}{\partial h}[-(1-y)\log(1-h)] = \frac{1-y}{1-h} \end{aligned} a项导h[ylog(h)]=hyb项导h[(1y)log(1h)]=1h1y

合并结果:

∂ ∂ h = 1 − y 1 − h − y h \frac{\partial}{\partial h} = \frac{1-y}{1-h} - \frac{y}{h} h=1h1yhy

步骤4:Sigmoid函数导数计算(链式法则核心步骤)

h = σ ( w T x + b ) = 1 1 + e − ( w T x + b ) ∂ h ∂ w = h ( 1 − h ) x (Sigmoid函数的优雅性质) \begin{aligned} h &= \sigma(w^Tx + b) = \frac{1}{1+e^{-(w^Tx + b)}} \\ \frac{\partial h}{\partial w} &= h(1-h)x \quad \text{(Sigmoid函数的优雅性质)} \end{aligned} hwh=σ(wTx+b)=1+e(wTx+b)1=h(1h)xSigmoid函数的优雅性质)

步骤5:梯度分量组合与化简(见证数学之美)

梯度分量 = ( 1 − y 1 − h − y h ) ⋅ h ( 1 − h ) x = [ ( 1 − y ) h − y ( 1 − h ) ] x = ( h − y ) x (所有复杂项神奇抵消!) \begin{aligned} \text{梯度分量} &= \left( \frac{1-y}{1-h} - \frac{y}{h} \right) \cdot h(1-h)x \\ &= \left[ (1-y)h - y(1-h) \right]x \\ &= (h - y)x \quad \text{(所有复杂项神奇抵消!)} \end{aligned} 梯度分量=(1h1yhy)h(1h)x=[(1y)hy(1h)]x=(hy)x(所有复杂项神奇抵消!)

步骤6:整合全局梯度(全体样本协同计算)

∂ L ∂ w = 1 N ∑ i = 1 N ( h ( i ) − y ( i ) ) x ( i ) \frac{\partial L}{\partial w} = \frac{1}{N}\sum_{i=1}^N (h^{(i)} - y^{(i)})x^{(i)} wL=N1i=1N(h(i)y(i))x(i)

重要性质总结表

性质数学表达式物理意义
梯度公式 ∂ L ∂ w = 1 N ∑ ( h − y ) x \frac{\partial L}{\partial w} = \frac{1}{N}\sum (h-y)x wL=N1(hy)x预测误差驱动物体参数调整
Sigmoid导数 d σ ( z ) d z = σ ( z ) ( 1 − σ ( z ) ) \frac{d\sigma(z)}{dz} = \sigma(z)(1-\sigma(z)) dzdσ(z)=σ(z)(1σ(z))自动生成正则化效果
概率计算 P ( y = 1 ∣ x ) = 1 1 + e − w T x P(y=1|x) = \frac{1}{1+e^{-w^Tx}} P(y=1∣x)=1+ewTx1完美映射到[0,1]概率空间

省略大量微分细节,可得:
梯度 = 1 N ∑ i = 1 N ( y ( i ) − h ( x ( i ) ) ) ∙ x ( i ) \text{梯度}=\frac{1}{N}\sum_{i=1}^N(y^{(i)}-h(x^{(i)}))\bullet x^{(i)} 梯度=N1i=1N(y(i)h(x(i)))x(i)
所以加入更新的速率以后可得:
w = w − α ⋅ ∂ ∂ w L ( w ) w=w-\alpha\cdot\frac{\partial}{\partial w}L(w) w=wαwL(w)

w = w − α N ∑ i = 1 N ( y ( i ) − ( w ∙ x ( i ) ) ) ∙ x ( i ) w=w-\frac{\alpha}{N}\sum_{i=1}^N(y^{(i)}-(w\bullet x^{(i)}))\bullet x^{(i)} w=wNαi=1N(y(i)(wx(i)))x(i)

五、通过逻辑回归解决二元分类问题

5.1数据准备

5.1.1 数据读取
import numpy as np # 导入NumPy数学工具箱
import pandas as pd # 导入Pandas数据处理工具箱
df_heart = pd.read_csv("/kaggle/input/logistic-regression/heart.csv")  # 读取文件
df_heart.head() # 显示前5行数据
df_heart.target.value_counts() # 输出分类值,及各个类别数目
import matplotlib.pyplot as plt # 导入绘图工具
# 以年龄+最大心率作为输入,查看分类结果散点图
plt.scatter(x=df_heart.age[df_heart.target==1],y=df_heart.thalach[(df_heart.target==1)], c="red")
plt.scatter(x=df_heart.age[df_heart.target==0],y=df_heart.thalach[(df_heart.target==0)], marker='^')
plt.legend(["Disease", "No Disease"]) # 显示图例
plt.xlabel("Age") # X轴-Age
plt.ylabel("Heart Rate") # Y轴-Heart Rate
plt.show() # 显示散点图

image-20250217162800659

5.1.2 构建特征集和标签集
X = df_heart.drop(['target'], axis = 1) # 构建特征集
y = df_heart.target.values # 构建标签集
y = y.reshape(-1,1) # -1是	相对索引,等价于len(y)
print("张量X的形状:", X.shape)
print("张量X的形状:", y.shape)
5.1.3 拆分数据集

按照80%/20%的比例准备训练集和测试集:

from sklearn.model_selection import train_test_split
X_train, X_test, y_train, y_test = train_test_split(X,y,test_size = 0.2)
5.1.4 数据特征缩放
from sklearn.preprocessing import MinMaxScaler # 导入数据缩放器
scaler = MinMaxScaler() # 选择归一化数据缩放器,MinMaxScaler
X_train = scaler.fit_transform(X_train) # 特征归一化 训练集fit_transform
X_test = scaler.transform(X_test) # 特征归一化 测试集transform

仅就这个数据集而言,Min Max Scaler进行的数据特征缩放不仅不会提高效率,似乎还会令预测准确率下降。

这个结果提示我们:没有绝对正确的理论,实践才是检验真理的唯一标准。

5.2 建立逻辑回归模型

5.1.1 逻辑函数
# 首先定义一个Sigmoid函数,输入Z,返回y'
def sigmoid(z):    y_hat = 1/(1+ np.exp(-z))return y_hat    
5.1.2 损失函数
# 然后定义损失函数
def loss_function(X,y,w,b):y_hat = sigmoid(np.dot(X,w) + b) # Sigmoid逻辑函数 + 线性函数(wX+b)得到y'loss = -(y*np.log(y_hat) + (1-y)*np.log(1-y_hat)) # 计算损失cost = np.sum(loss) / X.shape[0]  # 整个数据集平均损失    return cost # 返回整个数据集平均损失

L ( w , b ) = − 1 N ∑ ( x , y ) ∈ D [ y ∗ l o g ( h ( x ) ) + ( 1 − y ) ∗ l o g ( 1 − h ( x ) ) ] L(w,b)=-\frac{1}{N}\sum_{(x,y)\in D}\left[y^*\mathrm{log}(h(x))+(1-y)^*\mathrm{log}(1-h(x))\right] L(w,b)=N1(x,y)D[ylog(h(x))+(1y)log(1h(x))]

5.2.3 梯度下降的实现
# 然后构建梯度下降的函数
def gradient_descent(X,y,w,b,lr,iter) : #定义逻辑回归梯度下降函数l_history = np.zeros(iter) # 初始化记录梯度下降过程中误差值(损失)的数组w_history = np.zeros((iter,w.shape[0],w.shape[1])) # 初始化权重记录的数组b_history = np.zeros(iter) # 初始化记录梯度下降过程中偏置的数组  for i in range(iter): #进行机器训练的迭代y_hat = sigmoid(np.dot(X,w) + b) #Sigmoid逻辑函数+线性函数(wX+b)得到y'derivative_w = np.dot(X.T,((y_hat-y)))/X.shape[0]  # 给权重向量求导derivative_b = np.sum(y_hat-y)/X.shape[0] # 给偏置求导w = w - lr * derivative_w # 更新权重向量,lr即学习速率alphab = b - lr * derivative_b   # 更新偏置,lr即学习速率alphal_history[i] =  loss_function(X,y,w,b) # 梯度下降过程中的损失print ("轮次", i+1 , "当前轮训练集损失:",l_history[i]) w_history[i] = w # 梯度下降过程中权重的历史 请注意w_history和w的形状b_history[i] = b # 梯度下降过程中偏置的历史return l_history, w_history, b_history

梯度 = 1 N ∑ i = 1 N ( y ( i ) − h ( x ( i ) ) ) ∙ x ( i ) \text{梯度}=\frac{1}{N}\sum_{i=1}^N(y^{(i)}-h(x^{(i)}))\bullet x^{(i)} 梯度=N1i=1N(y(i)h(x(i)))x(i)

w = w − α ⋅ ∂ ∂ w L ( w ) w=w-\alpha\cdot\frac{\partial}{\partial w}L(w) w=wαwL(w)

5.2.4 分类预测的实现

定义一个负责分类预测的函数:

def predict(X,w,b): # 定义预测函数z = np.dot(X,w) + b # 线性函数y_hat = sigmoid(z) # 逻辑函数转换y_pred = np.zeros((y_hat.shape[0],1)) # 初始化预测结果变量  for i in range(y_hat.shape[0]):if y_hat[i,0] < 0.5:y_pred[i,0] = 0 # 如果预测概率小于0.5,输出分类0else:y_pred[i,0] = 1 # 如果预测概率大于0.5,输出分类1return y_pred # 返回预测分类的结果

5.3 开始训练机器

def logistic_regression(X,y,w,b,lr,iter): # 定义逻辑回归模型l_history,w_history,b_history = gradient_descent(X,y,w,b,lr,iter)#梯度下降print("训练最终损失:", l_history[-1]) # 打印最终损失y_pred = predict(X,w_history[-1],b_history[-1]) # 进行预测traning_acc = 100 - np.mean(np.abs(y_pred - y_train))*100 # 计算准确率print("逻辑回归训练准确率: {:.2f}%".format(traning_acc))  # 打印准确率return l_history, w_history, b_history # 返回训练历史记录
#初始化参数
dimension = X.shape[1] # 这里的维度 len(X)是矩阵的行的数,维度是列的数目
weight = np.full((dimension,1),0.1) # 权重向量,向量一般是1D,但这里实际上创建了2D张量
bias = 0 # 偏置值
#初始化超参数
alpha = 1 # 学习速率
iterations = 500 # 迭代次数
# 用逻辑回归函数训练机器
loss_history, weight_history, bias_history =  \logistic_regression(X_train,y_train,weight,bias,alpha,iterations)
y_pred = predict(X_test,weight_history[-1],bias_history[-1]) # 预测测试集
testing_acc = 100 - np.mean(np.abs(y_pred - y_test))*100 # 计算准确率
print("逻辑回归测试准确率: {:.2f}%".format(testing_acc))
逻辑回归测试准确率: 85.25%

5.4 测试分类结果

print ("逻辑回归预测分类值:",predict(X_test,weight_history[-1],bias_history[-1]))

5.5 绘制损失曲线

loss_history_test = np.zeros(iterations) # 初始化历史损失
for i in range(iterations): #求训练过程中不同参数带来的测试集损失loss_history_test[i] = loss_function(X_test,y_test,weight_history[i],bias_history[i])
index = np.arange(0,iterations,1)
plt.plot(index, loss_history,c='blue',linestyle='solid')
plt.plot(index, loss_history_test,c='red',linestyle='dashed')
plt.legend(["Training Loss", "Test Loss"])
plt.xlabel("Number of Iteration")
plt.ylabel("Cost")
plt.show() # 同时显示显示训练集和测试集损失曲线

image-20250217164703879

在迭代80~100次后,训练集的损失进一步下降,但是测试集的损失并没有跟着下降,反而显示呈上升趋势。

这是明显的过拟合现象。因此迭代应该在80–100结束。

六、工业级代码实现

真正做项目的时候,其实没多少人这么去写代码,大家会直接调用库函数进搞定项目

from sklearn.linear_model import LogisticRegression #导入逻辑回归模型
lr = LogisticRegression() # lr,就代表是逻辑回归模型
lr.fit(X_train,y_train) # fit,就相当于是梯度下降
print("SK-learn逻辑回归测试准确率{:.2f}%".format(lr.score(X_test,y_test)*100))
SK-learn逻辑回归测试准确率85.25%

这个准确率比我们之前的手写代码好很多,这是为什么呢?

6.1哑特征

cp这个字段,它的意义是“胸痛类型”,取值为0、1、2、3。这些分类值,是大小无关的。

但是问题在于,计算机会把它们理解为数值,认为1和2与1和3之间的关系不是并列的,是后者差值比前者要大。

解决的方法,是把这种类别特征拆分成多个哑特征,比如cp有0、1、2、3这4类,就拆分成个4特征,cp_0为一个特征、cp_1为一个特征、cp_2为一个特征、cp_3为一个特征。每一个特征都还原成二元分类,答案是Yes或者No,也就是数值1或0。

# 把3个文本型变量转换为哑变量
a = pd.get_dummies(df_heart['cp'], prefix = "cp")
b = pd.get_dummies(df_heart['thal'], prefix = "thal")
c = pd.get_dummies(df_heart['slope'], prefix = "slope")
# 把哑变量添加进dataframe
frames = [df_heart, a, b, c]
df_heart = pd.concat(frames, axis = 1)
df_heart = df_heart.drop(columns = ['cp', 'thal', 'slope'])
df_heart.head() # 显示新的dataframe

6.2二分类实战:信用卡欺诈检测

import pandas as pd
from sklearn.model_selection import StratifiedKFold# 读取真实工业数据集
df = pd.read_csv('creditcard.csv')
X = df.drop(['Class','Time'], axis=1)
y = df['Class']# 分层抽样保持样本分布
skf = StratifiedKFold(n_splits=5)
for train_index, test_index in skf.split(X, y):X_train, X_test = X.iloc[train_index], X.iloc[test_index]y_train, y_test = y.iloc[train_index], y.iloc[test_index]# 带类别权重的模型
model = LogisticRegression(class_weight={0:1, 1:10}, penalty='l1', solver='saga')
model.fit(X_train, y_train)# 输出特征重要性排序
importance = pd.DataFrame({'feature':X.columns, 'coef':model.coef_[0]})
print(importance.sort_values('coef', ascending=False))

6.3 多分类实战:手写数字识别(MNIST)

from sklearn.datasets import fetch_openml
from sklearn.preprocessing import MinMaxScaler# 加载MNIST数据集
mnist = fetch_openml('mnist_784', version=1)
X, y = mnist["data"], mnist["target"].astype(np.uint8)# 数据标准化
scaler = MinMaxScaler()
X_scaled = scaler.fit_transform(X[:10000]) # 抽样加速训练# OVR多分类策略
model = LogisticRegression(multi_class='ovr', penalty='l2', max_iter=1000)
model.fit(X_scaled, y[:10000])# 显示预测结果样例
plt.figure(figsize=(12,6))
for i in range(10):plt.subplot(2,5,i+1)plt.imshow(X[i].reshape(28,28), cmap='gray')plt.title(f'Pred: {model.predict([X_scaled[i]])[0]}')
plt.tight_layout()
get"].astype(np.uint8)# 数据标准化
scaler = MinMaxScaler()
X_scaled = scaler.fit_transform(X[:10000]) # 抽样加速训练# OVR多分类策略
model = LogisticRegression(multi_class='ovr', penalty='l2', max_iter=1000)
model.fit(X_scaled, y[:10000])# 显示预测结果样例
plt.figure(figsize=(12,6))
for i in range(10):plt.subplot(2,5,i+1)plt.imshow(X[i].reshape(28,28), cmap='gray')plt.title(f'Pred: {model.predict([X_scaled[i]])[0]}')
plt.tight_layout()

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.rhkb.cn/news/19605.html

如若内容造成侵权/违法违规/事实不符,请联系长河编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

s1K 数据集:是一个用于提升语言模型推理能力的高质量数据集。包含 1,000 个问题,每个问题都配有详细的 推理路径 和 答案。

2025-02-07&#xff0c; 由斯坦福大学、华盛顿大学等研究机构创建了 s1K 数据集&#xff0c;该数据集包含 1,000 个精心挑选的问题&#xff0c;并配以推理轨迹和答案&#xff0c;为语言模型推理能力的提升提供了重要的数据基础。 一、研究背景 1. 研究背景 近年来&#xff0c;…

DockerDesktop更改默认的磁盘镜像地存储位置

DockerDesktop更改默认的磁盘镜像地存储位置 文章目录 DockerDesktop更改默认的磁盘镜像地存储位置1. 默认存储位置2. 新建一个目录3. 将磁盘镜像存储位置改为新建的目录下 1. 默认存储位置 2. 新建一个目录 如&#xff1a;D:\DiskImagelocationData 3. 将磁盘镜像存储位置改为…

ASP.NET Core SixLabors.ImageSharp 位图图像创建和下载

从 MVC 控制器内部创建位图图像并将其发送到浏览器&#xff1b;用 C# 编写并与 Linux 和 Windows 服务器兼容。 使用从 ASP.NET MVC 中的控制器下载任何文件类型File。 此示例创建一个位图 (jpeg) 并将其发送到浏览器。它需要 NuGet 包SixLabors.ImageSharp v1.0.4。 另请参…

容联云联络中心AICC:深度整合DeepSeek,业务验证结果公开

容联云重磅推出AICC3.2版本&#xff0c;实现了智能化的升级与外呼效率的突破——深度整合DeepSeek-R1大模型、预测式外呼在数据分析侧的增强、全渠道路由能力、一键多呼效率的强化。 同时&#xff0c;全面接入DeepSeek-R1的容联云 AICC3.2 &#xff0c;目前已与某知名汽车金融企…

链表和list

链表和list ‍ ​ ​ ​ ​ ​ ​ ​ ​ ​ 算法题中的经典操作&#xff1a;用空间代替时间​ ​ ​ ​ 双链表头插顺序&#xff1a; 1.先修改新结点的左右指针 2.然后修改结点y的左指针 3.最后修改哨兵位的右指针 双链表在任意位置&#xff08;p&#xff09;之后插入…

Junit——白盒测试

Java单元测试框架&#xff0c;主要用于测试Java程序中的各个单元。 1.验证代码功能是否符合预期 2.及时 发现修复 代码中的缺陷&#xff0c;提高代码质量 入门 最早学习java&#xff0c;代码对不对&#xff0c;通过main 方法运行&#xff0c;观看结果是否符合预期。 packa…

1.MySQL概述

1.1 数据模型 介绍完了Mysql数据库的安装配置之后&#xff0c;接下来我们再来聊一聊Mysql当中的数据模型。学完了这一小节之后&#xff0c;我们就能够知道在Mysql数据库当中到底是如何来存储和管理数据的。 在介绍 Mysql的数据模型之前&#xff0c;需要先了解一个概念&#x…

Deep seek学习日记1

Deepseek最强大的就是它的深度思考&#xff0c;并且展现了它的思考过程。 五种可使用Deep seek的方式&#xff08;应该不限于这五种&#xff0c;后续嵌入deepseek的应该更多&#xff0c;多了解一点因为官网容易崩~~&#xff09;&#xff1a; 1.deep seek官网 2.硅基流动silicon…

JAVA中的异常

一、简介 1.1 什么是异常 异常&#xff0c;是对程序在运行过程中遇到的种种不正常的情况的描述。异常在java中用Exception类来描述。如果程序遇到了未经处理的异常&#xff0c;将会导致程序无法编译或者无法继续运行。 1.2 异常的继承体系 在java中使用类Throwable来描述所有…

数字水印嵌入及提取系统——基于小波变换GUI

数字水印嵌入及提取系统——基于小波变换GUI 基于小波变换的数字水印系统&#xff08;Matlab代码GUI操作&#xff09; 【有简洁程序报告】【可作開题完整文档达辩PPT】 本系统主要的内容包括&#xff1a; &#xff08;1&#xff09;使用小波变换技术实现二值水印图像的加密、…

Linux_帮助指令

man 获得帮助信息 基本语法: man [命令或配置文件] 在linux下,隐藏文件是以 .开头, 选项可以组合使用, 比如 ls -al, 不如 ls -al /root help 指令 基本语法: help 命令 (功能描述: 获取shell内置命名的帮助信息) 英语不好建议百度

Day4 25/2/17 MON

【一周刷爆LeetCode&#xff0c;算法大神左神&#xff08;左程云&#xff09;耗时100天打造算法与数据结构基础到高级全家桶教程&#xff0c;直击BTAJ等一线大厂必问算法面试题真题详解&#xff08;马士兵&#xff09;】https://www.bilibili.com/video/BV13g41157hK?p4&v…

redis集群模式

1.集群模式 作用&#xff1a;解决单点故障问题 集群的模式&#xff1a;1.主从模式&#xff0c;2、哨兵模式&#xff0c;3、集群化模式 1.1主从模式 特点&#xff1a;1个主节点多个从节点&#xff0c;主节点负责读写操作&#xff0c;而从节点只能负责读操作&#xff0c;当主…

力扣 乘积最大子数组

动态规划&#xff0c;注意负负得正&#xff0c;dp交换。 题目 注意这里的dp的乘积要求最大&#xff0c;而两个很大的负数相乘也是大的&#xff0c;因此在每遍历到一个数时要存一个最大值的dp与一个最小值的dp&#xff0c;然后遍历完后再去存ans的dp。由于存在负数&#xff0c;…

【Postgresql】Windows 部署 Postgresql 数据库 (图文教程)

文章目录 准备工作Postgresql 下载Postgresql 安装初始化数据库数据库链接设置允许远程连接测试链接 更多相关内容可查看 准备工作 操作系统&#xff1a;Windows 7 或更高版本&#xff08;推荐 Windows 10 或 Windows Server 2016&#xff09;。 硬件要求&#xff1a; 至少 …

【ENSP】链路聚合的两种模式

【ENSP】链路聚合的两种模式 1、背景介绍2、链路聚合的使用场景3、配置过程1、手工模式Eth-Trunk配置2、静态LACP模式Eth-Trunk 4、总结 1、背景介绍 随着网络规模的不断扩大&#xff0c;人们对骨干链路的带宽吞吐量和可靠性提出了越来越高的要求。在传统方案中&#xff0c;为…

《深度学习》——调整学习率和保存使用最优模型

调整学习率 在使用 PyTorch 进行深度学习训练时&#xff0c;调整学习率是一个重要的技巧&#xff0c;合适的学习率调整策略可以帮助模型更好地收敛。 PyTorch 提供了多种调整学习率的方法&#xff0c;下面将详细介绍几种常见的学习率调整策略及实例代码&#xff1a; torch.opt…

SpringBoot+微信小程序+数据可视化的宠物到家喂宠服务(程序+论文+讲解+安装+调试+售后等)

感兴趣的可以先收藏起来&#xff0c;还有大家在毕设选题&#xff0c;项目以及论文编写等相关问题都可以给我留言咨询&#xff0c;我会一一回复&#xff0c;希望帮助更多的人。 系统介绍 在经济高速发展、物质生活极大丰富的当下&#xff0c;人们的精神需求愈发凸显&#xff0…

《仙台有树》追剧疑问与DeepSeek解答

本篇形式&#xff1a;直接以两段对话直接呈现&#xff0c;有删减 本篇背景&#xff1a;看过太多逻辑bug&#xff0c;有些bug无药可救直接弃剧&#xff0c;有些bug情有可原包容理解。想到最近大火的DeepSeek&#xff0c;就与时俱进&#xff0c;简单直接点吧&#xff0c;也许自己…

Java版企业电子招标采购系统源业码Spring Cloud + Spring Boot +二次开发+ MybatisPlus + Redis

功能描述 1、门户管理&#xff1a;所有用户可在门户页面查看所有的公告信息及相关的通知信息。主要板块包含&#xff1a;招标公告、非招标公告、系统通知、政策法规。 2、立项管理&#xff1a;企业用户可对需要采购的项目进行立项申请&#xff0c;并提交审批&#xff0c;查看所…