如何从包含 Unicode 字符的路径读取图像?

问题描述 投票:0回答:6

我有以下代码,但它失败了,因为它无法从磁盘读取文件。图像始终是

None

# -*- coding: utf-8 -*-
import cv2
import numpy

bgrImage = cv2.imread(u'D:\\ö\\handschuh.jpg')

注意:我的文件已经保存为带有 BOM 的 UTF-8。我用Notepad++验证过。

在 Process Monitor 中,我看到 Python 正在从错误的路径访问文件:

Process Monitor

我读过:

python opencv unicode path
6个回答
44
投票

可以通过以下方式完成

  • 使用
    open()
    打开文件,它支持 Unicode,如链接答案中所示,
  • 将内容读取为字节数组,
  • 将字节数组转换为 NumPy 数组,
  • 解码图像
# -*- coding: utf-8 -*-
import cv2
import numpy

stream = open(u'D:\\ö\\handschuh.jpg', "rb")
bytes = bytearray(stream.read())
numpyarray = numpy.asarray(bytes, dtype=numpy.uint8)
bgrImage = cv2.imdecode(numpyarray, cv2.IMREAD_UNCHANGED)

或者(正如评论中提到的,感谢jdhao):

# -*- coding: utf-8 -*-
import cv2
import numpy

bgrImage = cv2.imdecode(np.fromfile(u'D:\\ö\\handschuh.jpg', np.uint8), cv2.IMREAD_UNCHANGED)

35
投票

受Thomas Weller的回答的启发,您还可以使用

np.fromfile()
读取图像并将其转换为ndarray,然后使用
cv2.imdecode()
将数组解码为三维numpy ndarray(假设这是一个没有Alpha 通道):

import numpy as np

# img is in BGR format if the underlying image is a color image
img = cv2.imdecode(np.fromfile('测试目录/test.jpg', dtype=np.uint8), cv2.IMREAD_UNCHANGED)

np.fromfile()
会将磁盘上的图像转换为 numpy 一维 ndarray 表示形式。
cv2.imdecode
可以解码此格式并转换为正常的 3 维图像表示。
cv2.IMREAD_UNCHANGED
是解码标志。完整的标志列表可以在这里找到。

PS。有关如何将图像写入带有 unicode 字符的路径,请参阅此处


1
投票

我将它们复制到临时目录中。对我来说效果很好。

import os
import shutil
import tempfile

import cv2


def cv_read(path, *args):
    """
    Read from a path with Unicode characters.

    :param path: path of a single image or a directory which contains images
    :param args: other args passed to cv2.imread
    :return: a single image or a list of images
    """
    with tempfile.TemporaryDirectory() as tmp_dir:
        if os.path.isdir(path):
            shutil.copytree(path, tmp_dir, dirs_exist_ok=True)
        elif os.path.isfile(path):
            shutil.copy(path, tmp_dir)
        else:
            raise FileNotFoundError

        img_arr = [
            cv2.imread(os.path.join(tmp_dir, img), *args)
            for img in os.listdir(tmp_dir)
        ]

        return img_arr if os.path.isdir(path) else img_arr[0]

0
投票

可以通过以下方式完成

  1. 保存当前目录
  2. 将当前目录更改为必须保存图像的目录
  3. 保存图像
  4. 将当前目录更改为步骤 1 中保存的目录
import os
from pathlib import Path
import cv2

im_path = Path(u'D:\\ö\\handschuh.jpg')

# Save current directory
curr_dir = os.getcwd()
# change current directory to the one the image must be saved
os.chdir(im_path.parent)
# read the image
bgrImage = cv2.imread(im_path.name)
# change current directory to the one saved in step 1
os.chdir(curr_dir)

-2
投票

我的问题和你类似,但是,我的程序将在以下位置终止

image = cv2.imread(filename)
声明。

我解决了这个问题,首先将文件名编码为utf-8,然后将其解码为

 image = cv2.imread(filename.encode('utf-8', 'surrogateescape').decode('utf-8', 'surrogateescape'))

-5
投票
bgrImage = cv2.imread(filename.encode('utf-8'))

将文件完整路径编码为utf-8

© www.soinside.com 2019 - 2024. All rights reserved.