运行《Scikit Learn与TensorFlow机器学习实战》示例代码遇文件找不到错误
解决MNIST数据集加载的FileNotFoundError问题
你遇到的这个FileNotFoundError本质上是scikit-learn旧API弃用加上代码逻辑顺序错误叠加导致的,我给你拆解原因和解决办法:
核心原因
fetch_mldata方法已经被scikit-learn彻底弃用,它原本的实现依赖手动下载MNIST数据集并放到指定目录,但新版本里这个API已经无法自动获取数据,只能依赖本地文件——你没提前准备这些文件,所以报错找不到mnist\train-labels-idx1-ubyte。- 你的代码还存在逻辑错误:先调用了
sgd_clf.fit(X_train, y_train_5),但y_train_5是在这之后才定义的,这其实会先引发NameError,只不过被数据集加载的问题掩盖了。
完整解决方案
1. 替换弃用的数据集加载API
改用scikit-learn官方推荐的fetch_openml方法,它能自动下载并缓存MNIST数据集,不需要手动处理任何本地文件。
2. 修正代码变量定义顺序
先定义二分类的目标变量y_train_5,再训练模型,避免未定义变量的错误。
3. 注意数据类型匹配
fetch_openml获取的标签y是字符串类型,判断是否为数字5时要和字符串'5'比较,而非数字5。
修正后的完整代码如下:
# 使用官方推荐的fetch_openml加载MNIST数据集 from sklearn.datasets import fetch_openml mnist = fetch_openml('mnist_784', version=1, cache=True, as_frame=False) X, y = mnist["data"], mnist["target"] # 确认数据集形状(应该输出(70000, 784)和(70000,)) print(X.shape) print(y.shape) # 可视化示例数字 import matplotlib import matplotlib.pyplot as plt some_digit = X[36000] some_digit_image = some_digit.reshape(28, 28) plt.imshow(some_digit_image, cmap=matplotlib.cm.binary, interpolation="nearest") plt.axis("off") plt.show() # 分割训练集和测试集(保持原书的60000/10000比例) X_train, X_test, y_train, y_test = X[:60000], X[60000:], y[:60000], y[60000:] # 先定义二分类目标:判断是否为数字5 y_train_5 = (y_train == '5') y_test_5 = (y_test == '5') # 训练SGD分类器并预测 from sklearn.linear_model import SGDClassifier sgd_clf = SGDClassifier(random_state=42) sgd_clf.fit(X_train, y_train_5) print(sgd_clf.predict([some_digit])) # 应该输出[True],因为X[36000]是数字5
额外说明
如果你坚持想用原书的旧方法(非常不推荐),需要手动从MNIST官方渠道下载四个压缩文件:
- train-images-idx3-ubyte.gz
- train-labels-idx1-ubyte.gz
- t10k-images-idx3-ubyte.gz
- t10k-labels-idx1-ubyte.gz
解压后放到脚本同级的mnist目录下,但这种方法不仅繁琐,还会因为scikit-learn版本更新出现更多兼容性问题,所以优先推荐使用fetch_openml的方案。
内容的提问来源于stack exchange,提问作者ASH
相关产品推荐
相关产品推荐

