Python从其他代码文件导入变量时img未定义报错如何解决
报错原因
当你使用import语句导入Python文件时,解释器会完整执行目标文件的所有顶层代码,你的报错触发逻辑为:
- 如果
./images/目录下没有匹配的.jpg图片,images列表为空,for fname in images循环完全不会运行,img变量从未被创建 - 循环结束后执行
h, w = img.shape[:2]时就会抛出NameError: name 'img' is not defined
即便目录下有图片,导入时也会触发cv2.imshow逐张弹出校准图片需要手动确认,完全不符合工具模块导入的使用需求。
最优解决方法
不要直接导入变量,先将校准生成的参数持久化存储到本地文件,主代码直接读取文件获取参数即可,效率更高也不会触发不必要的代码执行。
第一步:修改Calibration.py代码
增加入口保护和参数存储逻辑,修改后代码如下:
import cv2 import numpy as np import os import glob # 仅在直接运行本文件时执行校准逻辑,导入时不会运行 if __name__ == "__main__": # Defining the dimensions of checkerboard CHECKERBOARD = (7, 9) criteria = (cv2.TERM_CRITERIA_EPS + cv2.TERM_CRITERIA_MAX_ITER, 30, 0.001) # Creating vector to store vectors of 3D points for each checkerboard image objpoints = [] # Creating vector to store vectors of 2D points for each checkerboard image imgpoints = [] # Defining the world coordinates for 3D points objp = np.zeros((1, CHECKERBOARD[0] * CHECKERBOARD[1], 3), np.float32) objp[0, :, :2] = np.mgrid[0:CHECKERBOARD[0], 0:CHECKERBOARD[1]].T.reshape(-1, 2) prev_img_shape = None # Extracting path of individual image stored in a given directory images = glob.glob('./images/*.jpg') for fname in images: img = cv2.imread(fname) gray = cv2.cvtColor(img, cv2.COLOR_BGR2GRAY) # Find the chess board corners # If desired number of corners are found in the image then ret = true ret, corners = cv2.findChessboardCorners(gray, CHECKERBOARD, cv2.CALIB_CB_ADAPTIVE_THRESH + cv2.CALIB_CB_FAST_CHECK + cv2.CALIB_CB_NORMALIZE_IMAGE) """ If desired number of corner are detected, we refine the pixel coordinates and display them on the images of checker board """ if ret == True: objpoints.append(objp) # refining pixel coordinates for given 2d points. corners2 = cv2.cornerSubPix(gray, corners, (11, 11), (-1, -1), criteria) imgpoints.append(corners2) # Draw and display the corners img = cv2.drawChessboardCorners(img, CHECKERBOARD, corners2, ret) cv2.imshow('img', img) cv2.waitKey(0) cv2.destroyAllWindows() h, w = img.shape[:2] """ Performing camera calibration by passing the value of known 3D points (objpoints) and corresponding pixel coordinates of the detected corners (imgpoints) """ ret, mtx, dist, rvecs, tvecs = cv2.calibrateCamera(objpoints, imgpoints, gray.shape[::-1], None, None) print("Camera matrix : \n") print(mtx) print("dist : \n") print(dist) print("rvecs : \n") print(rvecs) print("tvecs : \n") print(tvecs) # 保存校准参数到本地文件 np.savez("calib_params.npz", mtx=mtx, dist=dist, rvecs=rvecs, tvecs=tvecs)
修改完成后直接单独运行一次Calibration.py,会在同级目录生成calib_params.npz参数文件。
第二步:主代码读取参数
不需要导入Calibration.py,直接读取参数文件即可获取需要的变量:
import numpy as np # 加载校准参数 params = np.load("calib_params.npz") mtx = params["mtx"] dist = params["dist"] rvecs = params["rvecs"] tvecs = params["tvecs"]
内容的提问来源于stack exchange,提问作者Rami El-Assaad
相关产品推荐
相关产品推荐

