1作用域在 Python 中只有“模块文件”、“函数def”和“类class”会创建新的作用域。除此之外所有缩进的代码块if、for 等都共用外面那一层的作用域。比如def init_network(): with open(../DeepLearningFromScratch-master/DeepLearningFromScratch-master/ch03/sample_weight.pkl,rb) as f: networkpickle.load(f) return networkreturn在with执行代码外面但是能读到with执行代码内部创建的局部变量说明network的生命周期在整个函数内if、for也是如此2全局变量Python的全局变量只读取全局变量的值如果你的函数只需要拿全局变量的数据来用直接写变量名就行Python 会自动去全局找network {W1: 0.5, b1: 0.1} # 全局变量 def read_weight(): # 这里只是“读取” network没有给它赋新值完全合法 w network[W1] print(w) read_weight() # 输出0.5修改全局变量指向的“内部内容”✅ 无需声明但要小心如果你的全局变量是字典dict或列表list你只是想修改里面的值比如换掉 network[W1] 的数字而不是把整个 network 替换掉那么也不需要 global。network {W1: 0.5} def update_value(): # 这里是“修改字典内部元素”而不是“给 network 重新赋值” network[W1] 0.9 update_value() print(network[W1]) # 输出0.9全局变量被成功修改了给全局变量重新赋值❌ 必须使用 global如果你的函数里写了 network {...}这叫作“赋值语句”。Python 会默认在函数内部创建一个新的局部变量外部的全局变量完全不会受影响。如果想让它修改全局变量必须在赋值前加上 global network。network {W1: 0.5} # 原始的全局变量 def bad_update(): network {W1: 0.9} # 没加 global这只是在函数内部新建了一个局部变量 print(函数内部:, network[W1]) # 输出 0.9 bad_update() print(函数外部:, network[W1]) # 输出 0.5全局完全没变 # ---------- 正确写法 ---------- def good_update(): global network # 先声明“我要用的是外部的那个 network” network {W1: 0.9} # 现在这行修改的是真正的全局变量了 good_update() print(函数外部:, network[W1]) # 输出 0.9全局被改掉了3python是解释语言一个函数返回值的类型你可以直接使用该类型及其内部的成员函数、变量不用import该类型但是创建该类型的变量需要import(train_img, train_label), (test_img, test_label) load_mnist(True,True,False) # 这里返回值中的元素都是np数组 print(train_img.shape) # 这里虽然没有import numpy但是可以直接用.shape在 C 中你有一个std::vectorint对象。如果你想调用v.size()编译器在编译时必须知道vector类里有size()这个成员函数。如果没包含头文件声明编译直接报错。在 Python 中train_img已经是一个“活生生”的 NumPy 数组对象了。它存储在内存里自带一个内部字典__dict__里面装着所有属性和方法。当你写.shape时Python 根本不去看什么类声明它只是运行时去这个对象的内存里找有没有叫shape的东西。找到了就直接返回数值。4视图和副本就像引用和拷贝一样import numpy as np xnp.array([1,2]) yx[0] y100 print(x) # [1 2] xnp.array([[1],[2]]) yx[0] y[0]1000 print(x) # [[1000] [ 2]]np数组中一维的取值是副本多维的取值是视图会产生视图的情况# 基本切片含步长 arr np.arange(10) view1 arr[2:8] # 切片 view2 arr[::2] # 带步长的切片也是视图 view3 arr[1, :] # 取二维数组的一行标量索引 切片 view4 arr[:, 0] # 取二维数组的一列 # 数组转置.T和部分重塑.reshape arr_2d np.array([[1,2],[3,4]]) view5 arr_2d.T # 转置 view6 arr.reshape(2, 5) # 绝大多数情况下 reshape 返回视图只要数据连续 # .view() 方法 view7 arr.view() # 显式创建视图 # np.diag()、np.triu() 等部分创建函数取决于版本和参数会产生副本的情况# 花式索引整数数组/列表索引 copy1 arr[[0, 2, 4]] # 索引是列表返回副本 copy2 arr[[1, 2]] # 二维数组取特定行 # 布尔掩码索引 copy3 arr[arr 5] # 用条件筛选返回副本 # 显式复制 copy4 arr.copy() # 强制独立副本 copy5 arr.flatten() # flatten 总是返回副本ravel 通常返回视图 # 类型转换.astype() copy6 arr.astype(np.float32) # 改变 dtype 一定会创建新内存5np数组原地修改不允许跨类和升级可以降级import numpy as np # xnp.array([1,2]) # x[0]0.1 # print(x) # [1 2] # x[0]-1.1 # print(x) # [0 2] 标量赋值会被截断向零舍入直接砍掉小数部分 # print(x*0.1) # [0.1 0.2] # xx*0.1是重新申请空间赋值不报错x*0.1是原地修改直接报错 # xx1 # print(x) #[False True] 原地运算允许整型到布尔降级转换 # # x*1 直接报错 原地运算不允许布尔到整型的升级转换 # print(x*1) # [1 0] 这里只要不是原地修改就不影响 # xnp.array([[1,2],[3,4]]) # #x[0]0.1 直接报错