Lesson 3. 线性回归的手动实现(3.1 变量相关性基础理论 & 3.2 数据生成器与 Python 模块编写)

简介: Lesson 3. 线性回归的手动实现(3.1 变量相关性基础理论 & 3.2 数据生成器与 Python 模块编写)

文章目录


  • 在此前的内容当中,我们已经学习了关于线性回归模型的基本概念,并且介绍了一个多元线性回归的损失函数求解方法——最小二乘法。
  • 在有了这一些列理论推导之后,本节我们将尝试在一个手动构建的数据集上进行完整的线性回归模型建模。


一、变量相关性基础理论


  • 变量彼此之间的相关性,是我们探究数据规律的重要手段。对于机器学习,相关性也是数据探索、特征工程环节的重要理论。
  • 因此,我们先介绍关于连续变量相关性的基础理论,并且在该理论基础之上,探讨关于规律捕捉和规律创造的相关话题,为下一节创建数据生成器做准备。
# 科学计算模块
import numpy as np
import pandas as pd
# 绘图模块
import matplotlib as mpl
import matplotlib.pyplot as plt

机器学习的学习目标,其实就是数据集中隐藏的数字规律,而又由于这些规律背后代表的是某些事物的真实属性或者运行状态。

相关系基本解释与相关系数计算公式

对于不同数据集来说,是否具备规律、以及规律隐藏的深浅都不一样。

对于模型来说,擅长挖掘的规律、以及规律挖掘的能力也都各不相同。

对于线性回归来说,捕捉的实际上是数据集的线性相关的规律。所谓线性相关,简单来说就是数据的同步变化特性。例如此前数据集:

Whole weight Rings
1 2
3 4


特征和标签就存在着非常明显的同步变化的特性:第二条样本特征增加 2、对应标签也增加 2,当然,这也就是线性模型本身可解释性的来源——体重越大的鲍鱼、年龄越大,并且体重每增加 2、年龄也增加 2。

这种同步变化特性用更加专业的角度来描述就是变量之间的相关性。这种相关性可以用一个计算公式算得,也就是相关性系数计算公式:

32.png


  • 此处介绍的相关系数计算也被称为皮尔逊相关系数,最早由统计学家卡尔·皮尔逊提出,是目前最为通用的相关系数计算方法。
  • 相关系数计算在 NumPy 中的实现
  • 当然,在 NumPy 中也提供了相关系数计算函数 corrcoef 可用于快速计算两个数组之间的相关系数。
A = np.array([[1, 2, 3], [4, 5, 10]]).T
A
#array([[ 1,  4],
#       [ 2,  5],
#       [ 3, 10]])
A[:, 0]
#array([1, 2, 3])
np.corrcoef(A[:, 0], A[:, 1])
#array([[1.        , 0.93325653],
#       [0.93325653, 1.        ]])

该函数最终返回的是相关系数矩阵 A 2 ∗ 2 A_{2*2}A 2∗2 ,其中 a i , j a_{i,j}a i,j

 表示第 i、j 两个变量之间的相关系数。

相关系数矩阵是一个对角线元素全是 1 的矩阵,并且上三角和下三角元素对应位置元素相等。当然,对于 A 中的两个数组相关系数计算结果为 0.933。

相关系数计算结果解读

相关系数的计算结果取值为 [-1,1] 之内,取值为负时代表两个变量同步变化关系为负,也就是其中一个数值增加、另一个数值减少。例如:

A = np.array([[1, 2, 3], [-1, -1.5, -5]]).T
A
#array([[ 1. , -1. ],
#       [ 2. , -1.5],
#       [ 3. , -5. ]])
plt.plot(A[:, 0], A[:, 1])

ddfa97a0bdad4a73bb3e1fcb893c603b.png


np.corrcoef(A[:, 0], A[:, 1])
#array([[ 1.        , -0.91766294],
#       [-0.91766294,  1.        ]])

总体来说,相关系数绝对值越大两个变量的相关性越强,绝对值为 1 时候代表完全相关,两个变量完全线性同步变化,其中一个变量可以由另一个变量线性表出。

绝对值为 0 时,则表示完全线性无关,两个变量没有线性同步变化规律,这两个变量没有线性关系。当绝对值介于 0 和 1 之间时候,相关性强弱可以表示如下:

Cor 相关性
0~0.09 没有相关性
0.1~0.3 弱相关
0.3~0.5 中等相关
0.5~1.0 强相关


  • 如果是双变量的相关性,我们也可以用一组函数关系及图像来进行表示。
np.random.randn(20)
#array([-1.64976142, -0.87343737,  0.07530987, -1.42079571, -0.83262953,
#        1.21936676, -0.75871775,  0.44775161,  0.46307329,  1.44154581,
#        0.79686385, -1.50887509, -0.53100092,  2.41405101, -0.28564285,
#       -1.51317621, -0.90461468, -0.45806723,  1.0310925 , -0.58551109])
X = np.random.randn(20)
y = X + 1


  • 很明显,此时 X 和 y 完全正相关。
np.corrcoef(X, y)
#array([[1., 1.],
#       [1., 1.]])
# 对应点图
plt.plot(X, y, 'o')



d2f47b18073f4f9f9cf014805a54e1e5.png

  • 当然,如果我们想在 y 基础上创建一个稍微弱化线性相关关系的数组,可以在 y 基础上加入一个随机数作为扰动项。例如:
a = y.shape
a
#(20,)
np.random.normal?
# 创建一个和y一样形状的服从标准正态分布的随机数组
np.random.normal(size=a)
#array([ 0.49622906,  1.3573347 , -0.20178063,  0.87805077, -1.42474422,
#       -1.70856044, -1.0952294 , -0.58293826,  1.09455328, -0.68583135,
#       -0.64713056,  0.26123903, -0.47562764,  1.39130696,  0.6881981 ,
#        0.30883974, -0.19414512,  1.6188312 , -2.05761665,  0.14654045])
np.random.normal?
ran = np.random.normal(size = X.shape)
ran
#array([ 0.26042618, -1.04154116, -0.08313493, -0.79742972, -0.13280839,
#        1.27921862,  0.48826155, -0.60279756,  0.60330237, -0.71903143,
#        0.2286587 ,  1.9293763 ,  2.45620622,  0.78343275, -0.37187501,
#        0.91938857,  1.79980253, -0.45157682, -0.37647247,  1.03357355])


  • 接下来,创建一个控制扰动项大小的变量 delta 。
delta = 0.5


  • 因此,扰动项最终计算过程为:
r = ran * delta
r
#array([ 0.13021309, -0.52077058, -0.04156746, -0.39871486, -0.0664042 ,
#        0.63960931,  0.24413077, -0.30139878,  0.30165118, -0.35951571,
#        0.11432935,  0.96468815,  1.22810311,  0.39171637, -0.18593751,
#        0.45969429,  0.89990127, -0.22578841, -0.18823623,  0.51678678])
y1 = y + r
y1
#array([ 0.16849765,  1.33677569,  2.94351355,  1.068285  ,  1.27528793,
#        0.41509024, -1.33128073,  1.71470201,  0.40760464,  0.84310426,
#        1.86461507, -0.33425138,  1.99110458,  1.67303745,  0.06872278,
#        0.07684552,  0.20245359,  0.7843353 ,  1.5186445 ,  2.23064098])



此处,y1 就是在 y 基础上加入扰动项之后的标签。由于有一个随性扰动项的存在,会使得 y1 和 X 的线性关系被削弱。

从更根本的角度来说,加入扰动项削弱线性相关性,也是因为扰动项本身无规律可循,加入数据之后只会掩盖原始规律。

类似扰动项我们也可称其为白噪声。白噪声其实也有一定的实际背景,在很多情况下,我们采集的数据本身就是包含一定随机误差的,或者说是包含了无法帮助提取有效规律的信息。

plt.subplot(121)
plt.plot(X, y, 'o')
plt.title('y=x+1')
plt.subplot(122)
plt.plot(X, y1, 'o')
plt.title('y=x+1+r')

bd5b7cba603141ebbb3a3639ba18fb3e.png

  • 由此可见,在加入了扰动项之后,模型线性相关性明显变弱。
  • 当然,伴随 delta 的增加,噪声数据的绝对值会越来越大,掩盖原始数据线性相关规律的趋势会更加明显。我们可以简单用一组图像来展示不同相关性时双变量呈现的分布情况:
# delta系数取值数组
dl = [0.5, 0.7, 1, 1.5, 2, 5]
# 空列表容器
yl = []          # 不同delta下y的取值所组成的列表
cl = []          # 不同y下相关系数矩阵所组成的列表
# 计算不同delta下y和相关系数计算情况
for i in dl:
    yn = X + 1 + (ran * i)
    cl.append(np.corrcoef(X, yn))
    yl.append(yn)
cl
#[array([[1.       , 0.9367437],
#        [0.9367437, 1.       ]]),
# array([[1.       , 0.8911804],
#        [0.8911804, 1.       ]]),
# array([[1.        , 0.81961547],
#        [0.81961547, 1.        ]]),
# array([[1.        , 0.71248276],
#        [0.71248276, 1.        ]]),
# array([[1.        , 0.62837293],
#        [0.62837293, 1.        ]]),
# array([[1.        , 0.39817207],
#        [0.39817207, 1.        ]])]
yl
#[array([ 1.627525  , -0.88382241,  1.86933795, -0.02300046,  0.73433085,
#        -0.33109922,  1.33691722,  2.86218277,  0.41444553,  1.9081874 ,
#        -1.15456573, -1.10209687,  0.22127724,  1.08855797,  2.65327611,
#         0.72665134,  1.91516867,  0.14535214, -0.00467952,  2.90418153]),
# array([ 1.83074703, -0.91569175,  2.18530488, -0.21976011,  0.71340074,
#        -0.63292082,  1.10134436,  3.28833318,  0.34776874,  1.78608826,
#        -1.14334884, -1.22150795,  0.02903983,  1.2104614 ,  2.61838561,
#         0.76623911,  1.93033199,  0.01149336,  0.01992074,  2.97614544]),
# array([ 2.13558008, -0.96349575,  2.65925528, -0.5148996 ,  0.68200557,
#        -1.08565322,  0.74798509,  3.92755879,  0.24775356,  1.60293956,
#        -1.12652351, -1.40062457, -0.25931629,  1.39331655,  2.56604986,
#         0.82562076,  1.95307696, -0.18929479,  0.05682113,  3.0840913 ]),
# array([ 2.64363515, -1.04316909,  3.4491726 , -1.00679874,  0.62968028,
#        -1.84020721,  0.15905296,  4.99293481,  0.08106159,  1.29769172,
#        -1.0984813 , -1.69915227, -0.73990982,  1.69807513,  2.47882362,
#         0.92459017,  1.99098525, -0.52394172,  0.11832178,  3.26400107]),
# array([ 3.15169023, -1.12284243,  4.23908993, -1.49869788,  0.577355  ,
#        -2.59476121, -0.42987917,  6.05831082, -0.08563037,  0.99244388,
#        -1.07043908, -1.99767997, -1.22050335,  2.00283371,  2.39159737,
#         1.02355959,  2.02889354, -0.85858865,  0.17982242,  3.44391085]),
# array([ 6.20002067, -1.60088248,  8.9785939 , -4.45009273,  0.26340331,
#        -7.12208519, -3.96347196, 12.45056692, -1.08578218, -0.83904317,
#        -0.90218579, -3.78884616, -4.10406454,  3.83138519,  1.86823989,
#         1.6173761 ,  2.25634329, -2.86647023,  0.54882631,  4.52336949])]
plt.plot(X, yl[0], 'o')

9fcd461b6693486ab0377989d212ae2c.png


plt.subplot(231)
plt.plot(X, yl[0], 'o')
plt.plot(X, y, 'r-')
plt.subplot(232)
plt.plot(X, yl[1], 'o')
plt.plot(X, y, 'r-')
plt.subplot(233)
plt.plot(X, yl[2], 'o')
plt.plot(X, y, 'r-')
plt.subplot(234)
plt.plot(X, yl[3], 'o')
plt.plot(X, y, 'r-')
plt.subplot(235)
plt.plot(X, yl[4], 'o')
plt.plot(X, y, 'r-')
plt.subplot(236)
plt.plot(X, yl[5], 'o')
plt.plot(X, y, 'r-')

cf6e1191d68647058b925f977579638f.png

能够明显看出,伴随 delta 取值越来越大,数据相关性越来越弱,当然,我们也能通过观察 cl 的取值来查看各组变量的相关系数。

cl
#[array([[1.       , 0.9367437],
#        [0.9367437, 1.       ]]),
# array([[1.       , 0.8911804],
#        [0.8911804, 1.       ]]),
# array([[1.        , 0.81961547],
#        [0.81961547, 1.        ]]),
# array([[1.        , 0.71248276],
#        [0.71248276, 1.        ]]),
# array([[1.        , 0.62837293],
#        [0.62837293, 1.        ]]),
# array([[1.        , 0.39817207],
#        [0.39817207, 1.        ]])]


捕捉规律与创建规律

简单线性回归就是在二维平面中通过构建一条直线来试图捕捉平面当中的点,线性相关性越弱、线性模型越难捕捉到这些所有点,模型效果就越差。

数据集之间线性相关性越明显,数据规律越明显,模型越容易捕捉到这些规律。

在这个基础理论之上,我们有以下两方面的应用:

(1) 可以在构建线性模型之前先探查数据本身的线性相关性,如果自变量和因变量存在很好的相关性,那就一定可以顺利的构建线性回归模型对数据进行拟合。

如果线性相关性不强,则说明当前数据并不适合构建线性回归模型,或者在构建模型之前我们需要对数据进行一些不影响真实规律的转化,令其表现出线性的分布趋势。

(2) 上述几组不同的数据,实际上就代表着对线性回归模型建模难度各不相同的几组数据, delta 越大对线性回归模型来说建模就更加困难。

据此,我们可以生成一个手动创建数据集的函数,该函数可以输出不同建模难度(规律深浅)的数据集,来辅助我们测试模型和优化算法的性能。

这里需要注意:线性相关性的减弱,不仅是对于线性回归模型,对于很多回归类问题都会造成更大的建模困难。


二、数据生成器与 Python 模块编写

  • 在有了相关性理论基础之后,我们即可创建一个可用于回归模型实验的数据生成器。
# 科学计算模块
import numpy as np
import pandas as pd
# 绘图模块
import matplotlib as mpl
import matplotlib.pyplot as plt


1. 自定义数据生成器


为了方便后续练习的展开,我们尝试自己创建一个数据生成器,用于自主生成一些符合某些条件、难度可控、具备某些特性的数据集。

在初学过程中,我们需要通过类似控制变量的方法、通过设计一些实验,去深入理解算法运行原理及一些优化方法的实际作用,这就需要我们自己动手,创建一些数据用于实验的原材料,通过一些实验深入了解模型原理。


1.1 手动生成数据

  • 我们先尝试生成两个特征、存在偏差,自变量和因变量存在线性关系的数据集。
num_inputs = 2               # 两个特征
num_examples = 1000  # 总共一千条数据


  • 然后尝试通过线性方程,确定自变量和因变量的真实关系。
np.random.seed(24)       # 设置随机数种子
np.random.randn(2, 2)
#array([[ 1.32921217, -0.77003345],
#       [-0.31628036, -0.99081039]])
# 线性方程系数
w_true = np.array([2, -1]).reshape(-1, 1)
b_true = np.array(1)​
# 扰动项相关
delta = 0.01​
# 创建数据集的特征和标签取值
features = np.random.randn(num_examples, num_inputs)
labels_true = features.dot(w_true) + b_true
labels = labels_true + np.random.normal(size = labels_true.shape) * delta
features
#array([[-1.07081626, -1.43871328],
#       [ 0.56441685,  0.29572189],
#       [-1.62640423,  0.2195652 ],
#       ...,
#       [-1.44029131,  0.50439425],
#       [ 0.96604603,  1.76623359],
#       [ 0.57852053, -1.34028424]])
labels_true


labels_true 所产生的数据如下。

df2d8bef67ec4487984d7dc757775d57.png



注意,此时 labels_true 和 features 满足严格意义上的线性方程关系


y=2x1x2+1


但我们实际使用的标签 labels,则是在 labels_true 的基础上增添了一个扰动项,np.random.normal(size = labels_true.shape) * delta,这其实也符合我们一般获取数据的情况:真实客观世界或许存在某个规律,但我们搜集到的数据往往会因为各种原因存在一定的误差,无法完全描述真实世界的客观规律,这其实也是模型误差的来源之一(另一个误差来源是模型本身捕获规律的能力)。


y=2x1x2+1

  • 相当于我们从上帝视角创建的数据真实服从的规律,而扰动项,则相当于人为创造的获取数据时的误差。
  • 简单查看我们创建的数据集。
features[: 10]
#array([[-1.07081626, -1.43871328],
#       [ 0.56441685,  0.29572189],
#       [-1.62640423,  0.2195652 ],
#       [ 0.6788048 ,  1.88927273],
#       [ 0.9615384 ,  0.1040112 ],
#       [-0.48116532,  0.85022853],
#       [ 1.45342467,  1.05773744],
#       [ 0.16556161,  0.51501838],
#       [-1.33693569,  0.56286114],
#       [ 1.39285483, -0.06332798]])
labels[: 10]
#array([[ 0.29161817],
#       [ 1.83851813],
#       [-2.46058022],
#       [ 0.44394438],
#       [ 2.8133944 ],
#       [-0.8109745 ],
#       [ 2.85143778],
#       [ 0.83156296],
#       [-2.22624102],
#       [ 3.84279053]])
plt.subplot(121)
plt.scatter(features[:, 0], labels)          # 第一个特征和标签的关系
plt.subplot(122)
plt.scatter(features[:,, 1] labels)          # 第二个特征和标签的关系


05bb3541bf0d42508901a14289d8be2b (1).png


  • 不难看出,两个特征和标签都存在一定的线性关系,并且跟特征的系数绝对值有很大关系。
  • 当然,若要增加线性模型的建模难度,可以增加扰动项的数值比例,从而削弱线性关系。
# 设置随机数种子
np.random.seed(24)   
# 修改因变量
labels1 = labels_true + np.random.normal(size = labels_true.shape) * 2
# 可视化展示
# 扰动较小的情况
plt.subplot(221)
plt.scatter(features[:, 0], labels)             # 第一个特征和标签的关系
plt.subplot(222)
plt.plot(features[:, 1], labels, 'ro')          # 第二个特征和标签的关系
# 扰动较大的情况
plt.subplot(223)
plt.scatter(features[:, 0], labels1)             # 第一个特征和标签的关系
plt.subplot(224)
plt.plot(features[:, 1], labels1, 'yo')          # 第二个特征和标签的关系


60c2a5c89515449a93c81aeacad22330.png


当然,我们也能生成非线性关系的数据集,此处我们创建满足y=2x2+1规律的数据集

np.power([2, 3], 2)
#array([4, 9], dtype=int32)
# 设置随机数种子
np.random.seed(24)   
num_inputs = 1               # 一个特征
num_examples = 1000          # 总共一千条数据
# 线性方程系数
w_true = np.array(2)
b_true = np.array(1)
# 特征和标签取值
features = np.random.randn(num_examples, num_inputs)
labels_true = np.power(features, 2) * w_true + b_true
labels = labels_true + np.random.normal(size = labels_true.shape) * 2
# 可视化展示
plt.scatter(features, labels)


b479b7a55c3b45248ba037436d706a74.png

此时需要注意的是,无论是创建了曲线规律的数据集,还是增加了扰动项绝对数值,都会对建模造成困难,但二者的造成困难的方式是不同的。

如果是曲线规律的数据集,则代表规律本身更加复杂,此时需要使用更加复杂的模型来进行规律提取,该部分属于模型选取和参数调优的技术内容。

如果是扰动项比较大,则代表规律被掩盖的比较深,此时需要采用其他技术手段进行白噪声的处理,该部分属于特征工程技术内容。


1.2 创建生成回归类数据的函数

  • 为了方便后续使用,我们将上述过程封装在一个函数内。
  • 定义创建函数
A = np.arange(4).reshape(2, 2)
A
#array([[0, 1],
#       [2, 3]])
np.power(A, 3)
#array([[ 0,  1],
#       [ 8, 27]], dtype=int32)
A.dot(2)
#array([[0, 2],
#       [4, 6]])
np.ones_like(A)
#array([[1, 1],
#       [1, 1]])


def arrayGenReg(num_examples = 1000, w = [2, -1, 1], bias = True, delta = 0.01, deg = 1):
    """回归类数据集创建函数。
    :param num_examples: 创建数据集的数据量
    :param w: 包括截距的(如果存在)特征系数向量
    :param bias:是否需要截距
    :param delta:扰动项取值
    :param deg:方程最高项次数
    :return: 生成的特征数组和标签数组
    """
    if bias == True:
        num_inputs = len(w)-1                                                           # 数据集特征个数
        features_true = np.random.randn(num_examples, num_inputs)                       # 原始特征
        w_true = np.array(w[:-1]).reshape(-1, 1)                                        # 自变量系数
        b_true = np.array(w[-1])                                                        # 截距
        labels_true = np.power(features_true, deg).dot(w_true) + b_true                 # 严格满足人造规律的标签
        features = np.concatenate((features_true, np.ones_like(labels_true)), axis=1)    # 加上全为1的一列之后的特征
    else: 
        num_inputs = len(w)
        features = np.random.randn(num_examples, num_inputs) 
        w_true = np.array(w).reshape(-1, 1)         
        labels_true = np.power(features, deg).dot(w_true)
    labels = labels_true + np.random.normal(size = labels_true.shape) * delta
    return features, labels

33.png

# 设置随机数种子
np.random.seed(24)   
# 扰动项取值为0.01
f, l = arrayGenReg(delta=0.01)
f
#array([[ 1.32921217, -0.77003345,  1.        ],
#       [-0.31628036, -0.99081039,  1.        ],
#       [-1.07081626, -1.43871328,  1.        ],
#       ...,
#       [ 1.5507578 , -0.35986144,  1.        ],
#       [-1.36267161, -0.61353562,  1.        ],
#       [-1.44029131,  0.50439425,  1.        ]])
# 绘制图像查看结果
plt.subplot(121)
plt.scatter(f[:, 0], l)             # 第一个特征和标签的关系
plt.subplot(122)
plt.scatter(f[:, 1], l)             # 第二个特征和标签的关系

ce33ab25dee5427696b0971e5a0762a9.png


  • 然后查看扰动项较大时数据情况。
# 设置随机数种子
np.random.seed(24)   
# 扰动项取值为2
f, l = arrayGenReg(delta=2)
# 绘制图像查看结果
plt.subplot(121)
plt.scatter(f[:, 0], l)             # 第一个特征和标签的关系
plt.subplot(122)
plt.scatter(f[:, 1], l)             # 第二个特征和标签的关系


b32468948a614da499d97d47466e58f7.png

  • 当特征和标签满足二阶关系时候数据表现。
# 设置随机数种子
np.random.seed(24)   
# 最高次项为2
f, l = arrayGenReg(deg=2)
# 绘制图像查看结果
plt.subplot(121)
plt.scatter(f[:, 0], l)             # 第一个特征和标签的关系
plt.subplot(122)
plt.scatter(f[:, 1], l)             # 第二个特征和标签的关系


915df3b7bb8c42a7bc8c8dbeaef54073.png

  • 在定义好数据创建函数之后,即可开始尝试手动实现线性回归模型。
  • 知识点补充:随机数种子的使用
  • 此处我们使用了一个随机数种子,以确保随机结果的可重复性。当我们设置某个随机数种子之后,每次随机过程都是可重复的:我们只需要再次调用相同随机种子,就可以重复此前随机过程。
np.random.randn(9)
#array([ 1.62779574,  0.35449279,  1.03752763, -0.38568351,  0.519818  ,
#        1.68658289, -1.32596315,  1.4289837 , -2.08935428])
np.random.seed(24)
np.random.randn(9)
#array([ 1.32921217, -0.77003345, -0.31628036, -0.99081039, -1.07081626,
#       -1.43871328,  0.56441685,  0.29572189, -1.62640423])
np.random.randn(9)
#array([ 0.2195652 ,  0.6788048 ,  1.88927273,  0.9615384 ,  0.1040112 ,
#       -0.48116532,  0.85022853,  1.45342467,  1.05773744])
np.random.seed(24)
np.random.randn(9)
#array([ 1.32921217, -0.77003345, -0.31628036, -0.99081039, -1.07081626,
#       -1.43871328,  0.56441685,  0.29572189, -1.62640423])
np.random.randn(9)
#array([ 0.2195652 ,  0.6788048 ,  1.88927273,  0.9615384 ,  0.1040112 ,
#       -0.48116532,  0.85022853,  1.45342467,  1.05773744]) 


当然,不同随机数种子所诞生的随机过程是不一样的。

此外,不同库中的随机过程需要用的不同随机种子也是不同的,比如上述我们用 np.random.seed 来规定 numpy 中相关随机过程,但如果是其他第三方库,如 random 库所定义的随机过程,就需要使用 random 库中的随机种子来确定。

import random
l = list(range(5))
l
#[0, 1, 2, 3, 4]
random.seed(24)
random.shuffle(l)
l
#[4, 2, 0, 1, 3]
random.shuffle(l)
l
#[1, 4, 0, 3, 2]
l = list(range(5))
l
#[0, 1, 2, 3, 4]
random.seed(24)
random.shuffle(l)
l
#[4, 2, 0, 1, 3]
random.shuffle(l)
l
#[1, 4, 0, 3, 2]
l = list(range(5))
l
#[0, 1, 2, 3, 4]
np.random.seed(24)
random.shuffle(l)
l
#[4, 0, 3, 2, 1]
random.shuffle(l)
l
#[0, 4, 3, 1, 2]
l = list(range(5))
l
#[0, 1, 2, 3, 4]
np.random.seed(24)
random.shuffle(l)
l
#[4, 2, 3, 1, 0]


2. Python 模块的编写与调用


封装为模块有以下两种基本方法:

(1) 打开文本编辑器,将写好并测试完成的函数写入其中,并将文本的拓展名改写为 .py。

(2) 在 spyder 或者 pycharm 中复制相关函数,并保存为 .py 文件。

然后将文件保存在jupyter主目录下,并取名为 ML_basic_function,后续即可通过import

ML_basic_function 进行调用。

如果是 jupyter lab 用户,也可按照如下方式进行编写。

(1) 打开左侧文件管理栏页,点击新建。

486c2d0654334beaa68262cf75a713a7.png

  • (2) 在新建目录中,选择 Test File,并通过重命名将其命名为 ML_basic_function.py。

f38c4dbd017c47bea299b68887d15559.png


(3) 在打开的文本编辑器中输入代码,并且需要注意,需要在 .py 文件内导入相关的包。

3cdccf7c44dd48bfa0c15876922da2f6.png



4) 测试能否调用,首先重启当前 jupyter。


1fb1199e02fc474a98aaf492bad4d598.png



然后尝试导入自定义模块。



































































相关文章
|
4天前
|
JSON API 数据格式
Python网络编程:HTTP请求(requests模块)
在现代编程中,HTTP请求几乎无处不在。无论是数据抓取、API调用还是与远程服务器进行交互,HTTP请求都是不可或缺的一部分。在Python中,requests模块被广泛认为是发送HTTP请求的最简便和强大的工具之一。本文将详细介绍requests模块的功能,并通过一个综合示例展示其应用。
|
5天前
|
XML 存储 数据格式
使用Python的zipfile模块巧解Word批量生成问题
通过以上步骤,我们得到了填充了特定数据的 Word 文档。这个过程可以通过循环对多个数据集重复执行,从而实现批量生成多个 Word 文档的目标。
11 5
|
3天前
|
Python
Python模块的创建方法?
【8月更文挑战第18天】Python模块的创建方法?
4 2
|
3天前
|
Shell Python 容器
Python模块
【8月更文挑战第18天】Python模块
7 2
|
3天前
|
Shell Python 容器
Python模块是其代码组织和重用的基本方式。
【8月更文挑战第18天】Python模块是其代码组织和重用的基本方式。
8 1
|
4天前
|
机器学习/深度学习 JSON API
【Python奇迹】FastAPI框架大显神通:一键部署机器学习模型,让数据预测飞跃至Web舞台,震撼开启智能服务新纪元!
【8月更文挑战第16天】在数据驱动的时代,高效部署机器学习模型至关重要。FastAPI凭借其高性能与灵活性,成为搭建模型API的理想选择。本文详述了从环境准备、模型训练到使用FastAPI部署的全过程。首先,确保安装了Python及相关库(fastapi、uvicorn、scikit-learn)。接着,以线性回归为例,构建了一个预测房价的模型。通过定义FastAPI端点,实现了基于房屋大小预测价格的功能,并介绍了如何运行服务器及测试API。最终,用户可通过HTTP请求获取预测结果,极大地提升了模型的实用性和集成性。
18 1
|
5天前
|
数据采集 数据可视化 算法
GitHub星标68K!Python数据分析入门手册带你从数据获取到可视化
Python作为一门优秀的编程语言,近年来受到很多编程爱好者的青睐。一是因为Python本身具有简捷优美、易学易用的特点;二是由于互联网的飞速发展,我们正迎来大数据的时代,而Python 无论是在数据的采集与处理方面,还是在数据分析与可视化方面都有独特的优势。我们可以利用 Python 便捷地开展与数据相关的项目,以很低的学习成本快速完成项目的研究。
|
5天前
|
数据采集 Java PHP
使用Python+requests简单实现模拟登录以及抓取接口数据
本文通过Python的requests库演示了如何实现模拟登录和抓取接口数据的过程,包括设置请求头、发送POST请求进行登录以及使用登录后的会话进行GET请求获取数据。
17 1
|
1天前
|
缓存 NoSQL Shell
Python 模块的加载顺序
Python 模块的加载顺序
5 0
|
2天前
|
消息中间件 SQL Java
实时数仓 Hologres产品使用合集之如何用python将kafka数据写入
实时数仓Hologres是阿里云推出的一款高性能、实时分析的数据库服务,专为大数据分析和复杂查询场景设计。使用Hologres,企业能够打破传统数据仓库的延迟瓶颈,实现数据到决策的无缝衔接,加速业务创新和响应速度。以下是Hologres产品的一些典型使用场景合集。